diff --git a/.gitignore b/.gitignore index 995ff7b13..070bc265d 100644 --- a/.gitignore +++ b/.gitignore @@ -65,3 +65,9 @@ src/fluid/luajit-2.0.5/src/host/minilua src/fluid/luajit-2.0.5/src/jit/vmdef.lua release-git/ src/display/simd/ +data/fonts/truetype/NotoColorEmoji.ttf +build/ +debug-gdb/ +debug-mod/ +local-mod/ +local-gdb/ diff --git a/3rdparty/freetype-2.13.2/CMakeLists.txt b/3rdparty/freetype-2.13.2/CMakeLists.txt new file mode 100644 index 000000000..fec0decd4 --- /dev/null +++ b/3rdparty/freetype-2.13.2/CMakeLists.txt @@ -0,0 +1,245 @@ +# Copyright (C) 2013-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# Written originally by John Cary +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + +include(CheckIncludeFile) + +#-DFT_DEBUG_LEVEL_ERROR -DFT_DEBUG_LEVEL_TRACE + +option(FT_DISABLE_BZIP2 "" ON) +option(FT_DISABLE_BROTLI "" ON) +option(FT_ENABLE_ERROR_STRINGS "" OFF) +option(FT_CONFIG_OPTION_USE_LZW "" OFF) +option(FT_CONFIG_OPTION_MAC_FONTS "" OFF) +option(FT_CONFIG_OPTION_INCREMENTAL "" OFF) +option(TT_CONFIG_OPTION_BDF "" OFF) +option(FT_CONFIG_OPTION_USE_ZLIB "" OFF) +option(TT_CONFIG_OPTION_GX_VAR_SUPPORT "" OFF) + +# CMAKE_TOOLCHAIN_FILE must be set before `project' is called, which +# configures the base build environment and references the toolchain file +if (APPLE) + if (DEFINED IOS_PLATFORM) + if (NOT "${IOS_PLATFORM}" STREQUAL "OS" + AND NOT "${IOS_PLATFORM}" STREQUAL "SIMULATOR" + AND NOT "${IOS_PLATFORM}" STREQUAL "SIMULATOR64") + message(FATAL_ERROR + "IOS_PLATFORM must be set to either OS, SIMULATOR, or SIMULATOR64") + endif () + if (NOT "${CMAKE_GENERATOR}" STREQUAL "Xcode") + message(AUTHOR_WARNING + "You should use Xcode generator with IOS_PLATFORM enabled to get Universal builds.") + endif () + if (BUILD_SHARED_LIBS) + message(FATAL_ERROR + "BUILD_SHARED_LIBS can not be on with IOS_PLATFORM enabled") + endif () + if (BUILD_FRAMEWORK) + message(FATAL_ERROR + "BUILD_FRAMEWORK can not be on with IOS_PLATFORM enabled") + endif () + + # iOS only uses static libraries + set(BUILD_SHARED_LIBS OFF) + + set(CMAKE_TOOLCHAIN_FILE + ${CMAKE_SOURCE_DIR}/builds/cmake/iOS.cmake) + endif () +else () + if (DEFINED IOS_PLATFORM) + message(FATAL_ERROR "IOS_PLATFORM is not supported on this platform") + endif () +endif () + +project(freetype C) + +set(VERSION_MAJOR "2") +set(VERSION_MINOR "13") +set(VERSION_PATCH "2") + +# Generate LIBRARY_VERSION and LIBRARY_SOVERSION. +set(LIBTOOL_REGEX "version_info='([0-9]+):([0-9]+):([0-9]+)'") + +file(STRINGS "${PROJECT_SOURCE_DIR}/builds/unix/configure.raw" VERSION_INFO REGEX ${LIBTOOL_REGEX}) + +string(REGEX REPLACE ${LIBTOOL_REGEX} "\\1" LIBTOOL_CURRENT "${VERSION_INFO}") +string(REGEX REPLACE ${LIBTOOL_REGEX} "\\2" LIBTOOL_REVISION "${VERSION_INFO}") +string(REGEX REPLACE ${LIBTOOL_REGEX} "\\3" LIBTOOL_AGE "${VERSION_INFO}") + +# This is what libtool does internally on Unix platforms. +math(EXPR LIBRARY_SOVERSION "${LIBTOOL_CURRENT} - ${LIBTOOL_AGE}") +set(LIBRARY_VERSION "${LIBRARY_SOVERSION}.${LIBTOOL_AGE}.${LIBTOOL_REVISION}") + +option(FT_ENABLE_ERROR_STRINGS "Enable support for meaningful error descriptions." OFF) + +# Add local cmake modules +list(APPEND CMAKE_MODULE_PATH ${PROJECT_SOURCE_DIR}/builds/cmake) + +# Create the configuration file +if (UNIX) + check_include_file("unistd.h" HAVE_UNISTD_H) + check_include_file("fcntl.h" HAVE_FCNTL_H) + + file(READ "${PROJECT_SOURCE_DIR}/builds/unix/ftconfig.h.in" + FTCONFIG_H) + if (HAVE_UNISTD_H) + string(REGEX REPLACE + "#undef +(HAVE_UNISTD_H)" "#define \\1 1" + FTCONFIG_H "${FTCONFIG_H}") + endif () + if (HAVE_FCNTL_H) + string(REGEX REPLACE + "#undef +(HAVE_FCNTL_H)" "#define \\1 1" + FTCONFIG_H "${FTCONFIG_H}") + endif () +else () + file(READ "${PROJECT_SOURCE_DIR}/include/freetype/config/ftconfig.h" + FTCONFIG_H) +endif () + +set(FTCONFIG_H_NAME "${PROJECT_BINARY_DIR}/include/freetype/config/ftconfig.h") +if (EXISTS "${FTCONFIG_H_NAME}") + file(READ "${FTCONFIG_H_NAME}" ORIGINAL_FTCONFIG_H) +else () + set(ORIGINAL_FTCONFIG_H "") +endif () +if (NOT (ORIGINAL_FTCONFIG_H STREQUAL FTCONFIG_H)) + file(WRITE "${FTCONFIG_H_NAME}" "${FTCONFIG_H}") +endif () + +# Create the options file +file(READ "${PROJECT_SOURCE_DIR}/include/freetype/config/ftoption.h" FTOPTION_H) + +if (FT_ENABLE_ERROR_STRINGS) + string(REGEX REPLACE "/\\* +(#define +FT_CONFIG_OPTION_ERROR_STRINGS) +\\*/" "\\1" + FTOPTION_H "${FTOPTION_H}") +endif () + +set(FTOPTION_H_NAME "${PROJECT_BINARY_DIR}/include/freetype/config/ftoption.h") +if (EXISTS "${FTOPTION_H_NAME}") + file(READ "${FTOPTION_H_NAME}" ORIGINAL_FTOPTION_H) +else () + set(ORIGINAL_FTOPTION_H "") +endif () +if (NOT (ORIGINAL_FTOPTION_H STREQUAL FTOPTION_H)) + file(WRITE "${FTOPTION_H_NAME}" "${FTOPTION_H}") +endif () + +file(GLOB PUBLIC_HEADERS "include/ft2build.h" "include/freetype/*.h") +file(GLOB PUBLIC_CONFIG_HEADERS "include/freetype/config/*.h") +file(GLOB PRIVATE_HEADERS "include/freetype/internal/*.h") + +set(BASE_SRCS + src/autofit/autofit.c + src/base/ftbase.c +# src/base/ftbbox.c +# src/base/ftbdf.c + src/base/ftbitmap.c +# src/base/ftcid.c +# src/base/ftfstype.c +# src/base/ftgasp.c + src/base/ftglyph.c +# src/base/ftgxval.c + src/base/ftinit.c + src/base/ftmm.c +# src/base/ftotval.c + src/base/ftpatent.c +# src/base/ftpfr.c + src/base/ftstroke.c +# src/base/ftsynth.c + src/base/fttype1.c +# src/base/ftwinfnt.c +# src/bdf/bdf.c +# src/bzip2/ftbzip2.c + src/cache/ftcache.c + src/cff/cff.c +# src/cid/type1cid.c +# src/gzip/ftgzip.c +# src/lzw/ftlzw.c +# src/pcf/pcf.c +# src/pfr/pfr.c +# src/psaux/psaux.c + src/pshinter/pshinter.c + src/psnames/psnames.c + src/raster/raster.c +# src/sdf/sdf.c + src/sfnt/sfnt.c + src/smooth/smooth.c +# src/svg/svg.c + src/truetype/truetype.c +# src/type1/type1.c +# src/type42/type42.c +# src/winfonts/winfnt.c +) + +if (UNIX) + list(APPEND BASE_SRCS "builds/unix/ftsystem.c") +elseif (WIN32) + list(APPEND BASE_SRCS "builds/windows/ftsystem.c") +else () + list(APPEND BASE_SRCS "src/base/ftsystem.c") +endif () + +if (WIN32) + enable_language(RC) + list(APPEND BASE_SRCS builds/windows/ftdebug.c src/base/ftver.rc) +elseif (WINCE) + list(APPEND BASE_SRCS builds/wince/ftdebug.c) +else () + list(APPEND BASE_SRCS src/base/ftdebug.c) +endif () + +if (NOT DISABLE_FORCE_DEBUG_POSTFIX) + set(CMAKE_DEBUG_POSTFIX d) +endif () + +add_library(freetype + ${PUBLIC_HEADERS} + ${PUBLIC_CONFIG_HEADERS} + ${PRIVATE_HEADERS} + ${BASE_SRCS} +) + +set_target_properties(freetype PROPERTIES C_VISIBILITY_PRESET hidden) + +target_compile_definitions(freetype PRIVATE FT2_BUILD_LIBRARY) + +if (WIN32) + target_compile_definitions(freetype PRIVATE _CRT_SECURE_NO_WARNINGS _CRT_NONSTDC_NO_WARNINGS) + if (BUILD_SHARED_LIBS) + target_compile_definitions(freetype PRIVATE DLL_EXPORT) + endif () +endif () + +if (BUILD_SHARED_LIBS) + set_target_properties(freetype PROPERTIES VERSION ${LIBRARY_VERSION} SOVERSION ${LIBRARY_SOVERSION}) +endif () + +# Pick up ftconfig.h and ftoption.h generated above, first. +target_include_directories( + freetype + PUBLIC + $ + $ + $ + PRIVATE + ${CMAKE_CURRENT_BINARY_DIR}/include + ${CMAKE_CURRENT_SOURCE_DIR}/include + + # Make available for builds/unix/ftsystem.c. + ${CMAKE_CURRENT_BINARY_DIR}/include/freetype/config +) + +if (BUILD_SHARED_LIBS) + install(TARGETS freetype + LIBRARY DESTINATION "${LIB_TARGET}/lib" + ARCHIVE DESTINATION "${LIB_TARGET}/lib" + RUNTIME DESTINATION "${LIB_TARGET}/lib") +endif () diff --git a/3rdparty/freetype-2.13.2/LICENSE.TXT b/3rdparty/freetype-2.13.2/LICENSE.TXT new file mode 100644 index 000000000..8b9ce9e2e --- /dev/null +++ b/3rdparty/freetype-2.13.2/LICENSE.TXT @@ -0,0 +1,46 @@ +FREETYPE LICENSES +----------------- + +The FreeType 2 font engine is copyrighted work and cannot be used +legally without a software license. In order to make this project +usable to a vast majority of developers, we distribute it under two +mutually exclusive open-source licenses. + +This means that *you* must choose *one* of the two licenses described +below, then obey all its terms and conditions when using FreeType 2 in +any of your projects or products. + + - The FreeType License, found in the file `docs/FTL.TXT`, which is + similar to the original BSD license *with* an advertising clause + that forces you to explicitly cite the FreeType project in your + product's documentation. All details are in the license file. + This license is suited to products which don't use the GNU General + Public License. + + Note that this license is compatible to the GNU General Public + License version 3, but not version 2. + + - The GNU General Public License version 2, found in + `docs/GPLv2.TXT` (any later version can be used also), for + programs which already use the GPL. Note that the FTL is + incompatible with GPLv2 due to its advertisement clause. + +The contributed BDF and PCF drivers come with a license similar to +that of the X Window System. It is compatible to the above two +licenses (see files `src/bdf/README` and `src/pcf/README`). The same +holds for the source code files `src/base/fthash.c` and +`include/freetype/internal/fthash.h`; they were part of the BDF driver +in earlier FreeType versions. + +The gzip module uses the zlib license (see `src/gzip/zlib.h`) which +too is compatible to the above two licenses. + +The files `src/autofit/ft-hb.c` and `src/autofit/ft-hb.h` contain code +taken almost verbatim from the HarfBuzz file `hb-ft.cc`, which uses +the 'Old MIT' license, compatible to the above two licenses. + +The MD5 checksum support (only used for debugging in development +builds) is in the public domain. + + +--- end of LICENSE.TXT --- diff --git a/3rdparty/freetype-2.13.2/builds/cmake/FindBrotliDec.cmake b/3rdparty/freetype-2.13.2/builds/cmake/FindBrotliDec.cmake new file mode 100644 index 000000000..81036cb10 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/cmake/FindBrotliDec.cmake @@ -0,0 +1,52 @@ +# FindBrotliDec.cmake +# +# Copyright (C) 2019-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# Written by Werner Lemberg +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. +# +# +# Try to find libbrotlidec include and library directories. +# +# If found, the following variables are set. +# +# BROTLIDEC_INCLUDE_DIRS +# BROTLIDEC_LIBRARIES + +find_package(PkgConfig QUIET) + +pkg_check_modules(PC_BROTLIDEC QUIET libbrotlidec) + +if (PC_BROTLIDEC_VERSION) + set(BROTLIDEC_VERSION "${PC_BROTLIDEC_VERSION}") +endif () + + +find_path(BROTLIDEC_INCLUDE_DIRS + NAMES brotli/decode.h + HINTS ${PC_BROTLIDEC_INCLUDEDIR} + ${PC_BROTLIDEC_INCLUDE_DIRS} + PATH_SUFFIXES brotli) + +find_library(BROTLIDEC_LIBRARIES + NAMES brotlidec + HINTS ${PC_BROTLIDEC_LIBDIR} + ${PC_BROTLIDEC_LIBRARY_DIRS}) + + +include(FindPackageHandleStandardArgs) +find_package_handle_standard_args( + BrotliDec + REQUIRED_VARS BROTLIDEC_INCLUDE_DIRS BROTLIDEC_LIBRARIES + FOUND_VAR BROTLIDEC_FOUND + VERSION_VAR BROTLIDEC_VERSION) + +mark_as_advanced( + BROTLIDEC_INCLUDE_DIRS + BROTLIDEC_LIBRARIES) diff --git a/3rdparty/freetype-2.13.2/builds/cmake/FindHarfBuzz.cmake b/3rdparty/freetype-2.13.2/builds/cmake/FindHarfBuzz.cmake new file mode 100644 index 000000000..b481fa415 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/cmake/FindHarfBuzz.cmake @@ -0,0 +1,203 @@ +# Copyright (c) 2012, Intel Corporation +# Copyright (c) 2019 Sony Interactive Entertainment Inc. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions are met: +# +# * Redistributions of source code must retain the above copyright notice, this +# list of conditions and the following disclaimer. +# * Redistributions in binary form must reproduce the above copyright notice, +# this list of conditions and the following disclaimer in the documentation +# and/or other materials provided with the distribution. +# * Neither the name of Intel Corporation nor the names of its contributors may +# be used to endorse or promote products derived from this software without +# specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +# AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE +# LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR +# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF +# SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS +# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN +# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) +# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE +# POSSIBILITY OF SUCH DAMAGE. +# +# Try to find Harfbuzz include and library directories. +# +# After successful discovery, this will set for inclusion where needed: +# HarfBuzz_INCLUDE_DIRS - containg the HarfBuzz headers +# HarfBuzz_LIBRARIES - containg the HarfBuzz library + +#[=======================================================================[.rst: +FindHarfBuzz +-------------- + +Find HarfBuzz headers and libraries. + +Imported Targets +^^^^^^^^^^^^^^^^ + +``HarfBuzz::HarfBuzz`` + The HarfBuzz library, if found. + +``HarfBuzz::ICU`` + The HarfBuzz ICU library, if found. + +Result Variables +^^^^^^^^^^^^^^^^ + +This will define the following variables in your project: + +``HarfBuzz_FOUND`` + true if (the requested version of) HarfBuzz is available. +``HarfBuzz_VERSION`` + the version of HarfBuzz. +``HarfBuzz_LIBRARIES`` + the libraries to link against to use HarfBuzz. +``HarfBuzz_INCLUDE_DIRS`` + where to find the HarfBuzz headers. +``HarfBuzz_COMPILE_OPTIONS`` + this should be passed to target_compile_options(), if the + target is not used for linking + +#]=======================================================================] + +find_package(PkgConfig QUIET) +pkg_check_modules(PC_HARFBUZZ QUIET harfbuzz) +set(HarfBuzz_COMPILE_OPTIONS ${PC_HARFBUZZ_CFLAGS_OTHER}) +set(HarfBuzz_VERSION ${PC_HARFBUZZ_CFLAGS_VERSION}) + +find_path(HarfBuzz_INCLUDE_DIR + NAMES hb.h + HINTS ${PC_HARFBUZZ_INCLUDEDIR} ${PC_HARFBUZZ_INCLUDE_DIRS} + PATH_SUFFIXES harfbuzz +) + +find_library(HarfBuzz_LIBRARY + NAMES ${HarfBuzz_NAMES} harfbuzz + HINTS ${PC_HARFBUZZ_LIBDIR} ${PC_HARFBUZZ_LIBRARY_DIRS} +) + +if (HarfBuzz_INCLUDE_DIR AND NOT HarfBuzz_VERSION) + if (EXISTS "${HarfBuzz_INCLUDE_DIR}/hb-version.h") + file(READ "${HarfBuzz_INCLUDE_DIR}/hb-version.h" _harfbuzz_version_content) + + string(REGEX MATCH "#define +HB_VERSION_STRING +\"([0-9]+\\.[0-9]+\\.[0-9]+)\"" _dummy "${_harfbuzz_version_content}") + set(HarfBuzz_VERSION "${CMAKE_MATCH_1}") + endif () +endif () + +if ("${HarfBuzz_FIND_VERSION}" VERSION_GREATER "${HarfBuzz_VERSION}") + if (HarfBuzz_FIND_REQUIRED) + message(FATAL_ERROR + "Required version (" ${HarfBuzz_FIND_VERSION} ")" + " is higher than found version (" ${HarfBuzz_VERSION} ")") + else () + message(WARNING + "Required version (" ${HarfBuzz_FIND_VERSION} ")" + " is higher than found version (" ${HarfBuzz_VERSION} ")") + unset(HarfBuzz_VERSION) + unset(HarfBuzz_INCLUDE_DIRS) + unset(HarfBuzz_LIBRARIES) + return () + endif () +endif () + +# Find components +if (HarfBuzz_INCLUDE_DIR AND HarfBuzz_LIBRARY) + set(_HarfBuzz_REQUIRED_LIBS_FOUND ON) + set(HarfBuzz_LIBS_FOUND "HarfBuzz (required): ${HarfBuzz_LIBRARY}") +else () + set(_HarfBuzz_REQUIRED_LIBS_FOUND OFF) + set(HarfBuzz_LIBS_NOT_FOUND "HarfBuzz (required)") +endif () + +if (NOT CMAKE_VERSION VERSION_LESS 3.3) + if ("ICU" IN_LIST HarfBuzz_FIND_COMPONENTS) + pkg_check_modules(PC_HARFBUZZ_ICU QUIET harfbuzz-icu) + set(HarfBuzz_ICU_COMPILE_OPTIONS ${PC_HARFBUZZ_ICU_CFLAGS_OTHER}) + + find_path(HarfBuzz_ICU_INCLUDE_DIR + NAMES hb-icu.h + HINTS ${PC_HARFBUZZ_ICU_INCLUDEDIR} ${PC_HARFBUZZ_ICU_INCLUDE_DIRS} + PATH_SUFFIXES harfbuzz + ) + + find_library(HarfBuzz_ICU_LIBRARY + NAMES ${HarfBuzz_ICU_NAMES} harfbuzz-icu + HINTS ${PC_HARFBUZZ_ICU_LIBDIR} ${PC_HARFBUZZ_ICU_LIBRARY_DIRS} + ) + + if (HarfBuzz_ICU_LIBRARY) + if (HarfBuzz_FIND_REQUIRED_ICU) + list(APPEND HarfBuzz_LIBS_FOUND "ICU (required): ${HarfBuzz_ICU_LIBRARY}") + else () + list(APPEND HarfBuzz_LIBS_FOUND "ICU (optional): ${HarfBuzz_ICU_LIBRARY}") + endif () + else () + if (HarfBuzz_FIND_REQUIRED_ICU) + set(_HarfBuzz_REQUIRED_LIBS_FOUND OFF) + list(APPEND HarfBuzz_LIBS_NOT_FOUND "ICU (required)") + else () + list(APPEND HarfBuzz_LIBS_NOT_FOUND "ICU (optional)") + endif () + endif () + endif () +endif () + +if (NOT HarfBuzz_FIND_QUIETLY) + if (HarfBuzz_LIBS_FOUND) + message(STATUS "Found the following HarfBuzz libraries:") + foreach (found ${HarfBuzz_LIBS_FOUND}) + message(STATUS " ${found}") + endforeach () + endif () + if (HarfBuzz_LIBS_NOT_FOUND) + message(STATUS "The following HarfBuzz libraries were not found:") + foreach (found ${HarfBuzz_LIBS_NOT_FOUND}) + message(STATUS " ${found}") + endforeach () + endif () +endif () + +include(FindPackageHandleStandardArgs) +find_package_handle_standard_args(HarfBuzz + FOUND_VAR HarfBuzz_FOUND + REQUIRED_VARS HarfBuzz_INCLUDE_DIR HarfBuzz_LIBRARY _HarfBuzz_REQUIRED_LIBS_FOUND + VERSION_VAR HarfBuzz_VERSION +) + +if (NOT CMAKE_VERSION VERSION_LESS 3.1) + if (HarfBuzz_LIBRARY AND NOT TARGET HarfBuzz::HarfBuzz) + add_library(HarfBuzz::HarfBuzz UNKNOWN IMPORTED GLOBAL) + set_target_properties(HarfBuzz::HarfBuzz PROPERTIES + IMPORTED_LOCATION "${HarfBuzz_LIBRARY}" + INTERFACE_COMPILE_OPTIONS "${HarfBuzz_COMPILE_OPTIONS}" + INTERFACE_INCLUDE_DIRECTORIES "${HarfBuzz_INCLUDE_DIR}" + ) + endif () + + if (HarfBuzz_ICU_LIBRARY AND NOT TARGET HarfBuzz::ICU) + add_library(HarfBuzz::ICU UNKNOWN IMPORTED GLOBAL) + set_target_properties(HarfBuzz::ICU PROPERTIES + IMPORTED_LOCATION "${HarfBuzz_ICU_LIBRARY}" + INTERFACE_COMPILE_OPTIONS "${HarfBuzz_ICU_COMPILE_OPTIONS}" + INTERFACE_INCLUDE_DIRECTORIES "${HarfBuzz_ICU_INCLUDE_DIR}" + ) + endif () +endif () + +mark_as_advanced( + HarfBuzz_INCLUDE_DIR + HarfBuzz_ICU_INCLUDE_DIR + HarfBuzz_LIBRARY + HarfBuzz_ICU_LIBRARY +) + +if (HarfBuzz_FOUND) + set(HarfBuzz_LIBRARIES ${HarfBuzz_LIBRARY} ${HarfBuzz_ICU_LIBRARY}) + set(HarfBuzz_INCLUDE_DIRS ${HarfBuzz_INCLUDE_DIR} ${HarfBuzz_ICU_INCLUDE_DIR}) +endif () diff --git a/3rdparty/freetype-2.13.2/builds/cmake/iOS.cmake b/3rdparty/freetype-2.13.2/builds/cmake/iOS.cmake new file mode 100644 index 000000000..7aba7c523 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/cmake/iOS.cmake @@ -0,0 +1,270 @@ +# iOS.cmake +# +# Copyright (C) 2014-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# Written by David Wimsey +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. +# +# +# This file is derived from the files `Platform/Darwin.cmake' and +# `Platform/UnixPaths.cmake', which are part of CMake 2.8.4. It has been +# altered for iOS development. + + +# Options +# ------- +# +# IOS_PLATFORM = OS | SIMULATOR +# +# This decides whether SDKS are selected from the `iPhoneOS.platform' or +# `iPhoneSimulator.platform' folders. +# +# OS - the default, used to build for iPhone and iPad physical devices, +# which have an ARM architecture. +# SIMULATOR - used to build for the Simulator platforms, which have an +# x86 architecture. +# +# CMAKE_IOS_DEVELOPER_ROOT = /path/to/platform/Developer folder +# +# By default, this location is automatically chosen based on the +# IOS_PLATFORM value above. If you manually set this variable, it +# overrides the default location and forces the use of a particular +# Developer Platform. +# +# CMAKE_IOS_SDK_ROOT = /path/to/platform/Developer/SDKs/SDK folder +# +# By default, this location is automatically chosen based on the +# CMAKE_IOS_DEVELOPER_ROOT value. In this case it is always the most +# up-to-date SDK found in the CMAKE_IOS_DEVELOPER_ROOT path. If you +# manually set this variable, it forces the use of a specific SDK +# version. +# +# +# Macros +# ------ +# +# set_xcode_property (TARGET XCODE_PROPERTY XCODE_VALUE) +# +# A convenience macro for setting Xcode specific properties on targets. +# +# Example: +# +# set_xcode_property(myioslib IPHONEOS_DEPLOYMENT_TARGET "3.1") +# +# find_host_package (PROGRAM ARGS) +# +# A macro to find executable programs on the host system, not within the +# iOS environment. Thanks to the `android-cmake' project for providing +# the command. + + +# standard settings +set(CMAKE_SYSTEM_NAME Darwin) +set(CMAKE_SYSTEM_VERSION 1) +set(UNIX True) +set(APPLE True) +set(IOS True) + +# required as of cmake 2.8.10 +set(CMAKE_OSX_DEPLOYMENT_TARGET "" + CACHE STRING "Force unset of the deployment target for iOS" FORCE +) + +# determine the cmake host system version so we know where to find the iOS +# SDKs +find_program(CMAKE_UNAME uname /bin /usr/bin /usr/local/bin) +if (CMAKE_UNAME) + exec_program(uname ARGS -r OUTPUT_VARIABLE CMAKE_HOST_SYSTEM_VERSION) + string(REGEX REPLACE "^([0-9]+)\\.([0-9]+).*$" "\\1" + DARWIN_MAJOR_VERSION "${CMAKE_HOST_SYSTEM_VERSION}") +endif (CMAKE_UNAME) + +# skip the platform compiler checks for cross compiling +set(CMAKE_CXX_COMPILER_WORKS TRUE) +set(CMAKE_C_COMPILER_WORKS TRUE) + +# all iOS/Darwin specific settings - some may be redundant +set(CMAKE_SHARED_LIBRARY_PREFIX "lib") +set(CMAKE_SHARED_LIBRARY_SUFFIX ".dylib") +set(CMAKE_SHARED_MODULE_PREFIX "lib") +set(CMAKE_SHARED_MODULE_SUFFIX ".so") +set(CMAKE_MODULE_EXISTS 1) +set(CMAKE_DL_LIBS "") + +set(CMAKE_C_OSX_COMPATIBILITY_VERSION_FLAG + "-compatibility_version ") +set(CMAKE_C_OSX_CURRENT_VERSION_FLAG + "-current_version ") +set(CMAKE_CXX_OSX_COMPATIBILITY_VERSION_FLAG + "${CMAKE_C_OSX_COMPATIBILITY_VERSION_FLAG}") +set(CMAKE_CXX_OSX_CURRENT_VERSION_FLAG + "${CMAKE_C_OSX_CURRENT_VERSION_FLAG}") + +# hidden visibility is required for cxx on iOS +set(CMAKE_C_FLAGS_INIT "") +set(CMAKE_CXX_FLAGS_INIT + "-headerpad_max_install_names -fvisibility=hidden -fvisibility-inlines-hidden") + +set(CMAKE_C_LINK_FLAGS + "-Wl,-search_paths_first ${CMAKE_C_LINK_FLAGS}") +set(CMAKE_CXX_LINK_FLAGS + "-Wl,-search_paths_first ${CMAKE_CXX_LINK_FLAGS}") + +set(CMAKE_PLATFORM_HAS_INSTALLNAME 1) +set(CMAKE_SHARED_LIBRARY_CREATE_C_FLAGS + "-dynamiclib -headerpad_max_install_names") +set(CMAKE_SHARED_MODULE_CREATE_C_FLAGS + "-bundle -headerpad_max_install_names") +set(CMAKE_SHARED_MODULE_LOADER_C_FLAG + "-Wl,-bundle_loader,") +set(CMAKE_SHARED_MODULE_LOADER_CXX_FLAG + "-Wl,-bundle_loader,") +set(CMAKE_FIND_LIBRARY_SUFFIXES + ".dylib" ".so" ".a") + +# hack: If a new cmake (which uses CMAKE_INSTALL_NAME_TOOL) runs on an old +# build tree (where `install_name_tool' was hardcoded), and where +# CMAKE_INSTALL_NAME_TOOL isn't in the cache and still cmake didn't +# fail in `CMakeFindBinUtils.cmake' (because it isn't rerun), hardcode +# CMAKE_INSTALL_NAME_TOOL here to `install_name_tool' so it behaves as +# it did before. +if (NOT DEFINED CMAKE_INSTALL_NAME_TOOL) + find_program(CMAKE_INSTALL_NAME_TOOL install_name_tool) +endif (NOT DEFINED CMAKE_INSTALL_NAME_TOOL) + +# set up iOS platform unless specified manually with IOS_PLATFORM +if (NOT DEFINED IOS_PLATFORM) + set(IOS_PLATFORM "OS") +endif (NOT DEFINED IOS_PLATFORM) + +set(IOS_PLATFORM ${IOS_PLATFORM} CACHE STRING "Type of iOS Platform") + +# check the platform selection and setup for developer root +if (${IOS_PLATFORM} STREQUAL "OS") + set(IOS_PLATFORM_LOCATION "iPhoneOS.platform") + + # this causes the installers to properly locate the output libraries + set(CMAKE_XCODE_EFFECTIVE_PLATFORMS "-iphoneos") + +elseif (${IOS_PLATFORM} STREQUAL "SIMULATOR") + set(IOS_PLATFORM_LOCATION "iPhoneSimulator.platform") + + # this causes the installers to properly locate the output libraries + set(CMAKE_XCODE_EFFECTIVE_PLATFORMS "-iphonesimulator") + +else (${IOS_PLATFORM} STREQUAL "OS") + message(FATAL_ERROR + "Unsupported IOS_PLATFORM value selected. Please choose OS or SIMULATOR.") + +endif (${IOS_PLATFORM} STREQUAL "OS") + +# set up iOS developer location unless specified manually with +# CMAKE_IOS_DEVELOPER_ROOT -- +# note that Xcode 4.3 changed the installation location; choose the most +# recent one available +set(XCODE_POST_43_ROOT + "/Applications/Xcode.app/Contents/Developer/Platforms/${IOS_PLATFORM_LOCATION}/Developer") +set(XCODE_PRE_43_ROOT + "/Developer/Platforms/${IOS_PLATFORM_LOCATION}/Developer") + +if (NOT DEFINED CMAKE_IOS_DEVELOPER_ROOT) + if (EXISTS ${XCODE_POST_43_ROOT}) + set(CMAKE_IOS_DEVELOPER_ROOT ${XCODE_POST_43_ROOT}) + elseif (EXISTS ${XCODE_PRE_43_ROOT}) + set(CMAKE_IOS_DEVELOPER_ROOT ${XCODE_PRE_43_ROOT}) + endif (EXISTS ${XCODE_POST_43_ROOT}) +endif (NOT DEFINED CMAKE_IOS_DEVELOPER_ROOT) + +set(CMAKE_IOS_DEVELOPER_ROOT ${CMAKE_IOS_DEVELOPER_ROOT} + CACHE PATH "Location of iOS Platform" +) + +# find and use the most recent iOS SDK unless specified manually with +# CMAKE_IOS_SDK_ROOT +if (NOT DEFINED CMAKE_IOS_SDK_ROOT) + file(GLOB _CMAKE_IOS_SDKS "${CMAKE_IOS_DEVELOPER_ROOT}/SDKs/*") + if (_CMAKE_IOS_SDKS) + list(SORT _CMAKE_IOS_SDKS) + list(REVERSE _CMAKE_IOS_SDKS) + list(GET _CMAKE_IOS_SDKS 0 CMAKE_IOS_SDK_ROOT) + else (_CMAKE_IOS_SDKS) + message(FATAL_ERROR + "No iOS SDK's found in default search path ${CMAKE_IOS_DEVELOPER_ROOT}. Manually set CMAKE_IOS_SDK_ROOT or install the iOS SDK.") + endif (_CMAKE_IOS_SDKS) + + message(STATUS "Toolchain using default iOS SDK: ${CMAKE_IOS_SDK_ROOT}") +endif (NOT DEFINED CMAKE_IOS_SDK_ROOT) + +set(CMAKE_IOS_SDK_ROOT ${CMAKE_IOS_SDK_ROOT} + CACHE PATH "Location of the selected iOS SDK" +) + +# set the sysroot default to the most recent SDK +set(CMAKE_OSX_SYSROOT ${CMAKE_IOS_SDK_ROOT} + CACHE PATH "Sysroot used for iOS support" +) + +# set the architecture for iOS -- +# note that currently both ARCHS_STANDARD_32_BIT and +# ARCHS_UNIVERSAL_IPHONE_OS set armv7 only, so set both manually +if (${IOS_PLATFORM} STREQUAL "OS") + set(IOS_ARCH $(ARCHS_STANDARD_32_64_BIT)) +else (${IOS_PLATFORM} STREQUAL "OS") + set(IOS_ARCH i386) +endif (${IOS_PLATFORM} STREQUAL "OS") + +set(CMAKE_OSX_ARCHITECTURES ${IOS_ARCH} + CACHE string "Build architecture for iOS" +) + +# set the find root to the iOS developer roots and to user defined paths +set(CMAKE_FIND_ROOT_PATH + ${CMAKE_IOS_DEVELOPER_ROOT} + ${CMAKE_IOS_SDK_ROOT} + ${CMAKE_PREFIX_PATH} + CACHE string "iOS find search path root" +) + +# default to searching for frameworks first +set(CMAKE_FIND_FRAMEWORK FIRST) + +# set up the default search directories for frameworks +set(CMAKE_SYSTEM_FRAMEWORK_PATH + ${CMAKE_IOS_SDK_ROOT}/System/Library/Frameworks + ${CMAKE_IOS_SDK_ROOT}/System/Library/PrivateFrameworks + ${CMAKE_IOS_SDK_ROOT}/Developer/Library/Frameworks +) + +# only search the iOS SDKs, not the remainder of the host filesystem +set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM ONLY) +set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY) +set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY) + +# this little macro lets you set any Xcode specific property +macro(set_xcode_property TARGET XCODE_PROPERTY XCODE_VALUE) + set_property(TARGET ${TARGET} + PROPERTY XCODE_ATTRIBUTE_${XCODE_PROPERTY} ${XCODE_VALUE}) +endmacro(set_xcode_property) + +# this macro lets you find executable programs on the host system +macro(find_host_package) + set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER) + set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY NEVER) + set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE NEVER) + set(IOS FALSE) + + find_package(${ARGN}) + + set(IOS TRUE) + set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM ONLY) + set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY) + set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY) +endmacro(find_host_package) + +# eof diff --git a/3rdparty/freetype-2.13.2/builds/cmake/testbuild.sh b/3rdparty/freetype-2.13.2/builds/cmake/testbuild.sh new file mode 100644 index 000000000..007170b04 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/cmake/testbuild.sh @@ -0,0 +1,157 @@ +#!/bin/sh -e + +# Copyright (C) 2015-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + +# This script tests the CMake build. Simply run +# +# builds/cmake/testbuild.sh +# +# or +# +# BUILD_SHARED_LIBS=1 builds/cmake/testbuild.sh +# +# The script: +# +# - builds the main CMakeLists.txt +# - builds and runs a small test app in a separate build tree so +# the config-module is tested, too +# +# Options (environment variables): +# +# - The variable BUILD_SHARED_LIBS will be forwarded to the CMake project +# that builds the library. +# + + +# prepare temporary dir + +cd `dirname $0`/../.. +ftdir=`pwd` +tmpdir=/tmp/freetype-cmake-testbuild +rm -rf $tmpdir +mkdir -p $tmpdir + + +# build and install freetype + +if test -n "$BUILD_SHARED_LIBS"; then + bsl=-DBUILD_SHARED_LIBS=$BUILD_SHARED_LIBS +else + bsl=-UBUILD_SHARED_LIBS +fi + +build_opts="-DWITH_ZLIB=0 \ + -DWITH_BZip2=0 \ + -DWITH_PNG=0 \ + -DWITH_HarfBuzz=0 \ + $bsl \ + -DCMAKE_INSTALL_PREFIX=$tmpdir/out" + +(set -x; cmake -H$ftdir \ + -B$tmpdir/ftb \ + -DCMAKE_BUILD_TYPE=Debug \ + $build_opts) +(set -x; cmake --build $tmpdir/ftb \ + --config Debug \ + --target install) + +(set -x; cmake $tmpdir/ftb \ + -DCMAKE_BUILD_TYPE=Release) +(set -x; cmake --build $tmpdir/ftb \ + --config Release \ + --target install \ + --clean-first) + + +# create test project CMakeLists.txt + +cat >$tmpdir/CMakeLists.txt << END +cmake_minimum_required(VERSION 2.6) +project(freetype-cmake-testbuild) + +find_package(Freetype REQUIRED CONFIG) + +add_executable(freetype-cmake-test main.c) +target_link_libraries(freetype-cmake-test freetype) + +enable_testing() +add_test(freetype-cmake-test freetype-cmake-test) +END + + +# create test project main.c + +cat >$tmpdir/main.c << END +#include +#include + +#include +#include + + +FT_Library library; + + +int main(int argc, + char*argv[]) +{ + FT_Error error; + FT_Int major = 0; + FT_Int minor = 0; + FT_Int patch = 0; + + error = FT_Init_FreeType(&library); + if (error) + return EXIT_FAILURE; + + FT_Library_Version(library, &major, &minor, &patch); + if (major != FREETYPE_MAJOR + || minor != FREETYPE_MINOR + || patch != FREETYPE_PATCH) + return EXIT_FAILURE; + + printf("FT_Library_Version: %d.%d.%d\n", major, minor, patch); + + error = FT_Done_FreeType(library); + if (error) + return EXIT_FAILURE; + + return EXIT_SUCCESS; +} +END + + +# build and test + +mkdir -p $tmpdir/tb +cd $tmpdir/tb + +LD_LIBRARY_PATH=$tmpdir/out/lib:$LD_LIBRARY_PATH +DYLD_LIBRARY_PATH=$tmpdir/out/lib:$DYLD_LIBRARY_PATH +export LD_LIBRARY_PATH +export DYLD_LIBRARY_PATH + +(set -x; cmake $tmpdir \ + -DCMAKE_BUILD_TYPE=Debug \ + -DCMAKE_PREFIX_PATH=$tmpdir/out) +(set -x; cmake --build . \ + --config Debug) +(set -x; ctest -V -C Debug) + +(set -x; cmake . \ + -DCMAKE_BUILD_TYPE=Release) +(set -x; cmake --build . \ + --config Release \ + --clean-first) +(set -x; ctest -V -C Release) + +rm -rf $tmpdir + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/mac/FreeType.m68k_cfm.make.txt b/3rdparty/freetype-2.13.2/builds/mac/FreeType.m68k_cfm.make.txt new file mode 100644 index 000000000..b74565f10 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/mac/FreeType.m68k_cfm.make.txt @@ -0,0 +1,209 @@ +# File: FreeType.m68k_cfm.make +# Target: FreeType.m68k_cfm +# Created: Thursday, October 27, 2005 09:23:25 PM + + +MAKEFILE = FreeType.m68k_cfm.make +\xA5MondoBuild\xA5 = {MAKEFILE} # Make blank to avoid rebuilds when makefile is modified + +ObjDir = :objs: +Includes = \xB6 + -ansi strict \xB6 + -includes unix \xB6 + -i :include: \xB6 + -i :src: \xB6 + -i :include:freetype:config: + +Sym-68K = -sym off + +COptions = \xB6 + -d FT_MACINTOSH=1 \xB6 + -d HAVE_FSSPEC=1 \xB6 + -d HAVE_FSREF=0 \xB6 + -d HAVE_QUICKDRAW_TOOLBOX=1 \xB6 + -d HAVE_QUICKDRAW_CARBON=0 \xB6 + -d HAVE_ATS=0 \xB6 + -d FT2_BUILD_LIBRARY \xB6 + -d FT_CONFIG_CONFIG_H="" \xB6 + -d FT_CONFIG_MODULES_H="" \xB6 + {Includes} {Sym-68K} -model cfmseg + + +### Source Files ### + +SrcFiles = \xB6 + :src:autofit:autofit.c \xB6 + :builds:mac:ftbase.c \xB6 + :src:base:ftbbox.c \xB6 + :src:base:ftbdf.c \xB6 + :src:base:ftbitmap.c \xB6 + :src:base:ftdebug.c \xB6 + :src:base:ftfstype.c \xB6 + :src:base:ftglyph.c \xB6 + :src:base:ftgxval.c \xB6 + :src:base:ftinit.c \xB6 + :src:base:ftmm.c \xB6 + :src:base:ftotval.c \xB6 + :src:base:ftpfr.c \xB6 + :src:base:ftstroke.c \xB6 + :src:base:ftsynth.c \xB6 + :src:base:ftsystem.c \xB6 + :src:base:fttype1.c \xB6 + :src:base:ftwinfnt.c \xB6 + :src:cache:ftcache.c \xB6 + :src:bdf:bdf.c \xB6 + :src:cff:cff.c \xB6 + :src:cid:type1cid.c \xB6 +# :src:gxvalid:gxvalid.c \xB6 + :src:gzip:ftgzip.c \xB6 + :src:bzip2:ftbzip2.c \xB6 + :src:lzw:ftlzw.c \xB6 + :src:otvalid:otvalid.c \xB6 + :src:pcf:pcf.c \xB6 + :src:pfr:pfr.c \xB6 + :src:psaux:psaux.c \xB6 + :src:pshinter:pshinter.c \xB6 + :src:psnames:psmodule.c \xB6 + :src:raster:raster.c \xB6 + :src:sfnt:sfnt.c \xB6 + :src:smooth:smooth.c \xB6 + :src:truetype:truetype.c \xB6 + :src:type1:type1.c \xB6 + :src:type42:type42.c \xB6 + :src:winfonts:winfnt.c + + +### Object Files ### + +ObjFiles-68K = \xB6 + "{ObjDir}autofit.c.o" \xB6 + "{ObjDir}ftbase.c.o" \xB6 + "{ObjDir}ftbbox.c.o" \xB6 + "{ObjDir}ftbdf.c.o" \xB6 + "{ObjDir}ftbitmap.c.o" \xB6 + "{ObjDir}ftdebug.c.o" \xB6 + "{ObjDir}ftfstype.c.o" \xB6 + "{ObjDir}ftglyph.c.o" \xB6 + "{ObjDir}ftgxval.c.o" \xB6 + "{ObjDir}ftinit.c.o" \xB6 + "{ObjDir}ftmm.c.o" \xB6 + "{ObjDir}ftotval.c.o" \xB6 + "{ObjDir}ftpfr.c.o" \xB6 + "{ObjDir}ftstroke.c.o" \xB6 + "{ObjDir}ftsynth.c.o" \xB6 + "{ObjDir}ftsystem.c.o" \xB6 + "{ObjDir}fttype1.c.o" \xB6 + "{ObjDir}ftwinfnt.c.o" \xB6 + "{ObjDir}ftcache.c.o" \xB6 + "{ObjDir}bdf.c.o" \xB6 + "{ObjDir}cff.c.o" \xB6 + "{ObjDir}type1cid.c.o" \xB6 +# "{ObjDir}gxvalid.c.o" \xB6 + "{ObjDir}ftgzip.c.o" \xB6 + "{ObjDir}ftbzip2.c.o" \xB6 + "{ObjDir}ftlzw.c.o" \xB6 + "{ObjDir}otvalid.c.o" \xB6 + "{ObjDir}pcf.c.o" \xB6 + "{ObjDir}pfr.c.o" \xB6 + "{ObjDir}psaux.c.o" \xB6 + "{ObjDir}pshinter.c.o" \xB6 + "{ObjDir}psmodule.c.o" \xB6 + "{ObjDir}raster.c.o" \xB6 + "{ObjDir}sfnt.c.o" \xB6 + "{ObjDir}smooth.c.o" \xB6 + "{ObjDir}truetype.c.o" \xB6 + "{ObjDir}type1.c.o" \xB6 + "{ObjDir}type42.c.o" \xB6 + "{ObjDir}winfnt.c.o" + + +### Libraries ### + +LibFiles-68K = + + +### Default Rules ### + +.c.o \xC4 .c {\xA5MondoBuild\xA5} + {C} {depDir}{default}.c -o {targDir}{default}.c.o {COptions} + + +### Build Rules ### + +:builds:mac:ftbase.c \xC4\xC4 :src:base:ftbase.c + Duplicate :src:base:ftbase.c :builds:mac:ftbase.c + +"{ObjDir}ftbase.c.o" \xC4\xC4 :builds:mac:ftbase.c + {C} :builds:mac:ftbase.c -o "{ObjDir}ftbase.c.o" \xB6 + -i :builds:mac: \xB6 + -i :src:base: \xB6 + {COptions} + +FreeType.m68k_cfm \xC4\xC4 FreeType.m68k_cfm.o + +FreeType.m68k_cfm.o \xC4\xC4 {ObjFiles-68K} {LibFiles-68K} {\xA5MondoBuild\xA5} + Lib \xB6 + -o {Targ} \xB6 + {ObjFiles-68K} \xB6 + {LibFiles-68K} \xB6 + {Sym-68K} \xB6 + -mf -d + + + +### Required Dependencies ### + +"{ObjDir}autofit.c.o" \xC4 :src:autofit:autofit.c +# "{ObjDir}ftbase.c.o" \xC4 :src:base:ftbase.c +"{ObjDir}ftbbox.c.o" \xC4 :src:base:ftbbox.c +"{ObjDir}ftbdf.c.o" \xC4 :src:base:ftbdf.c +"{ObjDir}ftbitmap.c.o" \xC4 :src:base:ftbitmap.c +"{ObjDir}ftdebug.c.o" \xC4 :src:base:ftdebug.c +"{ObjDir}ftfstype.c.o" \xC4 :src:base:ftfstype.c +"{ObjDir}ftglyph.c.o" \xC4 :src:base:ftglyph.c +"{ObjDir}ftgxval.c.o" \xC4 :src:base:ftgxval.c +"{ObjDir}ftinit.c.o" \xC4 :src:base:ftinit.c +"{ObjDir}ftmm.c.o" \xC4 :src:base:ftmm.c +"{ObjDir}ftotval.c.o" \xC4 :src:base:ftotval.c +"{ObjDir}ftpfr.c.o" \xC4 :src:base:ftpfr.c +"{ObjDir}ftstroke.c.o" \xC4 :src:base:ftstroke.c +"{ObjDir}ftsynth.c.o" \xC4 :src:base:ftsynth.c +"{ObjDir}ftsystem.c.o" \xC4 :src:base:ftsystem.c +"{ObjDir}fttype1.c.o" \xC4 :src:base:fttype1.c +"{ObjDir}ftwinfnt.c.o" \xC4 :src:base:ftwinfnt.c +"{ObjDir}ftcache.c.o" \xC4 :src:cache:ftcache.c +"{ObjDir}bdf.c.o" \xC4 :src:bdf:bdf.c +"{ObjDir}cff.c.o" \xC4 :src:cff:cff.c +"{ObjDir}type1cid.c.o" \xC4 :src:cid:type1cid.c +# "{ObjDir}gxvalid.c.o" \xC4 :src:gxvalid:gxvalid.c +"{ObjDir}ftgzip.c.o" \xC4 :src:gzip:ftgzip.c +"{ObjDir}ftbzip2.c.o" \xC4 :src:bzip2:ftbzip2.c +"{ObjDir}ftlzw.c.o" \xC4 :src:lzw:ftlzw.c +"{ObjDir}otvalid.c.o" \xC4 :src:otvalid:otvalid.c +"{ObjDir}pcf.c.o" \xC4 :src:pcf:pcf.c +"{ObjDir}pfr.c.o" \xC4 :src:pfr:pfr.c +"{ObjDir}psaux.c.o" \xC4 :src:psaux:psaux.c +"{ObjDir}pshinter.c.o" \xC4 :src:pshinter:pshinter.c +"{ObjDir}psmodule.c.o" \xC4 :src:psnames:psmodule.c +"{ObjDir}raster.c.o" \xC4 :src:raster:raster.c +"{ObjDir}sfnt.c.o" \xC4 :src:sfnt:sfnt.c +"{ObjDir}smooth.c.o" \xC4 :src:smooth:smooth.c +"{ObjDir}truetype.c.o" \xC4 :src:truetype:truetype.c +"{ObjDir}type1.c.o" \xC4 :src:type1:type1.c +"{ObjDir}type42.c.o" \xC4 :src:type42:type42.c +"{ObjDir}winfnt.c.o" \xC4 :src:winfonts:winfnt.c + + +### Optional Dependencies ### +### Build this target to generate "include file" dependencies. ### + +Dependencies \xC4 $OutOfDate + MakeDepend \xB6 + -append {MAKEFILE} \xB6 + -ignore "{CIncludes}" \xB6 + -objdir "{ObjDir}" \xB6 + -objext .o \xB6 + {Includes} \xB6 + {SrcFiles} + + diff --git a/3rdparty/freetype-2.13.2/builds/mac/FreeType.m68k_far.make.txt b/3rdparty/freetype-2.13.2/builds/mac/FreeType.m68k_far.make.txt new file mode 100644 index 000000000..d880ddbb7 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/mac/FreeType.m68k_far.make.txt @@ -0,0 +1,208 @@ +# File: FreeType.m68k_far.make +# Target: FreeType.m68k_far +# Created: Tuesday, October 25, 2005 03:34:05 PM + + +MAKEFILE = FreeType.m68k_far.make +\xA5MondoBuild\xA5 = {MAKEFILE} # Make blank to avoid rebuilds when makefile is modified + +ObjDir = :objs: +Includes = \xB6 + -includes unix \xB6 + -i :include: \xB6 + -i :src: \xB6 + -i :include:freetype:config: + +Sym-68K = -sym off + +COptions = \xB6 + -d FT_MACINTOSH=1 \xB6 + -d HAVE_FSSPEC=1 \xB6 + -d HAVE_FSREF=0 \xB6 + -d HAVE_QUICKDRAW_TOOLBOX=1 \xB6 + -d HAVE_QUICKDRAW_CARBON=0 \xB6 + -d HAVE_ATS=0 \xB6 + -d FT2_BUILD_LIBRARY \xB6 + -d FT_CONFIG_CONFIG_H="" \xB6 + -d FT_CONFIG_MODULES_H="" \xB6 + {Includes} {Sym-68K} -model far + + +### Source Files ### + +SrcFiles = \xB6 + :src:autofit:autofit.c \xB6 + :builds:mac:ftbase.c \xB6 + :src:base:ftbbox.c \xB6 + :src:base:ftbdf.c \xB6 + :src:base:ftbitmap.c \xB6 + :src:base:ftdebug.c \xB6 + :src:base:ftfstype.c \xB6 + :src:base:ftglyph.c \xB6 + :src:base:ftgxval.c \xB6 + :src:base:ftinit.c \xB6 + :src:base:ftmm.c \xB6 + :src:base:ftotval.c \xB6 + :src:base:ftpfr.c \xB6 + :src:base:ftstroke.c \xB6 + :src:base:ftsynth.c \xB6 + :src:base:ftsystem.c \xB6 + :src:base:fttype1.c \xB6 + :src:base:ftwinfnt.c \xB6 + :src:cache:ftcache.c \xB6 + :src:bdf:bdf.c \xB6 + :src:cff:cff.c \xB6 + :src:cid:type1cid.c \xB6 + :src:gxvalid:gxvalid.c \xB6 + :src:gzip:ftgzip.c \xB6 + :src:bzip2:ftbzip2.c \xB6 + :src:lzw:ftlzw.c \xB6 + :src:otvalid:otvalid.c \xB6 + :src:pcf:pcf.c \xB6 + :src:pfr:pfr.c \xB6 + :src:psaux:psaux.c \xB6 + :src:pshinter:pshinter.c \xB6 + :src:psnames:psmodule.c \xB6 + :src:raster:raster.c \xB6 + :src:sfnt:sfnt.c \xB6 + :src:smooth:smooth.c \xB6 + :src:truetype:truetype.c \xB6 + :src:type1:type1.c \xB6 + :src:type42:type42.c \xB6 + :src:winfonts:winfnt.c + + +### Object Files ### + +ObjFiles-68K = \xB6 + "{ObjDir}autofit.c.o" \xB6 + "{ObjDir}ftbase.c.o" \xB6 + "{ObjDir}ftbbox.c.o" \xB6 + "{ObjDir}ftbdf.c.o" \xB6 + "{ObjDir}ftbitmap.c.o" \xB6 + "{ObjDir}ftdebug.c.o" \xB6 + "{ObjDir}ftfstype.c.o" \xB6 + "{ObjDir}ftglyph.c.o" \xB6 + "{ObjDir}ftgxval.c.o" \xB6 + "{ObjDir}ftinit.c.o" \xB6 + "{ObjDir}ftmm.c.o" \xB6 + "{ObjDir}ftotval.c.o" \xB6 + "{ObjDir}ftpfr.c.o" \xB6 + "{ObjDir}ftstroke.c.o" \xB6 + "{ObjDir}ftsynth.c.o" \xB6 + "{ObjDir}ftsystem.c.o" \xB6 + "{ObjDir}fttype1.c.o" \xB6 + "{ObjDir}ftwinfnt.c.o" \xB6 + "{ObjDir}ftcache.c.o" \xB6 + "{ObjDir}bdf.c.o" \xB6 + "{ObjDir}cff.c.o" \xB6 + "{ObjDir}type1cid.c.o" \xB6 + "{ObjDir}gxvalid.c.o" \xB6 + "{ObjDir}ftgzip.c.o" \xB6 + "{ObjDir}ftbzip2.c.o" \xB6 + "{ObjDir}ftlzw.c.o" \xB6 + "{ObjDir}otvalid.c.o" \xB6 + "{ObjDir}pcf.c.o" \xB6 + "{ObjDir}pfr.c.o" \xB6 + "{ObjDir}psaux.c.o" \xB6 + "{ObjDir}pshinter.c.o" \xB6 + "{ObjDir}psmodule.c.o" \xB6 + "{ObjDir}raster.c.o" \xB6 + "{ObjDir}sfnt.c.o" \xB6 + "{ObjDir}smooth.c.o" \xB6 + "{ObjDir}truetype.c.o" \xB6 + "{ObjDir}type1.c.o" \xB6 + "{ObjDir}type42.c.o" \xB6 + "{ObjDir}winfnt.c.o" + + +### Libraries ### + +LibFiles-68K = + + +### Default Rules ### + +.c.o \xC4 .c {\xA5MondoBuild\xA5} + {C} {depDir}{default}.c -o {targDir}{default}.c.o {COptions} \xB6 + -ansi strict + +### Build Rules ### + +:builds:mac:ftbase.c \xC4\xC4 :src:base:ftbase.c + Duplicate :src:base:ftbase.c :builds:mac:ftbase.c + +"{ObjDir}ftbase.c.o" \xC4\xC4 :builds:mac:ftbase.c + {C} :builds:mac:ftbase.c -o "{ObjDir}ftbase.c.o" \xB6 + -i :builds:mac: \xB6 + -i :src:base: \xB6 + {COptions} + +FreeType.m68k_far \xC4\xC4 FreeType.m68k_far.o + +FreeType.m68k_far.o \xC4\xC4 {ObjFiles-68K} {LibFiles-68K} {\xA5MondoBuild\xA5} + Lib \xB6 + -o {Targ} \xB6 + {ObjFiles-68K} \xB6 + {LibFiles-68K} \xB6 + {Sym-68K} \xB6 + -mf -d + + + +### Required Dependencies ### + +"{ObjDir}autofit.c.o" \xC4 :src:autofit:autofit.c +# "{ObjDir}ftbase.c.o" \xC4 :src:base:ftbase.c +"{ObjDir}ftbbox.c.o" \xC4 :src:base:ftbbox.c +"{ObjDir}ftbdf.c.o" \xC4 :src:base:ftbdf.c +"{ObjDir}ftbitmap.c.o" \xC4 :src:base:ftbitmap.c +"{ObjDir}ftdebug.c.o" \xC4 :src:base:ftdebug.c +"{ObjDir}ftfstype.c.o" \xC4 :src:base:ftfstype.c +"{ObjDir}ftglyph.c.o" \xC4 :src:base:ftglyph.c +"{ObjDir}ftgxval.c.o" \xC4 :src:base:ftgxval.c +"{ObjDir}ftinit.c.o" \xC4 :src:base:ftinit.c +"{ObjDir}ftmm.c.o" \xC4 :src:base:ftmm.c +"{ObjDir}ftotval.c.o" \xC4 :src:base:ftotval.c +"{ObjDir}ftpfr.c.o" \xC4 :src:base:ftpfr.c +"{ObjDir}ftstroke.c.o" \xC4 :src:base:ftstroke.c +"{ObjDir}ftsynth.c.o" \xC4 :src:base:ftsynth.c +"{ObjDir}ftsystem.c.o" \xC4 :src:base:ftsystem.c +"{ObjDir}fttype1.c.o" \xC4 :src:base:fttype1.c +"{ObjDir}ftwinfnt.c.o" \xC4 :src:base:ftwinfnt.c +"{ObjDir}ftcache.c.o" \xC4 :src:cache:ftcache.c +"{ObjDir}bdf.c.o" \xC4 :src:bdf:bdf.c +"{ObjDir}cff.c.o" \xC4 :src:cff:cff.c +"{ObjDir}type1cid.c.o" \xC4 :src:cid:type1cid.c +"{ObjDir}gxvalid.c.o" \xC4 :src:gxvalid:gxvalid.c +"{ObjDir}ftgzip.c.o" \xC4 :src:gzip:ftgzip.c +"{ObjDir}ftbzip2.c.o" \xC4 :src:bzip2:ftbzip2.c +"{ObjDir}ftlzw.c.o" \xC4 :src:lzw:ftlzw.c +"{ObjDir}otvalid.c.o" \xC4 :src:otvalid:otvalid.c +"{ObjDir}pcf.c.o" \xC4 :src:pcf:pcf.c +"{ObjDir}pfr.c.o" \xC4 :src:pfr:pfr.c +"{ObjDir}psaux.c.o" \xC4 :src:psaux:psaux.c +"{ObjDir}pshinter.c.o" \xC4 :src:pshinter:pshinter.c +"{ObjDir}psmodule.c.o" \xC4 :src:psnames:psmodule.c +"{ObjDir}raster.c.o" \xC4 :src:raster:raster.c +"{ObjDir}sfnt.c.o" \xC4 :src:sfnt:sfnt.c +"{ObjDir}smooth.c.o" \xC4 :src:smooth:smooth.c +"{ObjDir}truetype.c.o" \xC4 :src:truetype:truetype.c +"{ObjDir}type1.c.o" \xC4 :src:type1:type1.c +"{ObjDir}type42.c.o" \xC4 :src:type42:type42.c +"{ObjDir}winfnt.c.o" \xC4 :src:winfonts:winfnt.c + + +### Optional Dependencies ### +### Build this target to generate "include file" dependencies. ### + +Dependencies \xC4 $OutOfDate + MakeDepend \xB6 + -append {MAKEFILE} \xB6 + -ignore "{CIncludes}" \xB6 + -objdir "{ObjDir}" \xB6 + -objext .o \xB6 + {Includes} \xB6 + {SrcFiles} + + diff --git a/3rdparty/freetype-2.13.2/builds/mac/FreeType.ppc_carbon.make.txt b/3rdparty/freetype-2.13.2/builds/mac/FreeType.ppc_carbon.make.txt new file mode 100644 index 000000000..1fa8c3076 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/mac/FreeType.ppc_carbon.make.txt @@ -0,0 +1,212 @@ +# File: FreeType.ppc_carbon.make +# Target: FreeType.ppc_carbon +# Created: Friday, October 28, 2005 03:40:06 PM + + +MAKEFILE = FreeType.ppc_carbon.make +\xA5MondoBuild\xA5 = {MAKEFILE} # Make blank to avoid rebuilds when makefile is modified + +ObjDir = :objs: +Includes = \xB6 + -ansi strict \xB6 + -includes unix \xB6 + -i :include: \xB6 + -i :src: \xB6 + -i :include:freetype:config: + +Sym-PPC = -sym off + +PPCCOptions = \xB6 + -d FT_MACINTOSH=1 \xB6 + -d HAVE_FSSPEC=1 \xB6 + -d HAVE_FSREF=1 \xB6 + -d HAVE_QUICKDRAW_TOOLBOX=1 \xB6 + -d HAVE_QUICKDRAW_CARBON=1 \xB6 + -d HAVE_ATS=0 \xB6 + -d FT2_BUILD_LIBRARY \xB6 + -d FT_CONFIG_CONFIG_H="" \xB6 + -d FT_CONFIG_MODULES_H="" \xB6 + {Includes} {Sym-PPC} -d TARGET_API_MAC_CARBON=1 + + +### Source Files ### + +SrcFiles = \xB6 + :src:autofit:autofit.c \xB6 + :builds:mac:ftbase.c \xB6 + :src:base:ftbbox.c \xB6 + :src:base:ftbdf.c \xB6 + :src:base:ftbitmap.c \xB6 + :src:base:ftdebug.c \xB6 + :src:base:ftfstype.c \xB6 + :src:base:ftglyph.c \xB6 + :src:base:ftgxval.c \xB6 + :src:base:ftinit.c \xB6 + :src:base:ftmm.c \xB6 + :src:base:ftotval.c \xB6 + :src:base:ftpfr.c \xB6 + :src:base:ftstroke.c \xB6 + :src:base:ftsynth.c \xB6 + :src:base:ftsystem.c \xB6 + :src:base:fttype1.c \xB6 + :src:base:ftwinfnt.c \xB6 + :src:cache:ftcache.c \xB6 + :src:bdf:bdf.c \xB6 + :src:cff:cff.c \xB6 + :src:cid:type1cid.c \xB6 + :src:gxvalid:gxvalid.c \xB6 + :src:gzip:ftgzip.c \xB6 + :src:bzip2:ftbzip2.c \xB6 + :src:lzw:ftlzw.c \xB6 + :src:otvalid:otvalid.c \xB6 + :src:pcf:pcf.c \xB6 + :src:pfr:pfr.c \xB6 + :src:psaux:psaux.c \xB6 + :src:pshinter:pshinter.c \xB6 + :src:psnames:psmodule.c \xB6 + :src:raster:raster.c \xB6 + :src:sfnt:sfnt.c \xB6 + :src:smooth:smooth.c \xB6 + :src:truetype:truetype.c \xB6 + :src:type1:type1.c \xB6 + :src:type42:type42.c \xB6 + :src:winfonts:winfnt.c + + +### Object Files ### + +ObjFiles-PPC = \xB6 + "{ObjDir}autofit.c.x" \xB6 + "{ObjDir}ftbase.c.x" \xB6 + "{ObjDir}ftbbox.c.x" \xB6 + "{ObjDir}ftbdf.c.x" \xB6 + "{ObjDir}ftbitmap.c.x" \xB6 + "{ObjDir}ftdebug.c.x" \xB6 + "{ObjDir}ftfstype.c.x" \xB6 + "{ObjDir}ftglyph.c.x" \xB6 + "{ObjDir}ftgxval.c.x" \xB6 + "{ObjDir}ftinit.c.x" \xB6 + "{ObjDir}ftmm.c.x" \xB6 + "{ObjDir}ftotval.c.x" \xB6 + "{ObjDir}ftpfr.c.x" \xB6 + "{ObjDir}ftstroke.c.x" \xB6 + "{ObjDir}ftsynth.c.x" \xB6 + "{ObjDir}ftsystem.c.x" \xB6 + "{ObjDir}fttype1.c.x" \xB6 + "{ObjDir}ftwinfnt.c.x" \xB6 + "{ObjDir}ftcache.c.x" \xB6 + "{ObjDir}bdf.c.x" \xB6 + "{ObjDir}cff.c.x" \xB6 + "{ObjDir}type1cid.c.x" \xB6 + "{ObjDir}gxvalid.c.x" \xB6 + "{ObjDir}ftgzip.c.x" \xB6 + "{ObjDir}ftbzip2.c.x" \xB6 + "{ObjDir}ftlzw.c.x" \xB6 + "{ObjDir}otvalid.c.x" \xB6 + "{ObjDir}pcf.c.x" \xB6 + "{ObjDir}pfr.c.x" \xB6 + "{ObjDir}psaux.c.x" \xB6 + "{ObjDir}pshinter.c.x" \xB6 + "{ObjDir}psmodule.c.x" \xB6 + "{ObjDir}raster.c.x" \xB6 + "{ObjDir}sfnt.c.x" \xB6 + "{ObjDir}smooth.c.x" \xB6 + "{ObjDir}truetype.c.x" \xB6 + "{ObjDir}type1.c.x" \xB6 + "{ObjDir}type42.c.x" \xB6 + "{ObjDir}winfnt.c.x" + + +### Libraries ### + +LibFiles-PPC = + + +### Default Rules ### + +.c.x \xC4 .c {\xA5MondoBuild\xA5} + {PPCC} {depDir}{default}.c -o {targDir}{default}.c.x {PPCCOptions} + + +### Build Rules ### + +:builds:mac:ftbase.c \xC4\xC4 :src:base:ftbase.c + Duplicate :src:base:ftbase.c :builds:mac:ftbase.c + +"{ObjDir}ftbase.c.x" \xC4\xC4 :builds:mac:ftbase.c + {PPCC} :builds:mac:ftbase.c -o {ObjDir}ftbase.c.x \xB6 + -i :builds:mac: \xB6 + -i :src:base: \xB6 + {PPCCOptions} + +FreeType.ppc_carbon \xC4\xC4 FreeType.ppc_carbon.o + +FreeType.ppc_carbon.o \xC4\xC4 {ObjFiles-PPC} {LibFiles-PPC} {\xA5MondoBuild\xA5} + PPCLink \xB6 + -o {Targ} \xB6 + {ObjFiles-PPC} \xB6 + {LibFiles-PPC} \xB6 + {Sym-PPC} \xB6 + -mf -d \xB6 + -t 'XCOF' \xB6 + -c 'MPS ' \xB6 + -xm l + + + +### Required Dependencies ### + +"{ObjDir}autofit.c.x" \xC4 :src:autofit:autofit.c +# "{ObjDir}ftbase.c.x" \xC4 :builds:mac:ftbase.c +"{ObjDir}ftbbox.c.x" \xC4 :src:base:ftbbox.c +"{ObjDir}ftbdf.c.x" \xC4 :src:base:ftbdf.c +"{ObjDir}ftbitmap.c.x" \xC4 :src:base:ftbitmap.c +"{ObjDir}ftdebug.c.x" \xC4 :src:base:ftdebug.c +"{ObjDir}ftfstype.c.x" \xC4 :src:base:ftfstype.c +"{ObjDir}ftglyph.c.x" \xC4 :src:base:ftglyph.c +"{ObjDir}ftgxval.c.x" \xC4 :src:base:ftgxval.c +"{ObjDir}ftinit.c.x" \xC4 :src:base:ftinit.c +"{ObjDir}ftmm.c.x" \xC4 :src:base:ftmm.c +"{ObjDir}ftotval.c.x" \xC4 :src:base:ftotval.c +"{ObjDir}ftpfr.c.x" \xC4 :src:base:ftpfr.c +"{ObjDir}ftstroke.c.x" \xC4 :src:base:ftstroke.c +"{ObjDir}ftsynth.c.x" \xC4 :src:base:ftsynth.c +"{ObjDir}ftsystem.c.x" \xC4 :src:base:ftsystem.c +"{ObjDir}fttype1.c.x" \xC4 :src:base:fttype1.c +"{ObjDir}ftwinfnt.c.x" \xC4 :src:base:ftwinfnt.c +"{ObjDir}ftcache.c.x" \xC4 :src:cache:ftcache.c +"{ObjDir}bdf.c.x" \xC4 :src:bdf:bdf.c +"{ObjDir}cff.c.x" \xC4 :src:cff:cff.c +"{ObjDir}type1cid.c.x" \xC4 :src:cid:type1cid.c +"{ObjDir}gxvalid.c.x" \xC4 :src:gxvalid:gxvalid.c +"{ObjDir}ftgzip.c.x" \xC4 :src:gzip:ftgzip.c +"{ObjDir}ftbzip2.c.x" \xC4 :src:bzip2:ftbzip2.c +"{ObjDir}ftlzw.c.x" \xC4 :src:lzw:ftlzw.c +"{ObjDir}otvalid.c.x" \xC4 :src:otvalid:otvalid.c +"{ObjDir}pcf.c.x" \xC4 :src:pcf:pcf.c +"{ObjDir}pfr.c.x" \xC4 :src:pfr:pfr.c +"{ObjDir}psaux.c.x" \xC4 :src:psaux:psaux.c +"{ObjDir}pshinter.c.x" \xC4 :src:pshinter:pshinter.c +"{ObjDir}psmodule.c.x" \xC4 :src:psnames:psmodule.c +"{ObjDir}raster.c.x" \xC4 :src:raster:raster.c +"{ObjDir}sfnt.c.x" \xC4 :src:sfnt:sfnt.c +"{ObjDir}smooth.c.x" \xC4 :src:smooth:smooth.c +"{ObjDir}truetype.c.x" \xC4 :src:truetype:truetype.c +"{ObjDir}type1.c.x" \xC4 :src:type1:type1.c +"{ObjDir}type42.c.x" \xC4 :src:type42:type42.c +"{ObjDir}winfnt.c.x" \xC4 :src:winfonts:winfnt.c + + +### Optional Dependencies ### +### Build this target to generate "include file" dependencies. ### + +Dependencies \xC4 $OutOfDate + MakeDepend \xB6 + -append {MAKEFILE} \xB6 + -ignore "{CIncludes}" \xB6 + -objdir "{ObjDir}" \xB6 + -objext .x \xB6 + {Includes} \xB6 + {SrcFiles} + + diff --git a/3rdparty/freetype-2.13.2/builds/mac/FreeType.ppc_classic.make.txt b/3rdparty/freetype-2.13.2/builds/mac/FreeType.ppc_classic.make.txt new file mode 100644 index 000000000..2550190cb --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/mac/FreeType.ppc_classic.make.txt @@ -0,0 +1,213 @@ +# File: FreeType.ppc_classic.make +# Target: FreeType.ppc_classic +# Created: Thursday, October 27, 2005 07:42:43 PM + + +MAKEFILE = FreeType.ppc_classic.make +\xA5MondoBuild\xA5 = {MAKEFILE} # Make blank to avoid rebuilds when makefile is modified + +ObjDir = :objs: +Includes = \xB6 + -ansi strict \xB6 + -includes unix \xB6 + -i :include: \xB6 + -i :src: \xB6 + -i :include:freetype:config: + +Sym-PPC = -sym off + +PPCCOptions = \xB6 + -d FT_MACINTOSH=1 \xB6 + -d HAVE_FSSPEC=1 \xB6 + -d HAVE_FSREF=0 \xB6 + -d HAVE_QUICKDRAW_TOOLBOX=1 \xB6 + -d HAVE_QUICKDRAW_CARBON=0 \xB6 + -d HAVE_ATS=0 \xB6 + -d FT2_BUILD_LIBRARY \xB6 + -d FT_CONFIG_CONFIG_H="" \xB6 + -d FT_CONFIG_MODULES_H="" \xB6 + {Includes} {Sym-PPC} + + +### Source Files ### + +SrcFiles = \xB6 + :src:autofit:autofit.c \xB6 + :builds:mac:ftbase.c \xB6 + :src:base:ftbbox.c \xB6 + :src:base:ftbdf.c \xB6 + :src:base:ftbitmap.c \xB6 + :src:base:ftdebug.c \xB6 + :src:base:ftfstype.c \xB6 + :src:base:ftglyph.c \xB6 + :src:base:ftgxval.c \xB6 + :src:base:ftinit.c \xB6 + :src:base:ftmm.c \xB6 + :src:base:ftotval.c \xB6 + :src:base:ftpfr.c \xB6 + :src:base:ftstroke.c \xB6 + :src:base:ftsynth.c \xB6 + :src:base:ftsystem.c \xB6 + :src:base:fttype1.c \xB6 + :src:base:ftwinfnt.c \xB6 + :src:cache:ftcache.c \xB6 + :src:bdf:bdf.c \xB6 + :src:cff:cff.c \xB6 + :src:cid:type1cid.c \xB6 + :src:gxvalid:gxvalid.c \xB6 + :src:gzip:ftgzip.c \xB6 + :src:bzip2:ftbzip2.c \xB6 + :src:lzw:ftlzw.c \xB6 + :src:otvalid:otvalid.c \xB6 + :src:pcf:pcf.c \xB6 + :src:pfr:pfr.c \xB6 + :src:psaux:psaux.c \xB6 + :src:pshinter:pshinter.c \xB6 + :src:psnames:psmodule.c \xB6 + :src:raster:raster.c \xB6 + :src:sfnt:sfnt.c \xB6 + :src:smooth:smooth.c \xB6 + :src:truetype:truetype.c \xB6 + :src:type1:type1.c \xB6 + :src:type42:type42.c \xB6 + :src:winfonts:winfnt.c + + +### Object Files ### + +ObjFiles-PPC = \xB6 + "{ObjDir}autofit.c.x" \xB6 + "{ObjDir}ftbase.c.x" \xB6 + "{ObjDir}ftbbox.c.x" \xB6 + "{ObjDir}ftbdf.c.x" \xB6 + "{ObjDir}ftbitmap.c.x" \xB6 + "{ObjDir}ftdebug.c.x" \xB6 + "{ObjDir}ftfstype.c.x" \xB6 + "{ObjDir}ftglyph.c.x" \xB6 + "{ObjDir}ftgxval.c.x" \xB6 + "{ObjDir}ftinit.c.x" \xB6 + "{ObjDir}ftmm.c.x" \xB6 + "{ObjDir}ftotval.c.x" \xB6 + "{ObjDir}ftpfr.c.x" \xB6 + "{ObjDir}ftstroke.c.x" \xB6 + "{ObjDir}ftsynth.c.x" \xB6 + "{ObjDir}ftsystem.c.x" \xB6 + "{ObjDir}fttype1.c.x" \xB6 + "{ObjDir}ftwinfnt.c.x" \xB6 + "{ObjDir}ftcache.c.x" \xB6 + "{ObjDir}bdf.c.x" \xB6 + "{ObjDir}cff.c.x" \xB6 + "{ObjDir}type1cid.c.x" \xB6 + "{ObjDir}gxvalid.c.x" \xB6 + "{ObjDir}ftgzip.c.x" \xB6 + "{ObjDir}ftbzip2.c.x" \xB6 + "{ObjDir}ftlzw.c.x" \xB6 + "{ObjDir}otvalid.c.x" \xB6 + "{ObjDir}pcf.c.x" \xB6 + "{ObjDir}pfr.c.x" \xB6 + "{ObjDir}psaux.c.x" \xB6 + "{ObjDir}pshinter.c.x" \xB6 + "{ObjDir}psmodule.c.x" \xB6 + "{ObjDir}raster.c.x" \xB6 + "{ObjDir}sfnt.c.x" \xB6 + "{ObjDir}smooth.c.x" \xB6 + "{ObjDir}truetype.c.x" \xB6 + "{ObjDir}type1.c.x" \xB6 + "{ObjDir}type42.c.x" \xB6 + "{ObjDir}winfnt.c.x" + + +### Libraries ### + +LibFiles-PPC = + + +### Default Rules ### + +.c.x \xC4 .c {\xA5MondoBuild\xA5} + {PPCC} {depDir}{default}.c -o {targDir}{default}.c.x {PPCCOptions} + + +### Build Rules ### + +:builds:mac:ftbase.c \xC4\xC4 :src:base:ftbase.c + Duplicate :src:base:ftbase.c :builds:mac:ftbase.c + +"{ObjDir}ftbase.c.x" \xC4\xC4 :builds:mac:ftbase.c + {PPCC} :builds:mac:ftbase.c -o "{ObjDir}ftbase.c.x" \xB6 + -i :builds:mac: \xB6 + -i :src:base: \xB6 + {PPCCOptions} + +FreeType.ppc_classic \xC4\xC4 FreeType.ppc_classic.o + +FreeType.ppc_classic.o \xC4\xC4 {ObjFiles-PPC} {LibFiles-PPC} {\xA5MondoBuild\xA5} + PPCLink \xB6 + -o {Targ} \xB6 + {ObjFiles-PPC} \xB6 + {LibFiles-PPC} \xB6 + {Sym-PPC} \xB6 + -mf -d \xB6 + -t 'XCOF' \xB6 + -c 'MPS ' \xB6 + -xm l + + + +### Required Dependencies ### + +"{ObjDir}autofit.c.x" \xC4 :src:autofit:autofit.c +# "{ObjDir}ftbase.c.x" \xC4 :builds:mac:ftbase.c +"{ObjDir}ftbbox.c.x" \xC4 :src:base:ftbbox.c +"{ObjDir}ftbdf.c.x" \xC4 :src:base:ftbdf.c +"{ObjDir}ftbitmap.c.x" \xC4 :src:base:ftbitmap.c +"{ObjDir}ftdebug.c.x" \xC4 :src:base:ftdebug.c +"{ObjDir}ftfstype.c.x" \xC4 :src:base:ftfstype.c +"{ObjDir}ftglyph.c.x" \xC4 :src:base:ftglyph.c +"{ObjDir}ftgxval.c.x" \xC4 :src:base:ftgxval.c +"{ObjDir}ftinit.c.x" \xC4 :src:base:ftinit.c +"{ObjDir}ftmm.c.x" \xC4 :src:base:ftmm.c +"{ObjDir}ftotval.c.x" \xC4 :src:base:ftotval.c +"{ObjDir}ftpfr.c.x" \xC4 :src:base:ftpfr.c +"{ObjDir}ftstroke.c.x" \xC4 :src:base:ftstroke.c +"{ObjDir}ftsynth.c.x" \xC4 :src:base:ftsynth.c +"{ObjDir}ftsystem.c.x" \xC4 :src:base:ftsystem.c +"{ObjDir}fttype1.c.x" \xC4 :src:base:fttype1.c +"{ObjDir}ftwinfnt.c.x" \xC4 :src:base:ftwinfnt.c +"{ObjDir}ftcache.c.x" \xC4 :src:cache:ftcache.c +"{ObjDir}bdf.c.x" \xC4 :src:bdf:bdf.c +"{ObjDir}cff.c.x" \xC4 :src:cff:cff.c +"{ObjDir}type1cid.c.x" \xC4 :src:cid:type1cid.c +"{ObjDir}gxvalid.c.x" \xC4 :src:gxvalid:gxvalid.c +"{ObjDir}ftgzip.c.x" \xC4 :src:gzip:ftgzip.c +"{ObjDir}ftbzip2.c.x" \xC4 :src:bzip2:ftbzip2.c +"{ObjDir}ftlzw.c.x" \xC4 :src:lzw:ftlzw.c +"{ObjDir}otvalid.c.x" \xC4 :src:otvalid:otvalid.c +"{ObjDir}pcf.c.x" \xC4 :src:pcf:pcf.c +"{ObjDir}pfr.c.x" \xC4 :src:pfr:pfr.c +"{ObjDir}psaux.c.x" \xC4 :src:psaux:psaux.c +"{ObjDir}pshinter.c.x" \xC4 :src:pshinter:pshinter.c +"{ObjDir}psmodule.c.x" \xC4 :src:psnames:psmodule.c +"{ObjDir}raster.c.x" \xC4 :src:raster:raster.c +"{ObjDir}sfnt.c.x" \xC4 :src:sfnt:sfnt.c +"{ObjDir}smooth.c.x" \xC4 :src:smooth:smooth.c +"{ObjDir}truetype.c.x" \xC4 :src:truetype:truetype.c +"{ObjDir}type1.c.x" \xC4 :src:type1:type1.c +"{ObjDir}type42.c.x" \xC4 :src:type42:type42.c +"{ObjDir}winfnt.c.x" \xC4 :src:winfonts:winfnt.c + + + +### Optional Dependencies ### +### Build this target to generate "include file" dependencies. ### + +Dependencies \xC4 $OutOfDate + MakeDepend \xB6 + -append {MAKEFILE} \xB6 + -ignore "{CIncludes}" \xB6 + -objdir "{ObjDir}" \xB6 + -objext .x \xB6 + {Includes} \xB6 + {SrcFiles} + + diff --git a/3rdparty/freetype-2.13.2/builds/mac/README b/3rdparty/freetype-2.13.2/builds/mac/README new file mode 100644 index 000000000..06e3d51da --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/mac/README @@ -0,0 +1,393 @@ +This folder contains + + * Makefile skeletons for Apple MPW (Macintosh's Programmer's Workshop) + + * Python script to generate MPW makefile from skeleton + + * Metrowerks CodeWarrior 9.0 project file in XML format + +------------------------------------------------------------ + +1. What is this +--------------- + +Files in this directory are designed to build FreeType +running on classic MacOS. To build FreeType running on +Mac OS X, build as the system is UNIX. + +However, Mac OS X is most useful to manipulate files in +vanilla FreeType to fit classic MacOS. + +The information about MacOS specific API is written in +appendix of this document. + +2. Requirement +-------------- + +You can use MPW: a free-charged developer environment +by Apple, or CodeWarrior: a commercial developer +environment by Metrowerks. GCC for MPW and Symantec +"Think C" are not tested at present. + + + 2-1. Apple MPW + -------------- + + Following C compilers are tested: + + m68k target: Apple SC 8.9.0d3e1 + ppc target: Apple MrC 5.0.0d3c1 + + The final MPW-GM (official release on 1999/Dec) is too + old and cannot compile FreeType, because bundled C + compilers cannot search header files in sub directories. + Updating by the final MPW-PR (pre-release on 2001/Feb) + is required. + + Required files are downloadable from: + + http://macintoshgarden.org/apps/macintosh-programmers-workshop + + Also you can find documents how to update by MPW-PR. + + Python is required to restore MPW makefiles from the + skeletons. Python bundled to Mac OS X is enough. For + classic MacOS, MacPython is available: + + https://homepages.cwi.nl/~jack/macpython/ + + MPW requires all files are typed by resource fork. + ResEdit bundled to MPW is enough. In Mac OS X, + /Developer/Tools/SetFile of DevTool is useful to + manipulate from commandline. + + 2-2. Metrowerks CodeWarrior + --------------------------- + + XML project file is generated and tested by + CodeWarrior 9.0. Older versions are not tested + at all. At present, static library for ppc target + is available in the project file. + + +3. How to build +--------------- + + 3-1. Apple MPW + -------------- + Detailed building procedure by Apple MPW is + described in following. + + 3-1-1. Generate MPW makefiles from the skeletons + ------------------------------------------------ + + Here are 4 skeletons for following targets are + included. + + - FreeType.m68k_far.make.txt + Ancient 32bit binary executable format for + m68k MacOS: System 6, with 32bit addressing + mode (far-pointer-model) So-called "Toolbox" + API is used. + + - FreeType.m68k_cfm.make.txt + CFM binary executable format for m68k MacOS: + System 7. So-called "Toolbox" API is used. + + - FreeType.ppc_classic.make.txt + CFM binary executable format for ppc MacOS: + System 7, MacOS 8, MacOS 9. So-called "Toolbox" + API is used. + + - FreeType.ppc_carbon.make.txt + CFM binary executable format for ppc MacOS: + MacOS 9. Carbon API is used. + + At present, static library is only supported, + although targets except of m68k_far are capable + to use shared library. + + MPW makefile syntax uses 8bit characters. To keep + from violating them during version control, here + we store skeletons in pure ASCII format. You must + generate MPW makefile by Python script ascii2mpw.py. + + In Mac OS X terminal, you can convert as: + + python builds/mac/ascii2mpw.py \ + < builds/mac/FreeType.m68k_far.make.txt \ + > FreeType.m68k_far.make + + The skeletons are designed to use in the top + directory where there are builds, include, src etc. + You must name the generated MPW makefile by removing + ".txt" from source skeleton name. + + 3-1-2. Add resource forks to related files + ------------------------------------------ + + MPW's Make and C compilers cannot recognize files + without resource fork. You have to add resource + fork to the files that MPW uses. In Mac OS X + terminal of the system, you can do as: + + find . -name '*.[ch]' -exec \ + /Developer/Tools/SetFile -a l -c "MPS " -t TEXT \{\} \; + + find . -name '*.make' -exec \ + /Developer/Tools/SetFile -a l -c "MPS " -t TEXT \{\} \; + + + 3-1-3. Open MPW shell and build + ------------------------------- + + Open MPW shell and go to the top directory that + FreeType sources are extracted (MPW makefile must + be located in there), from "Set Directory" in + "Directory" menu. + + Choose "Build" from "Build" menu, and type the + name of project by removing ".make" from MPW + makefile, as: FreeType.m68k_far + + If building is successfully finished, you can find + built library in objs/ directory. + + + 3-2. Metrowerks CodeWarrior + --------------------------- + + Detailed building procedure by Metrowerks + CodeWarrior (CW) 9.0 is described in following. + + 3-2-1. Import XML project file + ------------------------------ + + CW XML project file is not ready for double- + click. Start CodeWarrior IDE, and choose + "Import project" in "File" menu. Choose XML + project file: builds/mac/ftlib.prj.xml. + In next, you will be asked where to save CW + native project file: you must choose + "builds/mac/ftlib.prj". The project file is + designed with relative path from there. After + CW native project file is generated, it is + automatically loaded, small project window + titled "ftlib.prj" is displayed. + + 3-2-2. Building + --------------- + Choose "Make" from "Project" menu. If building + is successfully finished, you can find built + library at objs/FreeTypeLib. + +4. TODO +------- + + 4-1. All modules should be included + ----------------------------------- + + At present, MPW makefiles and CW project file are + just updated versions of these by Leonard. Some + modules are added after the last maintenance, they + are not included. + + 4-2. Working test with ftdemos + ------------------------------ + + At present, MPW makefiles and CW project file can + build FreeType for classic MacOS. But their working + behaviours are not tested at all. Building ftdemos + for classic MacOS and working test is required. + + +APPENDIX I +---------- + + A-1. Framework dependencies + --------------------------- + + src/base/ftmac.c adds two Mac-specific features to + FreeType. These features are based on MacOS libraries. + + * accessing resource-fork font + The fonts for classic MacOS store their graphical data + in resource forks which cannot be accessed via ANSI C + functions. FreeType2 provides functions to handle such + resource fork fonts, they are based on File Manager + framework of MacOS. In addition, HFS and HFS+ file + system driver of Linux is supported. Following + functions are for this purpose. + + FT_New_Face_From_Resource() + FT_New_Face_From_FSSpec() + FT_New_Face_From_FSRef() + + * resolving font name to font file + The font menu of MacOS application prefers font name + written in FOND resource than sfnt resource. FreeType2 + provides functions to find font file by name in MacOS + application, they are based on QuickDraw Font Manager + and Apple Type Service framework of MacOS. + + FT_GetFile_From_Mac_Name() + FT_GetFile_From_Mac_ATS_Name() + + Working functions for each MacOS are summarized as + following. + + upto MacOS 6: + not tested (you have to obtain MPW 2.x) + + MacOS 7.x, 8.x, 9.x (without CarbonLib): + FT_GetFile_From_Mac_Name() + FT_New_Face_From_Resource() + FT_New_Face_From_FSSpec() + + MacOS 9.x (with CarbonLib): + FT_GetFile_From_Mac_Name() + FT_New_Face_From_Resource() + FT_New_Face_From_FSSpec() + FT_New_Face_From_FSRef() + + Mac OS X upto 10.4.x: + FT_GetFile_From_Mac_Name() deprecated + FT_New_Face_From_FSSpec() deprecated + FT_GetFile_From_Mac_ATS_Name() deprecated? + FT_New_Face_From_FSRef() + + A-2. Deprecated Functions + ------------------------- + + A-2-1. FileManager + ------------------ + + For convenience to write MacOS application, ftmac.c + provides functions to specify a file by FSSpec and FSRef, + because the file identification pathname had ever been + unrecommended method in MacOS programming. + + Toward to MacOS X 10.4 & 5, Carbon functions using FSSpec + datatype is noticed as deprecated, and recommended to + migrate to FSRef datatype. The big differences of FSRef + against FSSpec are explained in Apple TechNotes 2078. + + https://developer.apple.com/library/archive/technotes/tn2078/ + + - filename length: the max length of file + name of FSRef is 255 chars (it is limit of HFS+), + that of FSSpec is 31 chars (it is limit of HFS). + + - filename encoding: FSSpec is localized by + legacy encoding for each language system, + FSRef is Unicode enabled. + + A-2-2. FontManager + ------------------ + + Following functions receive QuickDraw fontname: + + FT_GetFile_From_Mac_Name() + + QuickDraw is deprecated and replaced by Quartz + since Mac OS X 10.4. They are still kept for + backward compatibility. By undefinition of + HAVE_QUICKDRAW in building, you can change these + functions to return FT_Err_Unimplemented always. + + Replacement functions are added for migration. + + FT_GetFile_From_Mac_ATS_Name() + + They are usable on Mac OS X only. On older systems, + these functions return FT_Err_Unimplemented always. + + The detailed incompatibilities and possibility + of FontManager emulation without QuickDraw is + explained in + + http://gyvern.ipc.hiroshima-u.ac.jp/~mpsuzuki/ats_benchmark.html + + A-3. Framework Availabilities + ----------------------------- + + The framework of MacOS are often revised, especially + when new format of binary executable is introduced. + Following table is the minimum version of frameworks + to use functions used in FreeType2. The table is + extracted from MPW header files for assembly language. + + *** NOTE *** + The conditional definition of available data type + in MPW compiler is insufficient. You can compile + program using FSRef data type for older systems + (MacOS 7, 8) that don't know FSRef data type. + + + +-------------------+-----------------------------+ + CPU | mc680x0 | PowerPC | + +---------+---------+---------+---------+---------+ + Binary Executable Format | Classic | 68K-CFM | CFM | CFM | Mach-O | + +---------+---------+---------+---------+---------+ + Framework API | Toolbox | Toolbox | Toolbox | Carbon | Carbon | + +---------+---------+---------+---------+---------+ + + +---------+---------+---------+---------+---------+ + | ?(*) |Interface|Interface|CarbonLib|Mac OS X | + | |Lib |Lib | | | +* Files.h +---------+---------+---------+---------+---------+ +PBGetFCBInfoSync() | o | 7.1- | 7.1- | 1.0- | o | +FSMakeFSSpec() | o | 7.1- | 7.1- | 1.0- | o | +FSGetForkCBInfo() | o | (**) | 9.0- | 1.0- | o | +FSpMakeFSRef() | o | (**) | 9.0- | 1.0- | o | +FSGetCatalogInfo() | o | (**) | 9.0- | 1.0- | -10.3 | +FSPathMakeRef() | x | x | x | 1.1- | -10.3 | + +---------+---------+---------+---------+---------+ + + +---------+---------+---------+---------+---------+ + | ?(*) |Font |Font |CarbonLib|Mac OS X | + | |Manager |Manager | | | +* Fonts.h +---------+---------+---------+---------+---------+ +FMCreateFontFamilyIterator() | x | x | 9.0- | 1.0- | -10.3 | +FMDisposeFontFamilyIterator() | x | x | 9.0- | 1.0- | -10.3 | +FMGetNextFontFamily() | x | x | 9.0- | 1.0- | -10.3 | +FMGetFontFamilyName() | x | x | 9.0- | 1.0- | -10.3 | +FMCreateFontFamilyInstanceIterator() | x | x | 9.0- | 1.0- | -10.3 | +FMDisposeFontFamilyInstanceIterator() | x | x | 9.0- | 1.0- | -10.3 | +FMGetNextFontFamilyInstance() | x | x | 9.0- | 1.0- | -10.3 | + +---------+---------+---------+---------+---------+ + + +---------+---------+---------+---------+---------+ + | - | - | - |CarbonLib|Mac OS X | +* ATSFont.h (***) +---------+---------+---------+---------+---------+ +ATSFontFindFromName() | x | x | x | x | o | +ATSFontGetFileSpecification() | x | x | x | x | o | + +---------+---------+---------+---------+---------+ + + (*) + In the "Classic": the original binary executable + format, these framework functions are directly + transformed to MacOS system call. Therefore, the + exact availability should be checked by running + system. + + (**) + InterfaceLib is bundled to MacOS and its version + is usually equal to MacOS. There's no separate + update for InterfaceLib. It is supposed that + there's no InterfaceLib 9.x for m68k platforms. + In fact, these functions are FSRef dependent. + + (***) + ATSUI framework is available on ATSUnicode 8.5 on + ppc Toolbox CFM, CarbonLib 1.0 too. But its base: + ATS font manager is not published in these versions. + +------------------------------------------------------------ +Last update: 2013-Nov-03. + +Currently maintained by + suzuki toshiya, +Originally prepared by + Leonard Rosenthol, + Just van Rossum, diff --git a/3rdparty/freetype-2.13.2/builds/mac/ascii2mpw.py b/3rdparty/freetype-2.13.2/builds/mac/ascii2mpw.py new file mode 100644 index 000000000..ad32b2197 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/mac/ascii2mpw.py @@ -0,0 +1,24 @@ +#!/usr/bin/env python +import sys +import string + +if len( sys.argv ) == 1 : + for asc_line in sys.stdin.readlines(): + mpw_line = string.replace(asc_line, "\\xA5", "\245") + mpw_line = string.replace(mpw_line, "\\xB6", "\266") + mpw_line = string.replace(mpw_line, "\\xC4", "\304") + mpw_line = string.replace(mpw_line, "\\xC5", "\305") + mpw_line = string.replace(mpw_line, "\\xFF", "\377") + mpw_line = string.replace(mpw_line, "\n", "\r") + mpw_line = string.replace(mpw_line, "\\n", "\n") + sys.stdout.write(mpw_line) +elif sys.argv[1] == "-r" : + for mpw_line in sys.stdin.readlines(): + asc_line = string.replace(mpw_line, "\n", "\\n") + asc_line = string.replace(asc_line, "\r", "\n") + asc_line = string.replace(asc_line, "\245", "\\xA5") + asc_line = string.replace(asc_line, "\266", "\\xB6") + asc_line = string.replace(asc_line, "\304", "\\xC4") + asc_line = string.replace(asc_line, "\305", "\\xC5") + asc_line = string.replace(asc_line, "\377", "\\xFF") + sys.stdout.write(asc_line) diff --git a/3rdparty/freetype-2.13.2/builds/mac/freetype-Info.plist b/3rdparty/freetype-2.13.2/builds/mac/freetype-Info.plist new file mode 100644 index 000000000..344e5ac0b --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/mac/freetype-Info.plist @@ -0,0 +1,36 @@ + + + + + + + CFBundleDevelopmentRegion + English + + CFBundleExecutable + freetype + + CFBundleGetInfoString + FreeType ${PROJECT_VERSION} + + CFBundleInfoDictionaryVersion + 6.0 + + CFBundleName + FreeType + + CFBundlePackageType + FMWK + + CFBundleShortVersionString + ${PROJECT_VERSION} + + CFBundleSignature + ???? + + CFBundleVersion + ${PROJECT_VERSION} + + + diff --git a/3rdparty/freetype-2.13.2/builds/mac/ftlib.prj.xml b/3rdparty/freetype-2.13.2/builds/mac/ftlib.prj.xml new file mode 100644 index 000000000..cbbc45ee5 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/mac/ftlib.prj.xml @@ -0,0 +1,1194 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +]> + + + + + FreeTypeLib + + + + UserSourceTrees + + + AlwaysSearchUserPathstrue + InterpretDOSAndUnixPathstrue + RequireFrameworkStyleIncludesfalse + SourceRelativeIncludesfalse + UserSearchPaths + + SearchPath + Path: + PathFormatMacOS + PathRootProject + + Recursivetrue + FrameworkPathfalse + HostFlagsAll + + + SearchPath + Path:::include: + PathFormatMacOS + PathRootProject + + Recursivetrue + FrameworkPathfalse + HostFlagsAll + + + SearchPath + Path:::src: + PathFormatMacOS + PathRootProject + + Recursivetrue + FrameworkPathfalse + HostFlagsAll + + + SearchPath + Path:: + PathFormatMacOS + PathRootProject + + Recursivetrue + FrameworkPathfalse + HostFlagsAll + + + SystemSearchPaths + + SearchPath + Path: + PathFormatMacOS + PathRootCodeWarrior + + Recursivetrue + FrameworkPathfalse + HostFlagsAll + + + + + MWRuntimeSettings_WorkingDirectory + MWRuntimeSettings_CommandLine + MWRuntimeSettings_HostApplication + Path + PathFormatGeneric + PathRootAbsolute + + MWRuntimeSettings_EnvVars + + + LinkerMacOS PPC Linker + PreLinker + PostLinker + TargetnameFreeTypeLib + OutputDirectory + Path:::objs: + PathFormatMacOS + PathRootProject + + SaveEntriesUsingRelativePathsfalse + + + FileMappings + + FileTypeAPPL + FileExtension + Compiler + EditLanguage + Precompilefalse + Launchabletrue + ResourceFiletrue + IgnoredByMakefalse + + + FileTypeAppl + FileExtension + Compiler + EditLanguage + Precompilefalse + Launchabletrue + ResourceFiletrue + IgnoredByMakefalse + + + FileTypeMMLB + FileExtension + CompilerLib Import PPC + EditLanguage + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypeMPLF + FileExtension + CompilerLib Import PPC + EditLanguage + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypeMWCD + FileExtension + Compiler + EditLanguage + Precompilefalse + Launchabletrue + ResourceFiletrue + IgnoredByMakefalse + + + FileTypeRSRC + FileExtension + Compiler + EditLanguage + Precompilefalse + Launchabletrue + ResourceFiletrue + IgnoredByMakefalse + + + FileTypeTEXT + FileExtension.bh + CompilerBalloon Help + EditLanguage + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypeTEXT + FileExtension.c + CompilerMW C/C++ PPC + EditLanguageC/C++ + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypeTEXT + FileExtension.c++ + CompilerMW C/C++ PPC + EditLanguageC/C++ + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypeTEXT + FileExtension.cc + CompilerMW C/C++ PPC + EditLanguageC/C++ + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypeTEXT + FileExtension.cp + CompilerMW C/C++ PPC + EditLanguageC/C++ + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypeTEXT + FileExtension.cpp + CompilerMW C/C++ PPC + EditLanguageC/C++ + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypeTEXT + FileExtension.exp + Compiler + EditLanguage + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypeTEXT + FileExtension.h + CompilerMW C/C++ PPC + EditLanguageC/C++ + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMaketrue + + + FileTypeTEXT + FileExtension.p + CompilerMW Pascal PPC + EditLanguage + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypeTEXT + FileExtension.pas + CompilerMW Pascal PPC + EditLanguage + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypeTEXT + FileExtension.pch + CompilerMW C/C++ PPC + EditLanguageC/C++ + Precompiletrue + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypeTEXT + FileExtension.pch++ + CompilerMW C/C++ PPC + EditLanguageC/C++ + Precompiletrue + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypeTEXT + FileExtension.ppu + CompilerMW Pascal PPC + EditLanguage + Precompiletrue + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypeTEXT + FileExtension.r + CompilerRez + EditLanguageRez + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypeTEXT + FileExtension.s + CompilerPPCAsm + EditLanguage + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypeXCOF + FileExtension + CompilerXCOFF Import PPC + EditLanguage + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypedocu + FileExtension + Compiler + EditLanguage + Precompilefalse + Launchabletrue + ResourceFiletrue + IgnoredByMakefalse + + + FileTypersrc + FileExtension + Compiler + EditLanguage + Precompilefalse + Launchabletrue + ResourceFiletrue + IgnoredByMakefalse + + + FileTypeshlb + FileExtension + CompilerPEF Import PPC + EditLanguage + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileTypestub + FileExtension + CompilerPEF Import PPC + EditLanguage + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileExtension.doc + Compiler + EditLanguage + Precompilefalse + Launchabletrue + ResourceFilefalse + IgnoredByMaketrue + + + FileExtension.o + CompilerXCOFF Import PPC + EditLanguage + Precompilefalse + Launchablefalse + ResourceFilefalse + IgnoredByMakefalse + + + FileExtension.ppob + Compiler + EditLanguage + Precompilefalse + Launchabletrue + ResourceFiletrue + IgnoredByMakefalse + + + FileExtension.rsrc + Compiler + EditLanguage + Precompilefalse + Launchabletrue + ResourceFiletrue + IgnoredByMakefalse + + + + + CacheModDatestrue + DumpBrowserInfofalse + CacheSubprojectstrue + UseThirdPartyDebuggerfalse + BrowserGenerator1 + DebuggerAppPath + Path + PathFormatGeneric + PathRootAbsolute + + DebuggerCmdLineArgs + DebuggerWorkingDir + Path + PathFormatGeneric + PathRootAbsolute + + CodeCompletionPrefixFileNameMacHeaders.c + CodeCompletionMacroFileNameMacOS_Carbon_C++_Macros.h + + + ConsoleEncoding0 + LogSystemMessagestrue + AutoTargetDLLsfalse + StopAtWatchpointstrue + PauseWhileRunningfalse + PauseInterval5 + PauseUIFlags0 + AltExePath + Path + PathFormatGeneric + PathRootAbsolute + + StopAtTempBPOnLaunchtrue + CacheSymbolicstrue + TempBPFunctionNamemain + TempBPType0 + + + Enabledfalse + ConnectionName + DownloadPath + LaunchRemoteAppfalse + RemoteAppPath + CoreID0 + JTAGClockSpeed8000 + IsMultiCorefalse + OSDownloadfalse + UseGlobalOSDownloadfalse + OSDownloadConnectionName + OSDownloadPath + AltDownloadfalse + AltDownloadConnectionName + + + OtherExecutables + + + AnalyzerConnectionName + + + CustomColor1 + Red0 + Green32767 + Blue0 + + CustomColor2 + Red0 + Green32767 + Blue0 + + CustomColor3 + Red0 + Green32767 + Blue0 + + CustomColor4 + Red0 + Green32767 + Blue0 + + + + MWFrontEnd_C_cplusplus0 + MWFrontEnd_C_checkprotos1 + MWFrontEnd_C_arm0 + MWFrontEnd_C_trigraphs0 + MWFrontEnd_C_onlystdkeywords0 + MWFrontEnd_C_enumsalwaysint0 + MWFrontEnd_C_ansistrict1 + MWFrontEnd_C_wchar_type1 + MWFrontEnd_C_enableexceptions1 + MWFrontEnd_C_dontreusestrings0 + MWFrontEnd_C_poolstrings0 + MWFrontEnd_C_dontinline0 + MWFrontEnd_C_useRTTI1 + MWFrontEnd_C_unsignedchars0 + MWFrontEnd_C_autoinline0 + MWFrontEnd_C_booltruefalse1 + MWFrontEnd_C_inlinelevel0 + MWFrontEnd_C_ecplusplus0 + MWFrontEnd_C_defer_codegen0 + MWFrontEnd_C_templateparser0 + MWFrontEnd_C_c990 + MWFrontEnd_C_bottomupinline1 + MWFrontEnd_C_gcc_extensions0 + MWFrontEnd_C_instance_manager0 + + + C_CPP_Preprocessor_EmitFiletrue + C_CPP_Preprocessor_EmitLinefalse + C_CPP_Preprocessor_EmitFullPathfalse + C_CPP_Preprocessor_KeepCommentsfalse + C_CPP_Preprocessor_PCHUsesPrefixTextfalse + C_CPP_Preprocessor_EmitPragmastrue + C_CPP_Preprocessor_KeepWhiteSpacefalse + C_CPP_Preprocessor_MultiByteEncodingencASCII_Unicode + C_CPP_Preprocessor_PrefixText/* settings imported from old "C/C++ Language" panel */ + +#if !__option(precompile) +#include "ftoption.h" /* was "Prefix file" */ +#endif + + + + MWWarning_C_warn_illpragma0 + MWWarning_C_warn_emptydecl0 + MWWarning_C_warn_possunwant0 + MWWarning_C_warn_unusedvar1 + MWWarning_C_warn_unusedarg1 + MWWarning_C_warn_extracomma0 + MWWarning_C_pedantic0 + MWWarning_C_warningerrors0 + MWWarning_C_warn_hidevirtual0 + MWWarning_C_warn_implicitconv0 + MWWarning_C_warn_notinlined0 + MWWarning_C_warn_structclass0 + MWWarning_C_warn_missingreturn0 + MWWarning_C_warn_no_side_effect0 + MWWarning_C_warn_resultnotused0 + MWWarning_C_warn_padding0 + MWWarning_C_warn_impl_i2f_conv0 + MWWarning_C_warn_impl_f2i_conv0 + MWWarning_C_warn_impl_s2u_conv0 + MWWarning_C_warn_illtokenpasting0 + MWWarning_C_warn_filenamecaps0 + MWWarning_C_warn_filenamecapssystem0 + MWWarning_C_warn_undefmacro0 + MWWarning_C_warn_ptrintconv0 + + + MWMerge_MacOS_projectTypeApplication + MWMerge_MacOS_outputNameMerge Out + MWMerge_MacOS_outputCreator???? + MWMerge_MacOS_outputTypeAPPL + MWMerge_MacOS_suppressWarning0 + MWMerge_MacOS_copyFragments1 + MWMerge_MacOS_copyResources1 + MWMerge_MacOS_flattenResource0 + MWMerge_MacOS_flatFileNamea.rsrc + MWMerge_MacOS_flatFileOutputPath + Path: + PathFormatMacOS + PathRootProject + + MWMerge_MacOS_skipResources + DLGX + ckid + Proj + WSPC + + + + FileLockedfalse + ResourcesMapIsReadOnlyfalse + PrinterDriverIsMultiFinderCompatiblefalse + Invisiblefalse + HasBundlefalse + NameLockedfalse + Stationeryfalse + HasCustomIconfalse + Sharedfalse + HasBeenInitedfalse + Label0 + Comments + HasCustomBadgefalse + HasRoutingInfofalse + + + MWCodeGen_PPC_structalignmentPPC_mw + MWCodeGen_PPC_tracebacktablesNone + MWCodeGen_PPC_processorGeneric + MWCodeGen_PPC_function_align4 + MWCodeGen_PPC_tocdata1 + MWCodeGen_PPC_largetoc0 + MWCodeGen_PPC_profiler0 + MWCodeGen_PPC_vectortocdata0 + MWCodeGen_PPC_poolconst0 + MWCodeGen_PPC_peephole0 + MWCodeGen_PPC_readonlystrings0 + MWCodeGen_PPC_linkerpoolsstrings0 + MWCodeGen_PPC_volatileasm0 + MWCodeGen_PPC_schedule0 + MWCodeGen_PPC_altivec0 + MWCodeGen_PPC_altivec_move_block0 + MWCodeGen_PPC_strictIEEEfp0 + MWCodeGen_PPC_fpcontract1 + MWCodeGen_PPC_genfsel0 + MWCodeGen_PPC_orderedfpcmp0 + + + MWCodeGen_MachO_structalignmentPPC_mw + MWCodeGen_MachO_profiler_enumOff + MWCodeGen_MachO_processorGeneric + MWCodeGen_MachO_function_align4 + MWCodeGen_MachO_common0 + MWCodeGen_MachO_boolisint0 + MWCodeGen_MachO_peephole1 + MWCodeGen_MachO_readonlystrings0 + MWCodeGen_MachO_linkerpoolsstrings1 + MWCodeGen_MachO_volatileasm0 + MWCodeGen_MachO_schedule0 + MWCodeGen_MachO_altivec0 + MWCodeGen_MachO_vecmove0 + MWCodeGen_MachO_fp_ieee_strict0 + MWCodeGen_MachO_fpcontract1 + MWCodeGen_MachO_genfsel0 + MWCodeGen_MachO_fp_cmps_ordered0 + + + MWDisassembler_PPC_showcode1 + MWDisassembler_PPC_extended1 + MWDisassembler_PPC_mix0 + MWDisassembler_PPC_nohex0 + MWDisassembler_PPC_showdata1 + MWDisassembler_PPC_showexceptions1 + MWDisassembler_PPC_showsym0 + MWDisassembler_PPC_shownames1 + + + GlobalOptimizer_PPC_optimizationlevelLevel0 + GlobalOptimizer_PPC_optforSpeed + + + MWLinker_PPC_linksym1 + MWLinker_PPC_symfullpath1 + MWLinker_PPC_linkmap0 + MWLinker_PPC_nolinkwarnings0 + MWLinker_PPC_dontdeadstripinitcode0 + MWLinker_PPC_permitmultdefs0 + MWLinker_PPC_linkmodeFast + MWLinker_PPC_code_foldingNone + MWLinker_PPC_initname + MWLinker_PPC_mainname + MWLinker_PPC_termname + + + MWLinker_MacOSX_linksym1 + MWLinker_MacOSX_symfullpath0 + MWLinker_MacOSX_nolinkwarnings0 + MWLinker_MacOSX_linkmap0 + MWLinker_MacOSX_dontdeadstripinitcode0 + MWLinker_MacOSX_permitmultdefs0 + MWLinker_MacOSX_use_objectivec_semantics0 + MWLinker_MacOSX_strip_debug_symbols0 + MWLinker_MacOSX_split_segs0 + MWLinker_MacOSX_report_msl_overloads0 + MWLinker_MacOSX_objects_follow_linkorder0 + MWLinker_MacOSX_linkmodeNormal + MWLinker_MacOSX_exportsReferencedGlobals + MWLinker_MacOSX_sortcodeNone + MWLinker_MacOSX_mainname + MWLinker_MacOSX_initname + MWLinker_MacOSX_code_foldingNone + MWLinker_MacOSX_stabsgenNone + + + MWProject_MacOSX_typeExecutable + MWProject_MacOSX_outfile + MWProject_MacOSX_filecreator???? + MWProject_MacOSX_filetypeMEXE + MWProject_MacOSX_vmaddress4096 + MWProject_MacOSX_usedefaultvmaddr1 + MWProject_MacOSX_flatrsrc0 + MWProject_MacOSX_flatrsrcfilename + MWProject_MacOSX_flatrsrcoutputdir + Path: + PathFormatMacOS + PathRootProject + + MWProject_MacOSX_installpath./ + MWProject_MacOSX_dont_prebind0 + MWProject_MacOSX_flat_namespace0 + MWProject_MacOSX_frameworkversionA + MWProject_MacOSX_currentversion0 + MWProject_MacOSX_flat_oldimpversion0 + MWProject_MacOSX_AddrMode1 + + + MWPEF_exportsNone + MWPEF_libfolder0 + MWPEF_sortcodeNone + MWPEF_expandbss0 + MWPEF_sharedata0 + MWPEF_olddefversion0 + MWPEF_oldimpversion0 + MWPEF_currentversion0 + MWPEF_fragmentname + MWPEF_collapsereloads0 + + + MWProject_PPC_typeLibrary + MWProject_PPC_outfileFreeTypeLib + MWProject_PPC_filecreator???? + MWProject_PPC_filetype???? + MWProject_PPC_size0 + MWProject_PPC_minsize0 + MWProject_PPC_stacksize0 + MWProject_PPC_flags0 + MWProject_PPC_symfilename + MWProject_PPC_rsrcname + MWProject_PPC_rsrcheaderNative + MWProject_PPC_rsrctype???? + MWProject_PPC_rsrcid0 + MWProject_PPC_rsrcflags0 + MWProject_PPC_rsrcstore0 + MWProject_PPC_rsrcmerge0 + MWProject_PPC_flatrsrc0 + MWProject_PPC_flatrsrcoutputdir + Path: + PathFormatMacOS + PathRootProject + + MWProject_PPC_flatrsrcfilename + + + MWAssembler_PPC_auxheader0 + MWAssembler_PPC_symmodeMac + MWAssembler_PPC_dialectPPC + MWAssembler_PPC_prefixfile + MWAssembler_PPC_typecheck0 + MWAssembler_PPC_warnings0 + MWAssembler_PPC_casesensitive0 + + + PList_OutputTypeFile + PList_OutputEncodingUTF-8 + PList_PListVersion1.0 + PList_Prefix + PList_FileFilenameInfo.plist + PList_FileDirectory + Path: + PathFormatMacOS + PathRootProject + + PList_ResourceTypeplst + PList_ResourceID0 + PList_ResourceName + + + MWRez_Language_maxwidth80 + MWRez_Language_scriptRoman + MWRez_Language_alignmentAlign1 + MWRez_Language_filtermodeFilterSkip + MWRez_Language_suppresswarnings0 + MWRez_Language_escapecontrolchars1 + MWRez_Language_prefixname + MWRez_Language_filteredtypes'CODE' 'DATA' 'PICT' + + + + Name + ftsystem.c + MacOS + Text + Debug + + + Name + ftbase.c + MacOS + Text + Debug + + + Name + ftinit.c + MacOS + Text + Debug + + + Name + sfnt.c + MacOS + Text + Debug + + + Name + psnames.c + MacOS + Text + Debug + + + Name + ftdebug.c + MacOS + Text + Debug + + + Name + type1cid.c + MacOS + Text + Debug + + + Name + cff.c + MacOS + Text + Debug + + + Name + smooth.c + MacOS + Text + Debug + + + Name + winfnt.c + MacOS + Text + Debug + + + Name + truetype.c + MacOS + Text + Debug + + + Name + ftmac.c + MacOS + Text + Debug + + + Name + psaux.c + MacOS + Text + + + + Name + ftcache.c + MacOS + Text + + + + Name + ftglyph.c + MacOS + Text + + + + Name + type1.c + MacOS + Text + Debug + + + Name + pshinter.c + MacOS + Text + Debug + + + Name + pcf.c + MacOS + Text + Debug + + + Name + ftraster.c + MacOS + Text + Debug + + + Name + ftrend1.c + MacOS + Text + Debug + + + + + Name + ftsystem.c + MacOS + + + Name + ftbase.c + MacOS + + + Name + ftinit.c + MacOS + + + Name + sfnt.c + MacOS + + + Name + psnames.c + MacOS + + + Name + ftdebug.c + MacOS + + + Name + type1cid.c + MacOS + + + Name + cff.c + MacOS + + + Name + smooth.c + MacOS + + + Name + winfnt.c + MacOS + + + Name + truetype.c + MacOS + + + Name + ftmac.c + MacOS + + + Name + psaux.c + MacOS + + + Name + ftcache.c + MacOS + + + Name + ftglyph.c + MacOS + + + Name + type1.c + MacOS + + + Name + pshinter.c + MacOS + + + Name + pcf.c + MacOS + + + Name + ftraster.c + MacOS + + + Name + ftrend1.c + MacOS + + + + + + + FreeTypeLib + + + + base + + FreeTypeLib + Name + ftbase.c + MacOS + + + FreeTypeLib + Name + ftdebug.c + MacOS + + + FreeTypeLib + Name + ftglyph.c + MacOS + + + FreeTypeLib + Name + ftinit.c + MacOS + + + FreeTypeLib + Name + ftsystem.c + MacOS + + + FreeTypeLib + Name + ftmac.c + MacOS + + + ftmodules + + FreeTypeLib + Name + cff.c + MacOS + + + FreeTypeLib + Name + ftcache.c + MacOS + + + FreeTypeLib + Name + psaux.c + MacOS + + + FreeTypeLib + Name + psnames.c + MacOS + + + FreeTypeLib + Name + sfnt.c + MacOS + + + FreeTypeLib + Name + smooth.c + MacOS + + + FreeTypeLib + Name + truetype.c + MacOS + + + FreeTypeLib + Name + type1cid.c + MacOS + + + FreeTypeLib + Name + winfnt.c + MacOS + + + FreeTypeLib + Name + type1.c + MacOS + + + FreeTypeLib + Name + pshinter.c + MacOS + + + FreeTypeLib + Name + pcf.c + MacOS + + + FreeTypeLib + Name + ftraster.c + MacOS + + + FreeTypeLib + Name + ftrend1.c + MacOS + + + + + diff --git a/3rdparty/freetype-2.13.2/builds/mac/ftmac.c b/3rdparty/freetype-2.13.2/builds/mac/ftmac.c new file mode 100644 index 000000000..8fe556593 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/mac/ftmac.c @@ -0,0 +1,1542 @@ +/***************************************************************************/ +/* */ +/* ftmac.c */ +/* */ +/* Mac FOND support. Written by just@letterror.com. */ +/* Heavily Fixed by mpsuzuki, George Williams and Sean McBride */ +/* */ +/* Copyright (C) 1996-2023 by */ +/* Just van Rossum, David Turner, Robert Wilhelm, and Werner Lemberg. */ +/* */ +/* This file is part of the FreeType project, and may only be used, */ +/* modified, and distributed under the terms of the FreeType project */ +/* license, LICENSE.TXT. By continuing to use, modify, or distribute */ +/* this file you indicate that you have read the license and */ +/* understand and accept it fully. */ +/* */ +/***************************************************************************/ + + + /* + Notes + + Mac suitcase files can (and often do!) contain multiple fonts. To + support this I use the face_index argument of FT_(Open|New)_Face() + functions, and pretend the suitcase file is a collection. + + Warning: fbit and NFNT bitmap resources are not supported yet. In old + sfnt fonts, bitmap glyph data for each size is stored in each `NFNT' + resources instead of the `bdat' table in the sfnt resource. Therefore, + face->num_fixed_sizes is set to 0, because bitmap data in `NFNT' + resource is unavailable at present. + + The Mac FOND support works roughly like this: + + - Check whether the offered stream points to a Mac suitcase file. This + is done by checking the file type: it has to be 'FFIL' or 'tfil'. The + stream that gets passed to our init_face() routine is a stdio stream, + which isn't usable for us, since the FOND resources live in the + resource fork. So we just grab the stream->pathname field. + + - Read the FOND resource into memory, then check whether there is a + TrueType font and/or(!) a Type 1 font available. + + - If there is a Type 1 font available (as a separate `LWFN' file), read + its data into memory, massage it slightly so it becomes PFB data, wrap + it into a memory stream, load the Type 1 driver and delegate the rest + of the work to it by calling FT_Open_Face(). (XXX TODO: after this + has been done, the kerning data from the FOND resource should be + appended to the face: On the Mac there are usually no AFM files + available. However, this is tricky since we need to map Mac char + codes to ps glyph names to glyph ID's...) + + - If there is a TrueType font (an `sfnt' resource), read it into memory, + wrap it into a memory stream, load the TrueType driver and delegate + the rest of the work to it, by calling FT_Open_Face(). + + - Some suitcase fonts (notably Onyx) might point the `LWFN' file to + itself, even though it doesn't contains `POST' resources. To handle + this special case without opening the file an extra time, we just + ignore errors from the `LWFN' and fallback to the `sfnt' if both are + available. + */ + + +#include +#include +#include +#include "ftbase.h" + +#if defined( __GNUC__ ) || defined( __IBMC__ ) + /* This is for Mac OS X. Without redefinition, OS_INLINE */ + /* expands to `static inline' which doesn't survive the */ + /* -ansi compilation flag of GCC. */ +#if !HAVE_ANSI_OS_INLINE +#undef OS_INLINE +#define OS_INLINE static __inline__ +#endif +#include +#include +#include /* PATH_MAX */ +#else +#include +#include +#include +#include +#include +#include +#endif + +#ifndef PATH_MAX +#define PATH_MAX 1024 /* same with Mac OS X's syslimits.h */ +#endif + +#if defined( __MWERKS__ ) && !TARGET_RT_MAC_MACHO +#include +#endif + +#define FT_DEPRECATED_ATTRIBUTE + +#include + + /* undefine blocking-macros in ftmac.h */ +#undef FT_GetFile_From_Mac_Name +#undef FT_GetFile_From_Mac_ATS_Name +#undef FT_New_Face_From_FOND +#undef FT_New_Face_From_FSSpec +#undef FT_New_Face_From_FSRef + + + /* FSSpec functions are deprecated since Mac OS X 10.4 */ +#ifndef HAVE_FSSPEC +#if TARGET_API_MAC_OS8 || TARGET_API_MAC_CARBON +#define HAVE_FSSPEC 1 +#else +#define HAVE_FSSPEC 0 +#endif +#endif + + /* most FSRef functions were introduced since Mac OS 9 */ +#ifndef HAVE_FSREF +#if TARGET_API_MAC_OSX +#define HAVE_FSREF 1 +#else +#define HAVE_FSREF 0 +#endif +#endif + + /* QuickDraw is deprecated since Mac OS X 10.4 */ +#ifndef HAVE_QUICKDRAW_CARBON +#if TARGET_API_MAC_OS8 || TARGET_API_MAC_CARBON +#define HAVE_QUICKDRAW_CARBON 1 +#else +#define HAVE_QUICKDRAW_CARBON 0 +#endif +#endif + + /* AppleTypeService is available since Mac OS X */ +#ifndef HAVE_ATS +#if TARGET_API_MAC_OSX +#define HAVE_ATS 1 +#ifndef kATSOptionFlagsUnRestrictedScope /* since Mac OS X 10.1 */ +#define kATSOptionFlagsUnRestrictedScope kATSOptionFlagsDefault +#endif +#else +#define HAVE_ATS 0 +#endif +#endif + + /* `configure' checks the availability of `ResourceIndex' strictly */ + /* and sets HAVE_TYPE_RESOURCE_INDEX to 1 or 0 always. If it is */ + /* not set (e.g., a build without `configure'), the availability */ + /* is guessed from the SDK version. */ +#ifndef HAVE_TYPE_RESOURCE_INDEX +#if !defined( MAC_OS_X_VERSION_10_5 ) || \ + ( MAC_OS_X_VERSION_MAX_ALLOWED < MAC_OS_X_VERSION_10_5 ) +#define HAVE_TYPE_RESOURCE_INDEX 0 +#else +#define HAVE_TYPE_RESOURCE_INDEX 1 +#endif +#endif /* !HAVE_TYPE_RESOURCE_INDEX */ + +#if ( HAVE_TYPE_RESOURCE_INDEX == 0 ) +typedef short ResourceIndex; +#endif + + /* Set PREFER_LWFN to 1 if LWFN (Type 1) is preferred over + TrueType in case *both* are available (this is not common, + but it *is* possible). */ +#ifndef PREFER_LWFN +#define PREFER_LWFN 1 +#endif + +#ifdef FT_MACINTOSH + +#if !HAVE_QUICKDRAW_CARBON /* QuickDraw is deprecated since Mac OS X 10.4 */ + + FT_EXPORT_DEF( FT_Error ) + FT_GetFile_From_Mac_Name( const char* fontName, + FSSpec* pathSpec, + FT_Long* face_index ) + { + FT_UNUSED( fontName ); + FT_UNUSED( pathSpec ); + FT_UNUSED( face_index ); + + return FT_THROW( Unimplemented_Feature ); + } + +#else + + FT_EXPORT_DEF( FT_Error ) + FT_GetFile_From_Mac_Name( const char* fontName, + FSSpec* pathSpec, + FT_Long* face_index ) + { + OptionBits options = kFMUseGlobalScopeOption; + + FMFontFamilyIterator famIter; + OSStatus status = FMCreateFontFamilyIterator( NULL, NULL, + options, + &famIter ); + FMFont the_font = 0; + FMFontFamily family = 0; + + + if ( !fontName || !face_index ) + return FT_THROW( Invalid_Argument ); + + *face_index = 0; + while ( status == 0 && !the_font ) + { + status = FMGetNextFontFamily( &famIter, &family ); + if ( status == 0 ) + { + int stat2; + FMFontFamilyInstanceIterator instIter; + Str255 famNameStr; + char famName[256]; + + + /* get the family name */ + FMGetFontFamilyName( family, famNameStr ); + CopyPascalStringToC( famNameStr, famName ); + + /* iterate through the styles */ + FMCreateFontFamilyInstanceIterator( family, &instIter ); + + *face_index = 0; + stat2 = 0; + + while ( stat2 == 0 && !the_font ) + { + FMFontStyle style; + FMFontSize size; + FMFont font; + + + stat2 = FMGetNextFontFamilyInstance( &instIter, &font, + &style, &size ); + if ( stat2 == 0 && size == 0 ) + { + char fullName[256]; + + + /* build up a complete face name */ + ft_strcpy( fullName, famName ); + if ( style & bold ) + ft_strcat( fullName, " Bold" ); + if ( style & italic ) + ft_strcat( fullName, " Italic" ); + + /* compare with the name we are looking for */ + if ( ft_strcmp( fullName, fontName ) == 0 ) + { + /* found it! */ + the_font = font; + } + else + ++(*face_index); + } + } + + FMDisposeFontFamilyInstanceIterator( &instIter ); + } + } + + FMDisposeFontFamilyIterator( &famIter ); + + if ( the_font ) + { + FMGetFontContainer( the_font, pathSpec ); + return FT_Err_Ok; + } + else + return FT_THROW( Unknown_File_Format ); + } + +#endif /* HAVE_QUICKDRAW_CARBON */ + + +#if HAVE_ATS + + /* Private function. */ + /* The FSSpec type has been discouraged for a long time, */ + /* unfortunately an FSRef replacement API for */ + /* ATSFontGetFileSpecification() is only available in */ + /* Mac OS X 10.5 and later. */ + static OSStatus + FT_ATSFontGetFileReference( ATSFontRef ats_font_id, + FSRef* ats_font_ref ) + { + OSStatus err; + +#if !defined( MAC_OS_X_VERSION_10_5 ) || \ + MAC_OS_X_VERSION_MIN_REQUIRED < MAC_OS_X_VERSION_10_5 + FSSpec spec; + + + err = ATSFontGetFileSpecification( ats_font_id, &spec ); + if ( noErr == err ) + err = FSpMakeFSRef( &spec, ats_font_ref ); +#else + err = ATSFontGetFileReference( ats_font_id, ats_font_ref ); +#endif + + return err; + } + + + static FT_Error + FT_GetFileRef_From_Mac_ATS_Name( const char* fontName, + FSRef* ats_font_ref, + FT_Long* face_index ) + { + CFStringRef cf_fontName; + ATSFontRef ats_font_id; + + + *face_index = 0; + + cf_fontName = CFStringCreateWithCString( NULL, fontName, + kCFStringEncodingMacRoman ); + ats_font_id = ATSFontFindFromName( cf_fontName, + kATSOptionFlagsUnRestrictedScope ); + CFRelease( cf_fontName ); + + if ( ats_font_id == 0 || ats_font_id == 0xFFFFFFFFUL ) + return FT_THROW( Unknown_File_Format ); + + if ( noErr != FT_ATSFontGetFileReference( ats_font_id, ats_font_ref ) ) + return FT_THROW( Unknown_File_Format ); + + /* face_index calculation by searching preceding fontIDs */ + /* with same FSRef */ + { + ATSFontRef id2 = ats_font_id - 1; + FSRef ref2; + + + while ( id2 > 0 ) + { + if ( noErr != FT_ATSFontGetFileReference( id2, &ref2 ) ) + break; + if ( noErr != FSCompareFSRefs( ats_font_ref, &ref2 ) ) + break; + + id2--; + } + *face_index = ats_font_id - ( id2 + 1 ); + } + + return FT_Err_Ok; + } + +#endif + +#if !HAVE_ATS + + FT_EXPORT_DEF( FT_Error ) + FT_GetFilePath_From_Mac_ATS_Name( const char* fontName, + UInt8* path, + UInt32 maxPathSize, + FT_Long* face_index ) + { + FT_UNUSED( fontName ); + FT_UNUSED( path ); + FT_UNUSED( maxPathSize ); + FT_UNUSED( face_index ); + + return FT_THROW( Unimplemented_Feature ); + } + +#else + + FT_EXPORT_DEF( FT_Error ) + FT_GetFilePath_From_Mac_ATS_Name( const char* fontName, + UInt8* path, + UInt32 maxPathSize, + FT_Long* face_index ) + { + FSRef ref; + FT_Error err; + + + err = FT_GetFileRef_From_Mac_ATS_Name( fontName, &ref, face_index ); + if ( err ) + return err; + + if ( noErr != FSRefMakePath( &ref, path, maxPathSize ) ) + return FT_THROW( Unknown_File_Format ); + + return FT_Err_Ok; + } + +#endif /* HAVE_ATS */ + + +#if !HAVE_FSSPEC || !HAVE_ATS + + FT_EXPORT_DEF( FT_Error ) + FT_GetFile_From_Mac_ATS_Name( const char* fontName, + FSSpec* pathSpec, + FT_Long* face_index ) + { + FT_UNUSED( fontName ); + FT_UNUSED( pathSpec ); + FT_UNUSED( face_index ); + + return FT_THROW( Unimplemented_Feature ); + } + +#else + + /* This function is deprecated because FSSpec is deprecated in Mac OS X. */ + FT_EXPORT_DEF( FT_Error ) + FT_GetFile_From_Mac_ATS_Name( const char* fontName, + FSSpec* pathSpec, + FT_Long* face_index ) + { + FSRef ref; + FT_Error err; + + + err = FT_GetFileRef_From_Mac_ATS_Name( fontName, &ref, face_index ); + if ( err ) + return err; + + if ( noErr != FSGetCatalogInfo( &ref, kFSCatInfoNone, NULL, NULL, + pathSpec, NULL ) ) + return FT_THROW( Unknown_File_Format ); + + return FT_Err_Ok; + } + +#endif + + +#if defined( __MWERKS__ ) && !TARGET_RT_MAC_MACHO + +#define STREAM_FILE( stream ) ( (FT_FILE*)stream->descriptor.pointer ) + + + FT_CALLBACK_DEF( void ) + ft_FSp_stream_close( FT_Stream stream ) + { + ft_fclose( STREAM_FILE( stream ) ); + + stream->descriptor.pointer = NULL; + stream->size = 0; + stream->base = NULL; + } + + + FT_CALLBACK_DEF( unsigned long ) + ft_FSp_stream_io( FT_Stream stream, + unsigned long offset, + unsigned char* buffer, + unsigned long count ) + { + FT_FILE* file; + + + file = STREAM_FILE( stream ); + + ft_fseek( file, offset, SEEK_SET ); + + return (unsigned long)ft_fread( buffer, 1, count, file ); + } + +#endif /* __MWERKS__ && !TARGET_RT_MAC_MACHO */ + + +#if HAVE_FSSPEC && !HAVE_FSREF + + /* isDirectory is a dummy to synchronize API with FSPathMakeRef() */ + static OSErr + FT_FSPathMakeSpec( const UInt8* pathname, + FSSpec* spec_p, + Boolean isDirectory ) + { + const char *p, *q; + short vRefNum; + long dirID; + Str255 nodeName; + OSErr err; + FT_UNUSED( isDirectory ); + + + p = q = (const char *)pathname; + dirID = 0; + vRefNum = 0; + + while ( 1 ) + { + int len = ft_strlen( p ); + + + if ( len > 255 ) + len = 255; + + q = p + len; + + if ( q == p ) + return 0; + + if ( 255 < ft_strlen( (char *)pathname ) ) + { + while ( p < q && *q != ':' ) + q--; + } + + if ( p < q ) + *(char *)nodeName = q - p; + else if ( ft_strlen( p ) < 256 ) + *(char *)nodeName = ft_strlen( p ); + else + return errFSNameTooLong; + + ft_strncpy( (char *)nodeName + 1, (char *)p, *(char *)nodeName ); + err = FSMakeFSSpec( vRefNum, dirID, nodeName, spec_p ); + if ( err || '\0' == *q ) + return err; + + vRefNum = spec_p->vRefNum; + dirID = spec_p->parID; + + p = q; + } + } + + + static OSErr + FT_FSpMakePath( const FSSpec* spec_p, + UInt8* path, + UInt32 maxPathSize ) + { + OSErr err; + FSSpec spec = *spec_p; + short vRefNum; + long dirID; + Str255 parDir_name; + + + FT_MEM_SET( path, 0, maxPathSize ); + while ( 1 ) + { + int child_namelen = ft_strlen( (char *)path ); + unsigned char node_namelen = spec.name[0]; + unsigned char* node_name = spec.name + 1; + + + if ( node_namelen + child_namelen > maxPathSize ) + return errFSNameTooLong; + + FT_MEM_MOVE( path + node_namelen + 1, path, child_namelen ); + FT_MEM_COPY( path, node_name, node_namelen ); + if ( child_namelen > 0 ) + path[node_namelen] = ':'; + + vRefNum = spec.vRefNum; + dirID = spec.parID; + parDir_name[0] = '\0'; + err = FSMakeFSSpec( vRefNum, dirID, parDir_name, &spec ); + if ( noErr != err || dirID == spec.parID ) + break; + } + return noErr; + } + +#endif /* HAVE_FSSPEC && !HAVE_FSREF */ + + + static OSErr + FT_FSPathMakeRes( const UInt8* pathname, + ResFileRefNum* res ) + { + +#if HAVE_FSREF + + OSErr err; + FSRef ref; + + + if ( noErr != FSPathMakeRef( pathname, &ref, FALSE ) ) + return FT_THROW( Cannot_Open_Resource ); + + /* at present, no support for dfont format */ + err = FSOpenResourceFile( &ref, 0, NULL, fsRdPerm, res ); + if ( noErr == err ) + return err; + + /* fallback to original resource-fork font */ + *res = FSOpenResFile( &ref, fsRdPerm ); + err = ResError(); + +#else + + OSErr err; + FSSpec spec; + + + if ( noErr != FT_FSPathMakeSpec( pathname, &spec, FALSE ) ) + return FT_THROW( Cannot_Open_Resource ); + + /* at present, no support for dfont format without FSRef */ + /* (see above), try original resource-fork font */ + *res = FSpOpenResFile( &spec, fsRdPerm ); + err = ResError(); + +#endif /* HAVE_FSREF */ + + return err; + } + + + /* Return the file type for given pathname */ + static OSType + get_file_type_from_path( const UInt8* pathname ) + { + +#if HAVE_FSREF + + FSRef ref; + FSCatalogInfo info; + + + if ( noErr != FSPathMakeRef( pathname, &ref, FALSE ) ) + return ( OSType ) 0; + + if ( noErr != FSGetCatalogInfo( &ref, kFSCatInfoFinderInfo, &info, + NULL, NULL, NULL ) ) + return ( OSType ) 0; + + return ((FInfo *)(info.finderInfo))->fdType; + +#else + + FSSpec spec; + FInfo finfo; + + + if ( noErr != FT_FSPathMakeSpec( pathname, &spec, FALSE ) ) + return ( OSType ) 0; + + if ( noErr != FSpGetFInfo( &spec, &finfo ) ) + return ( OSType ) 0; + + return finfo.fdType; + +#endif /* HAVE_FSREF */ + + } + + + /* Given a PostScript font name, create the Macintosh LWFN file name. */ + static void + create_lwfn_name( char* ps_name, + Str255 lwfn_file_name ) + { + int max = 5, count = 0; + FT_Byte* p = lwfn_file_name; + FT_Byte* q = (FT_Byte*)ps_name; + + + lwfn_file_name[0] = 0; + + while ( *q ) + { + if ( ft_isupper( *q ) ) + { + if ( count ) + max = 3; + count = 0; + } + if ( count < max && ( ft_isalnum( *q ) || *q == '_' ) ) + { + *++p = *q; + lwfn_file_name[0]++; + count++; + } + q++; + } + } + + + static short + count_faces_sfnt( char* fond_data ) + { + /* The count is 1 greater than the value in the FOND. */ + /* Isn't that cute? :-) */ + + return EndianS16_BtoN( *( (short*)( fond_data + + sizeof ( FamRec ) ) ) ) + 1; + } + + + static short + count_faces_scalable( char* fond_data ) + { + AsscEntry* assoc; + short i, face, face_all; + + + face_all = EndianS16_BtoN( *( (short *)( fond_data + + sizeof ( FamRec ) ) ) ) + 1; + assoc = (AsscEntry*)( fond_data + sizeof ( FamRec ) + 2 ); + face = 0; + + for ( i = 0; i < face_all; i++ ) + { + if ( 0 == EndianS16_BtoN( assoc[i].fontSize ) ) + face++; + } + return face; + } + + + /* Look inside the FOND data, answer whether there should be an SFNT + resource, and answer the name of a possible LWFN Type 1 file. + + Thanks to Paul Miller (paulm@profoundeffects.com) for the fix + to load a face OTHER than the first one in the FOND! + */ + + static void + parse_fond( char* fond_data, + short* have_sfnt, + ResID* sfnt_id, + Str255 lwfn_file_name, + short face_index ) + { + AsscEntry* assoc; + AsscEntry* base_assoc; + FamRec* fond; + + + *sfnt_id = 0; + *have_sfnt = 0; + lwfn_file_name[0] = 0; + + fond = (FamRec*)fond_data; + assoc = (AsscEntry*)( fond_data + sizeof ( FamRec ) + 2 ); + base_assoc = assoc; + + /* the maximum faces in a FOND is 48, size of StyleTable.indexes[] */ + if ( 47 < face_index ) + return; + + /* Let's do a little range checking before we get too excited here */ + if ( face_index < count_faces_sfnt( fond_data ) ) + { + assoc += face_index; /* add on the face_index! */ + + /* if the face at this index is not scalable, + fall back to the first one (old behavior) */ + if ( EndianS16_BtoN( assoc->fontSize ) == 0 ) + { + *have_sfnt = 1; + *sfnt_id = EndianS16_BtoN( assoc->fontID ); + } + else if ( base_assoc->fontSize == 0 ) + { + *have_sfnt = 1; + *sfnt_id = EndianS16_BtoN( base_assoc->fontID ); + } + } + + if ( EndianS32_BtoN( fond->ffStylOff ) ) + { + unsigned char* p = (unsigned char*)fond_data; + StyleTable* style; + unsigned short string_count; + char ps_name[256]; + unsigned char* names[64]; + int i; + + + p += EndianS32_BtoN( fond->ffStylOff ); + style = (StyleTable*)p; + p += sizeof ( StyleTable ); + string_count = EndianS16_BtoN( *(short*)(p) ); + string_count = FT_MIN( 64, string_count ); + p += sizeof ( short ); + + for ( i = 0; i < string_count; i++ ) + { + names[i] = p; + p += names[i][0]; + p++; + } + + { + size_t ps_name_len = (size_t)names[0][0]; + + + if ( ps_name_len != 0 ) + { + ft_memcpy(ps_name, names[0] + 1, ps_name_len); + ps_name[ps_name_len] = 0; + } + if ( style->indexes[face_index] > 1 && + style->indexes[face_index] <= string_count ) + { + unsigned char* suffixes = names[style->indexes[face_index] - 1]; + + + for ( i = 1; i <= suffixes[0]; i++ ) + { + unsigned char* s; + size_t j = suffixes[i] - 1; + + + if ( j < string_count && ( s = names[j] ) != NULL ) + { + size_t s_len = (size_t)s[0]; + + + if ( s_len != 0 && ps_name_len + s_len < sizeof ( ps_name ) ) + { + ft_memcpy( ps_name + ps_name_len, s + 1, s_len ); + ps_name_len += s_len; + ps_name[ps_name_len] = 0; + } + } + } + } + } + + create_lwfn_name( ps_name, lwfn_file_name ); + } + } + + + static FT_Error + lookup_lwfn_by_fond( const UInt8* path_fond, + ConstStr255Param base_lwfn, + UInt8* path_lwfn, + int path_size ) + { + +#if HAVE_FSREF + + FSRef ref, par_ref; + int dirname_len; + + + /* Pathname for FSRef can be in various formats: HFS, HFS+, and POSIX. */ + /* We should not extract parent directory by string manipulation. */ + + if ( noErr != FSPathMakeRef( path_fond, &ref, FALSE ) ) + return FT_THROW( Invalid_Argument ); + + if ( noErr != FSGetCatalogInfo( &ref, kFSCatInfoNone, + NULL, NULL, NULL, &par_ref ) ) + return FT_THROW( Invalid_Argument ); + + if ( noErr != FSRefMakePath( &par_ref, path_lwfn, path_size ) ) + return FT_THROW( Invalid_Argument ); + + if ( ft_strlen( (char *)path_lwfn ) + 1 + base_lwfn[0] > path_size ) + return FT_THROW( Invalid_Argument ); + + /* now we have absolute dirname in path_lwfn */ + if ( path_lwfn[0] == '/' ) + ft_strcat( (char *)path_lwfn, "/" ); + else + ft_strcat( (char *)path_lwfn, ":" ); + + dirname_len = ft_strlen( (char *)path_lwfn ); + ft_strcat( (char *)path_lwfn, (char *)base_lwfn + 1 ); + path_lwfn[dirname_len + base_lwfn[0]] = '\0'; + + if ( noErr != FSPathMakeRef( path_lwfn, &ref, FALSE ) ) + return FT_THROW( Cannot_Open_Resource ); + + if ( noErr != FSGetCatalogInfo( &ref, kFSCatInfoNone, + NULL, NULL, NULL, NULL ) ) + return FT_THROW( Cannot_Open_Resource ); + + return FT_Err_Ok; + +#else + + int i; + FSSpec spec; + + + /* pathname for FSSpec is always HFS format */ + if ( ft_strlen( (char *)path_fond ) > path_size ) + return FT_THROW( Invalid_Argument ); + + ft_strcpy( (char *)path_lwfn, (char *)path_fond ); + + i = ft_strlen( (char *)path_lwfn ) - 1; + while ( i > 0 && ':' != path_lwfn[i] ) + i--; + + if ( i + 1 + base_lwfn[0] > path_size ) + return FT_THROW( Invalid_Argument ); + + if ( ':' == path_lwfn[i] ) + { + ft_strcpy( (char *)path_lwfn + i + 1, (char *)base_lwfn + 1 ); + path_lwfn[i + 1 + base_lwfn[0]] = '\0'; + } + else + { + ft_strcpy( (char *)path_lwfn, (char *)base_lwfn + 1 ); + path_lwfn[base_lwfn[0]] = '\0'; + } + + if ( noErr != FT_FSPathMakeSpec( path_lwfn, &spec, FALSE ) ) + return FT_THROW( Cannot_Open_Resource ); + + return FT_Err_Ok; + +#endif /* HAVE_FSREF */ + + } + + + static short + count_faces( Handle fond, + const UInt8* pathname ) + { + ResID sfnt_id; + short have_sfnt, have_lwfn; + Str255 lwfn_file_name; + UInt8 buff[PATH_MAX]; + FT_Error err; + short num_faces; + + + have_sfnt = have_lwfn = 0; + + HLock( fond ); + parse_fond( *fond, &have_sfnt, &sfnt_id, lwfn_file_name, 0 ); + + if ( lwfn_file_name[0] ) + { + err = lookup_lwfn_by_fond( pathname, lwfn_file_name, + buff, sizeof ( buff ) ); + if ( !err ) + have_lwfn = 1; + } + + if ( have_lwfn && ( !have_sfnt || PREFER_LWFN ) ) + num_faces = 1; + else + num_faces = count_faces_scalable( *fond ); + + HUnlock( fond ); + return num_faces; + } + + + /* Read Type 1 data from the POST resources inside the LWFN file, + return a PFB buffer. This is somewhat convoluted because the FT2 + PFB parser wants the ASCII header as one chunk, and the LWFN + chunks are often not organized that way, so we glue chunks + of the same type together. */ + static FT_Error + read_lwfn( FT_Memory memory, + ResFileRefNum res, + FT_Byte** pfb_data, + FT_ULong* size ) + { + FT_Error error = FT_Err_Ok; + ResID res_id; + unsigned char *buffer, *p, *size_p = NULL; + FT_ULong total_size = 0; + FT_ULong old_total_size = 0; + FT_ULong post_size, pfb_chunk_size; + Handle post_data; + char code, last_code; + + + UseResFile( res ); + + /* First pass: load all POST resources, and determine the size of */ + /* the output buffer. */ + res_id = 501; + last_code = -1; + + for (;;) + { + post_data = Get1Resource( TTAG_POST, res_id++ ); + if ( post_data == NULL ) + break; /* we are done */ + + code = (*post_data)[0]; + + if ( code != last_code ) + { + if ( code == 5 ) + total_size += 2; /* just the end code */ + else + total_size += 6; /* code + 4 bytes chunk length */ + } + + total_size += GetHandleSize( post_data ) - 2; + last_code = code; + + /* detect integer overflows */ + if ( total_size < old_total_size ) + { + error = FT_ERR( Array_Too_Large ); + goto Error; + } + + old_total_size = total_size; + } + + if ( FT_QALLOC( buffer, (FT_Long)total_size ) ) + goto Error; + + /* Second pass: append all POST data to the buffer, add PFB fields. */ + /* Glue all consecutive chunks of the same type together. */ + p = buffer; + res_id = 501; + last_code = -1; + pfb_chunk_size = 0; + + for (;;) + { + post_data = Get1Resource( TTAG_POST, res_id++ ); + if ( post_data == NULL ) + break; /* we are done */ + + post_size = (FT_ULong)GetHandleSize( post_data ) - 2; + code = (*post_data)[0]; + + if ( code != last_code ) + { + if ( last_code != -1 ) + { + /* we are done adding a chunk, fill in the size field */ + if ( size_p != NULL ) + { + *size_p++ = (FT_Byte)( pfb_chunk_size & 0xFF ); + *size_p++ = (FT_Byte)( ( pfb_chunk_size >> 8 ) & 0xFF ); + *size_p++ = (FT_Byte)( ( pfb_chunk_size >> 16 ) & 0xFF ); + *size_p++ = (FT_Byte)( ( pfb_chunk_size >> 24 ) & 0xFF ); + } + pfb_chunk_size = 0; + } + + *p++ = 0x80; + if ( code == 5 ) + *p++ = 0x03; /* the end */ + else if ( code == 2 ) + *p++ = 0x02; /* binary segment */ + else + *p++ = 0x01; /* ASCII segment */ + + if ( code != 5 ) + { + size_p = p; /* save for later */ + p += 4; /* make space for size field */ + } + } + + ft_memcpy( p, *post_data + 2, post_size ); + pfb_chunk_size += post_size; + p += post_size; + last_code = code; + } + + *pfb_data = buffer; + *size = total_size; + + Error: + CloseResFile( res ); + return error; + } + + + /* Create a new FT_Face from a file spec to an LWFN file. */ + static FT_Error + FT_New_Face_From_LWFN( FT_Library library, + const UInt8* pathname, + FT_Long face_index, + FT_Face* aface ) + { + FT_Byte* pfb_data; + FT_ULong pfb_size; + FT_Error error; + ResFileRefNum res; + + + if ( noErr != FT_FSPathMakeRes( pathname, &res ) ) + return FT_THROW( Cannot_Open_Resource ); + + pfb_data = NULL; + pfb_size = 0; + error = read_lwfn( library->memory, res, &pfb_data, &pfb_size ); + CloseResFile( res ); /* PFB is already loaded, useless anymore */ + if ( error ) + return error; + + return open_face_from_buffer( library, + pfb_data, + pfb_size, + face_index, + "type1", + aface ); + } + + + /* Create a new FT_Face from an SFNT resource, specified by res ID. */ + static FT_Error + FT_New_Face_From_SFNT( FT_Library library, + ResID sfnt_id, + FT_Long face_index, + FT_Face* aface ) + { + Handle sfnt = NULL; + FT_Byte* sfnt_data; + size_t sfnt_size; + FT_Error error = FT_Err_Ok; + FT_Memory memory = library->memory; + int is_cff, is_sfnt_ps; + + + sfnt = GetResource( TTAG_sfnt, sfnt_id ); + if ( sfnt == NULL ) + return FT_THROW( Invalid_Handle ); + + sfnt_size = (FT_ULong)GetHandleSize( sfnt ); + if ( FT_QALLOC( sfnt_data, (FT_Long)sfnt_size ) ) + { + ReleaseResource( sfnt ); + return error; + } + + HLock( sfnt ); + ft_memcpy( sfnt_data, *sfnt, sfnt_size ); + HUnlock( sfnt ); + ReleaseResource( sfnt ); + + is_cff = sfnt_size > 4 && !ft_memcmp( sfnt_data, "OTTO", 4 ); + is_sfnt_ps = sfnt_size > 4 && !ft_memcmp( sfnt_data, "typ1", 4 ); + + if ( is_sfnt_ps ) + { + FT_Stream stream; + + + if ( FT_NEW( stream ) ) + goto Try_OpenType; + + FT_Stream_OpenMemory( stream, sfnt_data, sfnt_size ); + if ( !open_face_PS_from_sfnt_stream( library, + stream, + face_index, + 0, NULL, + aface ) ) + { + FT_Stream_Close( stream ); + FT_FREE( stream ); + FT_FREE( sfnt_data ); + goto Exit; + } + + FT_FREE( stream ); + } + Try_OpenType: + error = open_face_from_buffer( library, + sfnt_data, + sfnt_size, + face_index, + is_cff ? "cff" : "truetype", + aface ); + Exit: + return error; + } + + + /* Create a new FT_Face from a file spec to a suitcase file. */ + static FT_Error + FT_New_Face_From_Suitcase( FT_Library library, + const UInt8* pathname, + FT_Long face_index, + FT_Face* aface ) + { + FT_Error error = FT_ERR( Cannot_Open_Resource ); + ResFileRefNum res_ref; + ResourceIndex res_index; + Handle fond; + short num_faces_in_res; + + + if ( noErr != FT_FSPathMakeRes( pathname, &res_ref ) ) + return FT_THROW( Cannot_Open_Resource ); + + UseResFile( res_ref ); + if ( ResError() ) + return FT_THROW( Cannot_Open_Resource ); + + num_faces_in_res = 0; + for ( res_index = 1; ; ++res_index ) + { + short num_faces_in_fond; + + + fond = Get1IndResource( TTAG_FOND, res_index ); + if ( ResError() ) + break; + + num_faces_in_fond = count_faces( fond, pathname ); + num_faces_in_res += num_faces_in_fond; + + if ( 0 <= face_index && face_index < num_faces_in_fond && error ) + error = FT_New_Face_From_FOND( library, fond, face_index, aface ); + + face_index -= num_faces_in_fond; + } + + CloseResFile( res_ref ); + if ( !error && aface ) + (*aface)->num_faces = num_faces_in_res; + return error; + } + + + /* documentation is in ftmac.h */ + + FT_EXPORT_DEF( FT_Error ) + FT_New_Face_From_FOND( FT_Library library, + Handle fond, + FT_Long face_index, + FT_Face* aface ) + { + short have_sfnt, have_lwfn = 0; + ResID sfnt_id, fond_id; + OSType fond_type; + Str255 fond_name; + Str255 lwfn_file_name; + UInt8 path_lwfn[PATH_MAX]; + OSErr err; + FT_Error error = FT_Err_Ok; + + + /* test for valid `aface' and `library' delayed to */ + /* `FT_New_Face_From_XXX' */ + + GetResInfo( fond, &fond_id, &fond_type, fond_name ); + if ( ResError() != noErr || fond_type != TTAG_FOND ) + return FT_THROW( Invalid_File_Format ); + + HLock( fond ); + parse_fond( *fond, &have_sfnt, &sfnt_id, lwfn_file_name, face_index ); + HUnlock( fond ); + + if ( lwfn_file_name[0] ) + { + ResFileRefNum res; + + + res = HomeResFile( fond ); + if ( noErr != ResError() ) + goto found_no_lwfn_file; + +#if HAVE_FSREF + + { + UInt8 path_fond[PATH_MAX]; + FSRef ref; + + + err = FSGetForkCBInfo( res, kFSInvalidVolumeRefNum, + NULL, NULL, NULL, &ref, NULL ); + if ( noErr != err ) + goto found_no_lwfn_file; + + err = FSRefMakePath( &ref, path_fond, sizeof ( path_fond ) ); + if ( noErr != err ) + goto found_no_lwfn_file; + + error = lookup_lwfn_by_fond( path_fond, lwfn_file_name, + path_lwfn, sizeof ( path_lwfn ) ); + if ( !error ) + have_lwfn = 1; + } + +#elif HAVE_FSSPEC + + { + UInt8 path_fond[PATH_MAX]; + FCBPBRec pb; + Str255 fond_file_name; + FSSpec spec; + + + FT_MEM_SET( &spec, 0, sizeof ( FSSpec ) ); + FT_MEM_SET( &pb, 0, sizeof ( FCBPBRec ) ); + + pb.ioNamePtr = fond_file_name; + pb.ioVRefNum = 0; + pb.ioRefNum = res; + pb.ioFCBIndx = 0; + + err = PBGetFCBInfoSync( &pb ); + if ( noErr != err ) + goto found_no_lwfn_file; + + err = FSMakeFSSpec( pb.ioFCBVRefNum, pb.ioFCBParID, + fond_file_name, &spec ); + if ( noErr != err ) + goto found_no_lwfn_file; + + err = FT_FSpMakePath( &spec, path_fond, sizeof ( path_fond ) ); + if ( noErr != err ) + goto found_no_lwfn_file; + + error = lookup_lwfn_by_fond( path_fond, lwfn_file_name, + path_lwfn, sizeof ( path_lwfn ) ); + if ( !error ) + have_lwfn = 1; + } + +#endif /* HAVE_FSREF, HAVE_FSSPEC */ + + } + + if ( have_lwfn && ( !have_sfnt || PREFER_LWFN ) ) + error = FT_New_Face_From_LWFN( library, + path_lwfn, + face_index, + aface ); + else + error = FT_ERR( Unknown_File_Format ); + + found_no_lwfn_file: + if ( have_sfnt && error ) + error = FT_New_Face_From_SFNT( library, + sfnt_id, + face_index, + aface ); + + return error; + } + + + /* Common function to load a new FT_Face from a resource file. */ + static FT_Error + FT_New_Face_From_Resource( FT_Library library, + const UInt8* pathname, + FT_Long face_index, + FT_Face* aface ) + { + OSType file_type; + FT_Error error; + + + /* LWFN is a (very) specific file format, check for it explicitly */ + file_type = get_file_type_from_path( pathname ); + if ( file_type == TTAG_LWFN ) + return FT_New_Face_From_LWFN( library, pathname, face_index, aface ); + + /* Otherwise the file type doesn't matter (there are more than */ + /* `FFIL' and `tfil'). Just try opening it as a font suitcase; */ + /* if it works, fine. */ + + error = FT_New_Face_From_Suitcase( library, pathname, face_index, aface ); + if ( !error ) + return error; + + /* let it fall through to normal loader (.ttf, .otf, etc.); */ + /* we signal this by returning no error and no FT_Face */ + *aface = NULL; + return 0; + } + + + /*************************************************************************/ + /* */ + /* */ + /* FT_New_Face */ + /* */ + /* */ + /* This is the Mac-specific implementation of FT_New_Face. In */ + /* addition to the standard FT_New_Face() functionality, it also */ + /* accepts pathnames to Mac suitcase files. For further */ + /* documentation see the original FT_New_Face() in freetype.h. */ + /* */ + FT_EXPORT_DEF( FT_Error ) + FT_New_Face( FT_Library library, + const char* pathname, + FT_Long face_index, + FT_Face* aface ) + { + FT_Open_Args args; + FT_Error error; + + + /* test for valid `library' and `aface' delayed to FT_Open_Face() */ + if ( !pathname ) + return FT_THROW( Invalid_Argument ); + + *aface = NULL; + + /* try resourcefork based font: LWFN, FFIL */ + error = FT_New_Face_From_Resource( library, (UInt8 *)pathname, + face_index, aface ); + if ( error || *aface ) + return error; + + /* let it fall through to normal loader (.ttf, .otf, etc.) */ + args.flags = FT_OPEN_PATHNAME; + args.pathname = (char*)pathname; + return FT_Open_Face( library, &args, face_index, aface ); + } + + + /*************************************************************************/ + /* */ + /* */ + /* FT_New_Face_From_FSRef */ + /* */ + /* */ + /* FT_New_Face_From_FSRef is identical to FT_New_Face except it */ + /* accepts an FSRef instead of a path. */ + /* */ + /* This function is deprecated because Carbon data types (FSRef) */ + /* are not cross-platform, and thus not suitable for the FreeType API. */ + FT_EXPORT_DEF( FT_Error ) + FT_New_Face_From_FSRef( FT_Library library, + const FSRef* ref, + FT_Long face_index, + FT_Face* aface ) + { + +#if !HAVE_FSREF + + FT_UNUSED( library ); + FT_UNUSED( ref ); + FT_UNUSED( face_index ); + FT_UNUSED( aface ); + + return FT_THROW( Unimplemented_Feature ); + +#else + + FT_Error error; + FT_Open_Args args; + OSErr err; + UInt8 pathname[PATH_MAX]; + + + /* test for valid `library' and `aface' delayed to `FT_Open_Face' */ + + if ( !ref ) + return FT_THROW( Invalid_Argument ); + + err = FSRefMakePath( ref, pathname, sizeof ( pathname ) ); + if ( err ) + error = FT_ERR( Cannot_Open_Resource ); + + error = FT_New_Face_From_Resource( library, pathname, face_index, aface ); + if ( error || *aface ) + return error; + + /* fallback to datafork font */ + args.flags = FT_OPEN_PATHNAME; + args.pathname = (char*)pathname; + return FT_Open_Face( library, &args, face_index, aface ); + +#endif /* HAVE_FSREF */ + + } + + + /*************************************************************************/ + /* */ + /* */ + /* FT_New_Face_From_FSSpec */ + /* */ + /* */ + /* FT_New_Face_From_FSSpec is identical to FT_New_Face except it */ + /* accepts an FSSpec instead of a path. */ + /* */ + /* This function is deprecated because Carbon data types (FSSpec) */ + /* are not cross-platform, and thus not suitable for the FreeType API. */ + FT_EXPORT_DEF( FT_Error ) + FT_New_Face_From_FSSpec( FT_Library library, + const FSSpec* spec, + FT_Long face_index, + FT_Face* aface ) + { + +#if HAVE_FSREF + + FSRef ref; + + + if ( !spec || FSpMakeFSRef( spec, &ref ) != noErr ) + return FT_THROW( Invalid_Argument ); + else + return FT_New_Face_From_FSRef( library, &ref, face_index, aface ); + +#elif HAVE_FSSPEC + + FT_Error error; + FT_Open_Args args; + OSErr err; + UInt8 pathname[PATH_MAX]; + + + if ( !spec ) + return FT_THROW( Invalid_Argument ); + + err = FT_FSpMakePath( spec, pathname, sizeof ( pathname ) ); + if ( err ) + error = FT_ERR( Cannot_Open_Resource ); + + error = FT_New_Face_From_Resource( library, pathname, face_index, aface ); + if ( error || *aface ) + return error; + + /* fallback to datafork font */ + args.flags = FT_OPEN_PATHNAME; + args.pathname = (char*)pathname; + return FT_Open_Face( library, &args, face_index, aface ); + +#else + + FT_UNUSED( library ); + FT_UNUSED( spec ); + FT_UNUSED( face_index ); + FT_UNUSED( aface ); + + return FT_THROW( Unimplemented_Feature ); + +#endif /* HAVE_FSREF, HAVE_FSSPEC */ + + } + +#endif /* FT_MACINTOSH */ + + +/* END */ diff --git a/3rdparty/freetype-2.13.2/builds/unix/aclocal.m4 b/3rdparty/freetype-2.13.2/builds/unix/aclocal.m4 new file mode 100644 index 000000000..563b92412 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/aclocal.m4 @@ -0,0 +1,9079 @@ +# generated automatically by aclocal 1.16.5 -*- Autoconf -*- + +# Copyright (C) 1996-2021 Free Software Foundation, Inc. + +# This file is free software; the Free Software Foundation +# gives unlimited permission to copy and/or distribute it, +# with or without modifications, as long as this notice is preserved. + +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY, to the extent permitted by law; without +# even the implied warranty of MERCHANTABILITY or FITNESS FOR A +# PARTICULAR PURPOSE. + +m4_ifndef([AC_CONFIG_MACRO_DIRS], [m4_defun([_AM_CONFIG_MACRO_DIRS], [])m4_defun([AC_CONFIG_MACRO_DIRS], [_AM_CONFIG_MACRO_DIRS($@)])]) +# libtool.m4 - Configure libtool for the host system. -*-Autoconf-*- +# +# Copyright (C) 1996-2001, 2003-2019, 2021-2022 Free Software +# Foundation, Inc. +# Written by Gordon Matzigkeit, 1996 +# +# This file is free software; the Free Software Foundation gives +# unlimited permission to copy and/or distribute it, with or without +# modifications, as long as this notice is preserved. + +m4_define([_LT_COPYING], [dnl +# Copyright (C) 2014 Free Software Foundation, Inc. +# This is free software; see the source for copying conditions. There is NO +# warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + +# GNU Libtool is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of of the License, or +# (at your option) any later version. +# +# As a special exception to the GNU General Public License, if you +# distribute this file as part of a program or library that is built +# using GNU Libtool, you may include this file under the same +# distribution terms that you use for the rest of that program. +# +# GNU Libtool is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see . +]) + +# serial 59 LT_INIT + + +# LT_PREREQ(VERSION) +# ------------------ +# Complain and exit if this libtool version is less that VERSION. +m4_defun([LT_PREREQ], +[m4_if(m4_version_compare(m4_defn([LT_PACKAGE_VERSION]), [$1]), -1, + [m4_default([$3], + [m4_fatal([Libtool version $1 or higher is required], + 63)])], + [$2])]) + + +# _LT_CHECK_BUILDDIR +# ------------------ +# Complain if the absolute build directory name contains unusual characters +m4_defun([_LT_CHECK_BUILDDIR], +[case `pwd` in + *\ * | *\ *) + AC_MSG_WARN([Libtool does not cope well with whitespace in `pwd`]) ;; +esac +]) + + +# LT_INIT([OPTIONS]) +# ------------------ +AC_DEFUN([LT_INIT], +[AC_PREREQ([2.62])dnl We use AC_PATH_PROGS_FEATURE_CHECK +AC_REQUIRE([AC_CONFIG_AUX_DIR_DEFAULT])dnl +AC_BEFORE([$0], [LT_LANG])dnl +AC_BEFORE([$0], [LT_OUTPUT])dnl +AC_BEFORE([$0], [LTDL_INIT])dnl +m4_require([_LT_CHECK_BUILDDIR])dnl + +dnl Autoconf doesn't catch unexpanded LT_ macros by default: +m4_pattern_forbid([^_?LT_[A-Z_]+$])dnl +m4_pattern_allow([^(_LT_EOF|LT_DLGLOBAL|LT_DLLAZY_OR_NOW|LT_MULTI_MODULE)$])dnl +dnl aclocal doesn't pull ltoptions.m4, ltsugar.m4, or ltversion.m4 +dnl unless we require an AC_DEFUNed macro: +AC_REQUIRE([LTOPTIONS_VERSION])dnl +AC_REQUIRE([LTSUGAR_VERSION])dnl +AC_REQUIRE([LTVERSION_VERSION])dnl +AC_REQUIRE([LTOBSOLETE_VERSION])dnl +m4_require([_LT_PROG_LTMAIN])dnl + +_LT_SHELL_INIT([SHELL=${CONFIG_SHELL-/bin/sh}]) + +dnl Parse OPTIONS +_LT_SET_OPTIONS([$0], [$1]) + +# This can be used to rebuild libtool when needed +LIBTOOL_DEPS=$ltmain + +# Always use our own libtool. +LIBTOOL='$(SHELL) $(top_builddir)/libtool' +AC_SUBST(LIBTOOL)dnl + +_LT_SETUP + +# Only expand once: +m4_define([LT_INIT]) +])# LT_INIT + +# Old names: +AU_ALIAS([AC_PROG_LIBTOOL], [LT_INIT]) +AU_ALIAS([AM_PROG_LIBTOOL], [LT_INIT]) +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([AC_PROG_LIBTOOL], []) +dnl AC_DEFUN([AM_PROG_LIBTOOL], []) + + +# _LT_PREPARE_CC_BASENAME +# ----------------------- +m4_defun([_LT_PREPARE_CC_BASENAME], [ +# Calculate cc_basename. Skip known compiler wrappers and cross-prefix. +func_cc_basename () +{ + for cc_temp in @S|@*""; do + case $cc_temp in + compile | *[[\\/]]compile | ccache | *[[\\/]]ccache ) ;; + distcc | *[[\\/]]distcc | purify | *[[\\/]]purify ) ;; + \-*) ;; + *) break;; + esac + done + func_cc_basename_result=`$ECHO "$cc_temp" | $SED "s%.*/%%; s%^$host_alias-%%"` +} +])# _LT_PREPARE_CC_BASENAME + + +# _LT_CC_BASENAME(CC) +# ------------------- +# It would be clearer to call AC_REQUIREs from _LT_PREPARE_CC_BASENAME, +# but that macro is also expanded into generated libtool script, which +# arranges for $SED and $ECHO to be set by different means. +m4_defun([_LT_CC_BASENAME], +[m4_require([_LT_PREPARE_CC_BASENAME])dnl +AC_REQUIRE([_LT_DECL_SED])dnl +AC_REQUIRE([_LT_PROG_ECHO_BACKSLASH])dnl +func_cc_basename $1 +cc_basename=$func_cc_basename_result +]) + + +# _LT_FILEUTILS_DEFAULTS +# ---------------------- +# It is okay to use these file commands and assume they have been set +# sensibly after 'm4_require([_LT_FILEUTILS_DEFAULTS])'. +m4_defun([_LT_FILEUTILS_DEFAULTS], +[: ${CP="cp -f"} +: ${MV="mv -f"} +: ${RM="rm -f"} +])# _LT_FILEUTILS_DEFAULTS + + +# _LT_SETUP +# --------- +m4_defun([_LT_SETUP], +[AC_REQUIRE([AC_CANONICAL_HOST])dnl +AC_REQUIRE([AC_CANONICAL_BUILD])dnl +AC_REQUIRE([_LT_PREPARE_SED_QUOTE_VARS])dnl +AC_REQUIRE([_LT_PROG_ECHO_BACKSLASH])dnl + +_LT_DECL([], [PATH_SEPARATOR], [1], [The PATH separator for the build system])dnl +dnl +_LT_DECL([], [host_alias], [0], [The host system])dnl +_LT_DECL([], [host], [0])dnl +_LT_DECL([], [host_os], [0])dnl +dnl +_LT_DECL([], [build_alias], [0], [The build system])dnl +_LT_DECL([], [build], [0])dnl +_LT_DECL([], [build_os], [0])dnl +dnl +AC_REQUIRE([AC_PROG_CC])dnl +AC_REQUIRE([LT_PATH_LD])dnl +AC_REQUIRE([LT_PATH_NM])dnl +dnl +AC_REQUIRE([AC_PROG_LN_S])dnl +test -z "$LN_S" && LN_S="ln -s" +_LT_DECL([], [LN_S], [1], [Whether we need soft or hard links])dnl +dnl +AC_REQUIRE([LT_CMD_MAX_LEN])dnl +_LT_DECL([objext], [ac_objext], [0], [Object file suffix (normally "o")])dnl +_LT_DECL([], [exeext], [0], [Executable file suffix (normally "")])dnl +dnl +m4_require([_LT_FILEUTILS_DEFAULTS])dnl +m4_require([_LT_CHECK_SHELL_FEATURES])dnl +m4_require([_LT_PATH_CONVERSION_FUNCTIONS])dnl +m4_require([_LT_CMD_RELOAD])dnl +m4_require([_LT_DECL_FILECMD])dnl +m4_require([_LT_CHECK_MAGIC_METHOD])dnl +m4_require([_LT_CHECK_SHAREDLIB_FROM_LINKLIB])dnl +m4_require([_LT_CMD_OLD_ARCHIVE])dnl +m4_require([_LT_CMD_GLOBAL_SYMBOLS])dnl +m4_require([_LT_WITH_SYSROOT])dnl +m4_require([_LT_CMD_TRUNCATE])dnl + +_LT_CONFIG_LIBTOOL_INIT([ +# See if we are running on zsh, and set the options that allow our +# commands through without removal of \ escapes INIT. +if test -n "\${ZSH_VERSION+set}"; then + setopt NO_GLOB_SUBST +fi +]) +if test -n "${ZSH_VERSION+set}"; then + setopt NO_GLOB_SUBST +fi + +_LT_CHECK_OBJDIR + +m4_require([_LT_TAG_COMPILER])dnl + +case $host_os in +aix3*) + # AIX sometimes has problems with the GCC collect2 program. For some + # reason, if we set the COLLECT_NAMES environment variable, the problems + # vanish in a puff of smoke. + if test set != "${COLLECT_NAMES+set}"; then + COLLECT_NAMES= + export COLLECT_NAMES + fi + ;; +esac + +# Global variables: +ofile=libtool +can_build_shared=yes + +# All known linkers require a '.a' archive for static linking (except MSVC and +# ICC, which need '.lib'). +libext=a + +with_gnu_ld=$lt_cv_prog_gnu_ld + +old_CC=$CC +old_CFLAGS=$CFLAGS + +# Set sane defaults for various variables +test -z "$CC" && CC=cc +test -z "$LTCC" && LTCC=$CC +test -z "$LTCFLAGS" && LTCFLAGS=$CFLAGS +test -z "$LD" && LD=ld +test -z "$ac_objext" && ac_objext=o + +_LT_CC_BASENAME([$compiler]) + +# Only perform the check for file, if the check method requires it +test -z "$MAGIC_CMD" && MAGIC_CMD=file +case $deplibs_check_method in +file_magic*) + if test "$file_magic_cmd" = '$MAGIC_CMD'; then + _LT_PATH_MAGIC + fi + ;; +esac + +# Use C for the default configuration in the libtool script +LT_SUPPORTED_TAG([CC]) +_LT_LANG_C_CONFIG +_LT_LANG_DEFAULT_CONFIG +_LT_CONFIG_COMMANDS +])# _LT_SETUP + + +# _LT_PREPARE_SED_QUOTE_VARS +# -------------------------- +# Define a few sed substitution that help us do robust quoting. +m4_defun([_LT_PREPARE_SED_QUOTE_VARS], +[# Backslashify metacharacters that are still active within +# double-quoted strings. +sed_quote_subst='s/\([["`$\\]]\)/\\\1/g' + +# Same as above, but do not quote variable references. +double_quote_subst='s/\([["`\\]]\)/\\\1/g' + +# Sed substitution to delay expansion of an escaped shell variable in a +# double_quote_subst'ed string. +delay_variable_subst='s/\\\\\\\\\\\$/\\\\\\$/g' + +# Sed substitution to delay expansion of an escaped single quote. +delay_single_quote_subst='s/'\''/'\'\\\\\\\'\''/g' + +# Sed substitution to avoid accidental globbing in evaled expressions +no_glob_subst='s/\*/\\\*/g' +]) + +# _LT_PROG_LTMAIN +# --------------- +# Note that this code is called both from 'configure', and 'config.status' +# now that we use AC_CONFIG_COMMANDS to generate libtool. Notably, +# 'config.status' has no value for ac_aux_dir unless we are using Automake, +# so we pass a copy along to make sure it has a sensible value anyway. +m4_defun([_LT_PROG_LTMAIN], +[m4_ifdef([AC_REQUIRE_AUX_FILE], [AC_REQUIRE_AUX_FILE([ltmain.sh])])dnl +_LT_CONFIG_LIBTOOL_INIT([ac_aux_dir='$ac_aux_dir']) +ltmain=$ac_aux_dir/ltmain.sh +])# _LT_PROG_LTMAIN + + + +# So that we can recreate a full libtool script including additional +# tags, we accumulate the chunks of code to send to AC_CONFIG_COMMANDS +# in macros and then make a single call at the end using the 'libtool' +# label. + + +# _LT_CONFIG_LIBTOOL_INIT([INIT-COMMANDS]) +# ---------------------------------------- +# Register INIT-COMMANDS to be passed to AC_CONFIG_COMMANDS later. +m4_define([_LT_CONFIG_LIBTOOL_INIT], +[m4_ifval([$1], + [m4_append([_LT_OUTPUT_LIBTOOL_INIT], + [$1 +])])]) + +# Initialize. +m4_define([_LT_OUTPUT_LIBTOOL_INIT]) + + +# _LT_CONFIG_LIBTOOL([COMMANDS]) +# ------------------------------ +# Register COMMANDS to be passed to AC_CONFIG_COMMANDS later. +m4_define([_LT_CONFIG_LIBTOOL], +[m4_ifval([$1], + [m4_append([_LT_OUTPUT_LIBTOOL_COMMANDS], + [$1 +])])]) + +# Initialize. +m4_define([_LT_OUTPUT_LIBTOOL_COMMANDS]) + + +# _LT_CONFIG_SAVE_COMMANDS([COMMANDS], [INIT_COMMANDS]) +# ----------------------------------------------------- +m4_defun([_LT_CONFIG_SAVE_COMMANDS], +[_LT_CONFIG_LIBTOOL([$1]) +_LT_CONFIG_LIBTOOL_INIT([$2]) +]) + + +# _LT_FORMAT_COMMENT([COMMENT]) +# ----------------------------- +# Add leading comment marks to the start of each line, and a trailing +# full-stop to the whole comment if one is not present already. +m4_define([_LT_FORMAT_COMMENT], +[m4_ifval([$1], [ +m4_bpatsubst([m4_bpatsubst([$1], [^ *], [# ])], + [['`$\]], [\\\&])]m4_bmatch([$1], [[!?.]$], [], [.]) +)]) + + + + + +# _LT_DECL([CONFIGNAME], VARNAME, VALUE, [DESCRIPTION], [IS-TAGGED?]) +# ------------------------------------------------------------------- +# CONFIGNAME is the name given to the value in the libtool script. +# VARNAME is the (base) name used in the configure script. +# VALUE may be 0, 1 or 2 for a computed quote escaped value based on +# VARNAME. Any other value will be used directly. +m4_define([_LT_DECL], +[lt_if_append_uniq([lt_decl_varnames], [$2], [, ], + [lt_dict_add_subkey([lt_decl_dict], [$2], [libtool_name], + [m4_ifval([$1], [$1], [$2])]) + lt_dict_add_subkey([lt_decl_dict], [$2], [value], [$3]) + m4_ifval([$4], + [lt_dict_add_subkey([lt_decl_dict], [$2], [description], [$4])]) + lt_dict_add_subkey([lt_decl_dict], [$2], + [tagged?], [m4_ifval([$5], [yes], [no])])]) +]) + + +# _LT_TAGDECL([CONFIGNAME], VARNAME, VALUE, [DESCRIPTION]) +# -------------------------------------------------------- +m4_define([_LT_TAGDECL], [_LT_DECL([$1], [$2], [$3], [$4], [yes])]) + + +# lt_decl_tag_varnames([SEPARATOR], [VARNAME1...]) +# ------------------------------------------------ +m4_define([lt_decl_tag_varnames], +[_lt_decl_filter([tagged?], [yes], $@)]) + + +# _lt_decl_filter(SUBKEY, VALUE, [SEPARATOR], [VARNAME1..]) +# --------------------------------------------------------- +m4_define([_lt_decl_filter], +[m4_case([$#], + [0], [m4_fatal([$0: too few arguments: $#])], + [1], [m4_fatal([$0: too few arguments: $#: $1])], + [2], [lt_dict_filter([lt_decl_dict], [$1], [$2], [], lt_decl_varnames)], + [3], [lt_dict_filter([lt_decl_dict], [$1], [$2], [$3], lt_decl_varnames)], + [lt_dict_filter([lt_decl_dict], $@)])[]dnl +]) + + +# lt_decl_quote_varnames([SEPARATOR], [VARNAME1...]) +# -------------------------------------------------- +m4_define([lt_decl_quote_varnames], +[_lt_decl_filter([value], [1], $@)]) + + +# lt_decl_dquote_varnames([SEPARATOR], [VARNAME1...]) +# --------------------------------------------------- +m4_define([lt_decl_dquote_varnames], +[_lt_decl_filter([value], [2], $@)]) + + +# lt_decl_varnames_tagged([SEPARATOR], [VARNAME1...]) +# --------------------------------------------------- +m4_define([lt_decl_varnames_tagged], +[m4_assert([$# <= 2])dnl +_$0(m4_quote(m4_default([$1], [[, ]])), + m4_ifval([$2], [[$2]], [m4_dquote(lt_decl_tag_varnames)]), + m4_split(m4_normalize(m4_quote(_LT_TAGS)), [ ]))]) +m4_define([_lt_decl_varnames_tagged], +[m4_ifval([$3], [lt_combine([$1], [$2], [_], $3)])]) + + +# lt_decl_all_varnames([SEPARATOR], [VARNAME1...]) +# ------------------------------------------------ +m4_define([lt_decl_all_varnames], +[_$0(m4_quote(m4_default([$1], [[, ]])), + m4_if([$2], [], + m4_quote(lt_decl_varnames), + m4_quote(m4_shift($@))))[]dnl +]) +m4_define([_lt_decl_all_varnames], +[lt_join($@, lt_decl_varnames_tagged([$1], + lt_decl_tag_varnames([[, ]], m4_shift($@))))dnl +]) + + +# _LT_CONFIG_STATUS_DECLARE([VARNAME]) +# ------------------------------------ +# Quote a variable value, and forward it to 'config.status' so that its +# declaration there will have the same value as in 'configure'. VARNAME +# must have a single quote delimited value for this to work. +m4_define([_LT_CONFIG_STATUS_DECLARE], +[$1='`$ECHO "$][$1" | $SED "$delay_single_quote_subst"`']) + + +# _LT_CONFIG_STATUS_DECLARATIONS +# ------------------------------ +# We delimit libtool config variables with single quotes, so when +# we write them to config.status, we have to be sure to quote all +# embedded single quotes properly. In configure, this macro expands +# each variable declared with _LT_DECL (and _LT_TAGDECL) into: +# +# ='`$ECHO "$" | $SED "$delay_single_quote_subst"`' +m4_defun([_LT_CONFIG_STATUS_DECLARATIONS], +[m4_foreach([_lt_var], m4_quote(lt_decl_all_varnames), + [m4_n([_LT_CONFIG_STATUS_DECLARE(_lt_var)])])]) + + +# _LT_LIBTOOL_TAGS +# ---------------- +# Output comment and list of tags supported by the script +m4_defun([_LT_LIBTOOL_TAGS], +[_LT_FORMAT_COMMENT([The names of the tagged configurations supported by this script])dnl +available_tags='_LT_TAGS'dnl +]) + + +# _LT_LIBTOOL_DECLARE(VARNAME, [TAG]) +# ----------------------------------- +# Extract the dictionary values for VARNAME (optionally with TAG) and +# expand to a commented shell variable setting: +# +# # Some comment about what VAR is for. +# visible_name=$lt_internal_name +m4_define([_LT_LIBTOOL_DECLARE], +[_LT_FORMAT_COMMENT(m4_quote(lt_dict_fetch([lt_decl_dict], [$1], + [description])))[]dnl +m4_pushdef([_libtool_name], + m4_quote(lt_dict_fetch([lt_decl_dict], [$1], [libtool_name])))[]dnl +m4_case(m4_quote(lt_dict_fetch([lt_decl_dict], [$1], [value])), + [0], [_libtool_name=[$]$1], + [1], [_libtool_name=$lt_[]$1], + [2], [_libtool_name=$lt_[]$1], + [_libtool_name=lt_dict_fetch([lt_decl_dict], [$1], [value])])[]dnl +m4_ifval([$2], [_$2])[]m4_popdef([_libtool_name])[]dnl +]) + + +# _LT_LIBTOOL_CONFIG_VARS +# ----------------------- +# Produce commented declarations of non-tagged libtool config variables +# suitable for insertion in the LIBTOOL CONFIG section of the 'libtool' +# script. Tagged libtool config variables (even for the LIBTOOL CONFIG +# section) are produced by _LT_LIBTOOL_TAG_VARS. +m4_defun([_LT_LIBTOOL_CONFIG_VARS], +[m4_foreach([_lt_var], + m4_quote(_lt_decl_filter([tagged?], [no], [], lt_decl_varnames)), + [m4_n([_LT_LIBTOOL_DECLARE(_lt_var)])])]) + + +# _LT_LIBTOOL_TAG_VARS(TAG) +# ------------------------- +m4_define([_LT_LIBTOOL_TAG_VARS], +[m4_foreach([_lt_var], m4_quote(lt_decl_tag_varnames), + [m4_n([_LT_LIBTOOL_DECLARE(_lt_var, [$1])])])]) + + +# _LT_TAGVAR(VARNAME, [TAGNAME]) +# ------------------------------ +m4_define([_LT_TAGVAR], [m4_ifval([$2], [$1_$2], [$1])]) + + +# _LT_CONFIG_COMMANDS +# ------------------- +# Send accumulated output to $CONFIG_STATUS. Thanks to the lists of +# variables for single and double quote escaping we saved from calls +# to _LT_DECL, we can put quote escaped variables declarations +# into 'config.status', and then the shell code to quote escape them in +# for loops in 'config.status'. Finally, any additional code accumulated +# from calls to _LT_CONFIG_LIBTOOL_INIT is expanded. +m4_defun([_LT_CONFIG_COMMANDS], +[AC_PROVIDE_IFELSE([LT_OUTPUT], + dnl If the libtool generation code has been placed in $CONFIG_LT, + dnl instead of duplicating it all over again into config.status, + dnl then we will have config.status run $CONFIG_LT later, so it + dnl needs to know what name is stored there: + [AC_CONFIG_COMMANDS([libtool], + [$SHELL $CONFIG_LT || AS_EXIT(1)], [CONFIG_LT='$CONFIG_LT'])], + dnl If the libtool generation code is destined for config.status, + dnl expand the accumulated commands and init code now: + [AC_CONFIG_COMMANDS([libtool], + [_LT_OUTPUT_LIBTOOL_COMMANDS], [_LT_OUTPUT_LIBTOOL_COMMANDS_INIT])]) +])#_LT_CONFIG_COMMANDS + + +# Initialize. +m4_define([_LT_OUTPUT_LIBTOOL_COMMANDS_INIT], +[ + +# The HP-UX ksh and POSIX shell print the target directory to stdout +# if CDPATH is set. +(unset CDPATH) >/dev/null 2>&1 && unset CDPATH + +sed_quote_subst='$sed_quote_subst' +double_quote_subst='$double_quote_subst' +delay_variable_subst='$delay_variable_subst' +_LT_CONFIG_STATUS_DECLARATIONS +LTCC='$LTCC' +LTCFLAGS='$LTCFLAGS' +compiler='$compiler_DEFAULT' + +# A function that is used when there is no print builtin or printf. +func_fallback_echo () +{ + eval 'cat <<_LTECHO_EOF +\$[]1 +_LTECHO_EOF' +} + +# Quote evaled strings. +for var in lt_decl_all_varnames([[ \ +]], lt_decl_quote_varnames); do + case \`eval \\\\\$ECHO \\\\""\\\\\$\$var"\\\\"\` in + *[[\\\\\\\`\\"\\\$]]*) + eval "lt_\$var=\\\\\\"\\\`\\\$ECHO \\"\\\$\$var\\" | \\\$SED \\"\\\$sed_quote_subst\\"\\\`\\\\\\"" ## exclude from sc_prohibit_nested_quotes + ;; + *) + eval "lt_\$var=\\\\\\"\\\$\$var\\\\\\"" + ;; + esac +done + +# Double-quote double-evaled strings. +for var in lt_decl_all_varnames([[ \ +]], lt_decl_dquote_varnames); do + case \`eval \\\\\$ECHO \\\\""\\\\\$\$var"\\\\"\` in + *[[\\\\\\\`\\"\\\$]]*) + eval "lt_\$var=\\\\\\"\\\`\\\$ECHO \\"\\\$\$var\\" | \\\$SED -e \\"\\\$double_quote_subst\\" -e \\"\\\$sed_quote_subst\\" -e \\"\\\$delay_variable_subst\\"\\\`\\\\\\"" ## exclude from sc_prohibit_nested_quotes + ;; + *) + eval "lt_\$var=\\\\\\"\\\$\$var\\\\\\"" + ;; + esac +done + +_LT_OUTPUT_LIBTOOL_INIT +]) + +# _LT_GENERATED_FILE_INIT(FILE, [COMMENT]) +# ------------------------------------ +# Generate a child script FILE with all initialization necessary to +# reuse the environment learned by the parent script, and make the +# file executable. If COMMENT is supplied, it is inserted after the +# '#!' sequence but before initialization text begins. After this +# macro, additional text can be appended to FILE to form the body of +# the child script. The macro ends with non-zero status if the +# file could not be fully written (such as if the disk is full). +m4_ifdef([AS_INIT_GENERATED], +[m4_defun([_LT_GENERATED_FILE_INIT],[AS_INIT_GENERATED($@)])], +[m4_defun([_LT_GENERATED_FILE_INIT], +[m4_require([AS_PREPARE])]dnl +[m4_pushdef([AS_MESSAGE_LOG_FD])]dnl +[lt_write_fail=0 +cat >$1 <<_ASEOF || lt_write_fail=1 +#! $SHELL +# Generated by $as_me. +$2 +SHELL=\${CONFIG_SHELL-$SHELL} +export SHELL +_ASEOF +cat >>$1 <<\_ASEOF || lt_write_fail=1 +AS_SHELL_SANITIZE +_AS_PREPARE +exec AS_MESSAGE_FD>&1 +_ASEOF +test 0 = "$lt_write_fail" && chmod +x $1[]dnl +m4_popdef([AS_MESSAGE_LOG_FD])])])# _LT_GENERATED_FILE_INIT + +# LT_OUTPUT +# --------- +# This macro allows early generation of the libtool script (before +# AC_OUTPUT is called), incase it is used in configure for compilation +# tests. +AC_DEFUN([LT_OUTPUT], +[: ${CONFIG_LT=./config.lt} +AC_MSG_NOTICE([creating $CONFIG_LT]) +_LT_GENERATED_FILE_INIT(["$CONFIG_LT"], +[# Run this file to recreate a libtool stub with the current configuration.]) + +cat >>"$CONFIG_LT" <<\_LTEOF +lt_cl_silent=false +exec AS_MESSAGE_LOG_FD>>config.log +{ + echo + AS_BOX([Running $as_me.]) +} >&AS_MESSAGE_LOG_FD + +lt_cl_help="\ +'$as_me' creates a local libtool stub from the current configuration, +for use in further configure time tests before the real libtool is +generated. + +Usage: $[0] [[OPTIONS]] + + -h, --help print this help, then exit + -V, --version print version number, then exit + -q, --quiet do not print progress messages + -d, --debug don't remove temporary files + +Report bugs to ." + +lt_cl_version="\ +m4_ifset([AC_PACKAGE_NAME], [AC_PACKAGE_NAME ])config.lt[]dnl +m4_ifset([AC_PACKAGE_VERSION], [ AC_PACKAGE_VERSION]) +configured by $[0], generated by m4_PACKAGE_STRING. + +Copyright (C) 2011 Free Software Foundation, Inc. +This config.lt script is free software; the Free Software Foundation +gives unlimited permision to copy, distribute and modify it." + +while test 0 != $[#] +do + case $[1] in + --version | --v* | -V ) + echo "$lt_cl_version"; exit 0 ;; + --help | --h* | -h ) + echo "$lt_cl_help"; exit 0 ;; + --debug | --d* | -d ) + debug=: ;; + --quiet | --q* | --silent | --s* | -q ) + lt_cl_silent=: ;; + + -*) AC_MSG_ERROR([unrecognized option: $[1] +Try '$[0] --help' for more information.]) ;; + + *) AC_MSG_ERROR([unrecognized argument: $[1] +Try '$[0] --help' for more information.]) ;; + esac + shift +done + +if $lt_cl_silent; then + exec AS_MESSAGE_FD>/dev/null +fi +_LTEOF + +cat >>"$CONFIG_LT" <<_LTEOF +_LT_OUTPUT_LIBTOOL_COMMANDS_INIT +_LTEOF + +cat >>"$CONFIG_LT" <<\_LTEOF +AC_MSG_NOTICE([creating $ofile]) +_LT_OUTPUT_LIBTOOL_COMMANDS +AS_EXIT(0) +_LTEOF +chmod +x "$CONFIG_LT" + +# configure is writing to config.log, but config.lt does its own redirection, +# appending to config.log, which fails on DOS, as config.log is still kept +# open by configure. Here we exec the FD to /dev/null, effectively closing +# config.log, so it can be properly (re)opened and appended to by config.lt. +lt_cl_success=: +test yes = "$silent" && + lt_config_lt_args="$lt_config_lt_args --quiet" +exec AS_MESSAGE_LOG_FD>/dev/null +$SHELL "$CONFIG_LT" $lt_config_lt_args || lt_cl_success=false +exec AS_MESSAGE_LOG_FD>>config.log +$lt_cl_success || AS_EXIT(1) +])# LT_OUTPUT + + +# _LT_CONFIG(TAG) +# --------------- +# If TAG is the built-in tag, create an initial libtool script with a +# default configuration from the untagged config vars. Otherwise add code +# to config.status for appending the configuration named by TAG from the +# matching tagged config vars. +m4_defun([_LT_CONFIG], +[m4_require([_LT_FILEUTILS_DEFAULTS])dnl +_LT_CONFIG_SAVE_COMMANDS([ + m4_define([_LT_TAG], m4_if([$1], [], [C], [$1]))dnl + m4_if(_LT_TAG, [C], [ + # See if we are running on zsh, and set the options that allow our + # commands through without removal of \ escapes. + if test -n "${ZSH_VERSION+set}"; then + setopt NO_GLOB_SUBST + fi + + cfgfile=${ofile}T + trap "$RM \"$cfgfile\"; exit 1" 1 2 15 + $RM "$cfgfile" + + cat <<_LT_EOF >> "$cfgfile" +#! $SHELL +# Generated automatically by $as_me ($PACKAGE) $VERSION +# NOTE: Changes made to this file will be lost: look at ltmain.sh. + +# Provide generalized library-building support services. +# Written by Gordon Matzigkeit, 1996 + +_LT_COPYING +_LT_LIBTOOL_TAGS + +# Configured defaults for sys_lib_dlsearch_path munging. +: \${LT_SYS_LIBRARY_PATH="$configure_time_lt_sys_library_path"} + +# ### BEGIN LIBTOOL CONFIG +_LT_LIBTOOL_CONFIG_VARS +_LT_LIBTOOL_TAG_VARS +# ### END LIBTOOL CONFIG + +_LT_EOF + + cat <<'_LT_EOF' >> "$cfgfile" + +# ### BEGIN FUNCTIONS SHARED WITH CONFIGURE + +_LT_PREPARE_MUNGE_PATH_LIST +_LT_PREPARE_CC_BASENAME + +# ### END FUNCTIONS SHARED WITH CONFIGURE + +_LT_EOF + + case $host_os in + aix3*) + cat <<\_LT_EOF >> "$cfgfile" +# AIX sometimes has problems with the GCC collect2 program. For some +# reason, if we set the COLLECT_NAMES environment variable, the problems +# vanish in a puff of smoke. +if test set != "${COLLECT_NAMES+set}"; then + COLLECT_NAMES= + export COLLECT_NAMES +fi +_LT_EOF + ;; + esac + + _LT_PROG_LTMAIN + + # We use sed instead of cat because bash on DJGPP gets confused if + # if finds mixed CR/LF and LF-only lines. Since sed operates in + # text mode, it properly converts lines to CR/LF. This bash problem + # is reportedly fixed, but why not run on old versions too? + $SED '$q' "$ltmain" >> "$cfgfile" \ + || (rm -f "$cfgfile"; exit 1) + + mv -f "$cfgfile" "$ofile" || + (rm -f "$ofile" && cp "$cfgfile" "$ofile" && rm -f "$cfgfile") + chmod +x "$ofile" +], +[cat <<_LT_EOF >> "$ofile" + +dnl Unfortunately we have to use $1 here, since _LT_TAG is not expanded +dnl in a comment (ie after a #). +# ### BEGIN LIBTOOL TAG CONFIG: $1 +_LT_LIBTOOL_TAG_VARS(_LT_TAG) +# ### END LIBTOOL TAG CONFIG: $1 +_LT_EOF +])dnl /m4_if +], +[m4_if([$1], [], [ + PACKAGE='$PACKAGE' + VERSION='$VERSION' + RM='$RM' + ofile='$ofile'], []) +])dnl /_LT_CONFIG_SAVE_COMMANDS +])# _LT_CONFIG + + +# LT_SUPPORTED_TAG(TAG) +# --------------------- +# Trace this macro to discover what tags are supported by the libtool +# --tag option, using: +# autoconf --trace 'LT_SUPPORTED_TAG:$1' +AC_DEFUN([LT_SUPPORTED_TAG], []) + + +# C support is built-in for now +m4_define([_LT_LANG_C_enabled], []) +m4_define([_LT_TAGS], []) + + +# LT_LANG(LANG) +# ------------- +# Enable libtool support for the given language if not already enabled. +AC_DEFUN([LT_LANG], +[AC_BEFORE([$0], [LT_OUTPUT])dnl +m4_case([$1], + [C], [_LT_LANG(C)], + [C++], [_LT_LANG(CXX)], + [Go], [_LT_LANG(GO)], + [Java], [_LT_LANG(GCJ)], + [Fortran 77], [_LT_LANG(F77)], + [Fortran], [_LT_LANG(FC)], + [Windows Resource], [_LT_LANG(RC)], + [m4_ifdef([_LT_LANG_]$1[_CONFIG], + [_LT_LANG($1)], + [m4_fatal([$0: unsupported language: "$1"])])])dnl +])# LT_LANG + + +# _LT_LANG(LANGNAME) +# ------------------ +m4_defun([_LT_LANG], +[m4_ifdef([_LT_LANG_]$1[_enabled], [], + [LT_SUPPORTED_TAG([$1])dnl + m4_append([_LT_TAGS], [$1 ])dnl + m4_define([_LT_LANG_]$1[_enabled], [])dnl + _LT_LANG_$1_CONFIG($1)])dnl +])# _LT_LANG + + +m4_ifndef([AC_PROG_GO], [ +# NOTE: This macro has been submitted for inclusion into # +# GNU Autoconf as AC_PROG_GO. When it is available in # +# a released version of Autoconf we should remove this # +# macro and use it instead. # +m4_defun([AC_PROG_GO], +[AC_LANG_PUSH(Go)dnl +AC_ARG_VAR([GOC], [Go compiler command])dnl +AC_ARG_VAR([GOFLAGS], [Go compiler flags])dnl +_AC_ARG_VAR_LDFLAGS()dnl +AC_CHECK_TOOL(GOC, gccgo) +if test -z "$GOC"; then + if test -n "$ac_tool_prefix"; then + AC_CHECK_PROG(GOC, [${ac_tool_prefix}gccgo], [${ac_tool_prefix}gccgo]) + fi +fi +if test -z "$GOC"; then + AC_CHECK_PROG(GOC, gccgo, gccgo, false) +fi +])#m4_defun +])#m4_ifndef + + +# _LT_LANG_DEFAULT_CONFIG +# ----------------------- +m4_defun([_LT_LANG_DEFAULT_CONFIG], +[AC_PROVIDE_IFELSE([AC_PROG_CXX], + [LT_LANG(CXX)], + [m4_define([AC_PROG_CXX], defn([AC_PROG_CXX])[LT_LANG(CXX)])]) + +AC_PROVIDE_IFELSE([AC_PROG_F77], + [LT_LANG(F77)], + [m4_define([AC_PROG_F77], defn([AC_PROG_F77])[LT_LANG(F77)])]) + +AC_PROVIDE_IFELSE([AC_PROG_FC], + [LT_LANG(FC)], + [m4_define([AC_PROG_FC], defn([AC_PROG_FC])[LT_LANG(FC)])]) + +dnl The call to [A][M_PROG_GCJ] is quoted like that to stop aclocal +dnl pulling things in needlessly. +AC_PROVIDE_IFELSE([AC_PROG_GCJ], + [LT_LANG(GCJ)], + [AC_PROVIDE_IFELSE([A][M_PROG_GCJ], + [LT_LANG(GCJ)], + [AC_PROVIDE_IFELSE([LT_PROG_GCJ], + [LT_LANG(GCJ)], + [m4_ifdef([AC_PROG_GCJ], + [m4_define([AC_PROG_GCJ], defn([AC_PROG_GCJ])[LT_LANG(GCJ)])]) + m4_ifdef([A][M_PROG_GCJ], + [m4_define([A][M_PROG_GCJ], defn([A][M_PROG_GCJ])[LT_LANG(GCJ)])]) + m4_ifdef([LT_PROG_GCJ], + [m4_define([LT_PROG_GCJ], defn([LT_PROG_GCJ])[LT_LANG(GCJ)])])])])]) + +AC_PROVIDE_IFELSE([AC_PROG_GO], + [LT_LANG(GO)], + [m4_define([AC_PROG_GO], defn([AC_PROG_GO])[LT_LANG(GO)])]) + +AC_PROVIDE_IFELSE([LT_PROG_RC], + [LT_LANG(RC)], + [m4_define([LT_PROG_RC], defn([LT_PROG_RC])[LT_LANG(RC)])]) +])# _LT_LANG_DEFAULT_CONFIG + +# Obsolete macros: +AU_DEFUN([AC_LIBTOOL_CXX], [LT_LANG(C++)]) +AU_DEFUN([AC_LIBTOOL_F77], [LT_LANG(Fortran 77)]) +AU_DEFUN([AC_LIBTOOL_FC], [LT_LANG(Fortran)]) +AU_DEFUN([AC_LIBTOOL_GCJ], [LT_LANG(Java)]) +AU_DEFUN([AC_LIBTOOL_RC], [LT_LANG(Windows Resource)]) +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([AC_LIBTOOL_CXX], []) +dnl AC_DEFUN([AC_LIBTOOL_F77], []) +dnl AC_DEFUN([AC_LIBTOOL_FC], []) +dnl AC_DEFUN([AC_LIBTOOL_GCJ], []) +dnl AC_DEFUN([AC_LIBTOOL_RC], []) + + +# _LT_TAG_COMPILER +# ---------------- +m4_defun([_LT_TAG_COMPILER], +[AC_REQUIRE([AC_PROG_CC])dnl + +_LT_DECL([LTCC], [CC], [1], [A C compiler])dnl +_LT_DECL([LTCFLAGS], [CFLAGS], [1], [LTCC compiler flags])dnl +_LT_TAGDECL([CC], [compiler], [1], [A language specific compiler])dnl +_LT_TAGDECL([with_gcc], [GCC], [0], [Is the compiler the GNU compiler?])dnl + +# If no C compiler was specified, use CC. +LTCC=${LTCC-"$CC"} + +# If no C compiler flags were specified, use CFLAGS. +LTCFLAGS=${LTCFLAGS-"$CFLAGS"} + +# Allow CC to be a program name with arguments. +compiler=$CC +])# _LT_TAG_COMPILER + + +# _LT_COMPILER_BOILERPLATE +# ------------------------ +# Check for compiler boilerplate output or warnings with +# the simple compiler test code. +m4_defun([_LT_COMPILER_BOILERPLATE], +[m4_require([_LT_DECL_SED])dnl +ac_outfile=conftest.$ac_objext +echo "$lt_simple_compile_test_code" >conftest.$ac_ext +eval "$ac_compile" 2>&1 >/dev/null | $SED '/^$/d; /^ *+/d' >conftest.err +_lt_compiler_boilerplate=`cat conftest.err` +$RM conftest* +])# _LT_COMPILER_BOILERPLATE + + +# _LT_LINKER_BOILERPLATE +# ---------------------- +# Check for linker boilerplate output or warnings with +# the simple link test code. +m4_defun([_LT_LINKER_BOILERPLATE], +[m4_require([_LT_DECL_SED])dnl +ac_outfile=conftest.$ac_objext +echo "$lt_simple_link_test_code" >conftest.$ac_ext +eval "$ac_link" 2>&1 >/dev/null | $SED '/^$/d; /^ *+/d' >conftest.err +_lt_linker_boilerplate=`cat conftest.err` +$RM -r conftest* +])# _LT_LINKER_BOILERPLATE + +# _LT_REQUIRED_DARWIN_CHECKS +# ------------------------- +m4_defun_once([_LT_REQUIRED_DARWIN_CHECKS],[ + case $host_os in + rhapsody* | darwin*) + AC_CHECK_TOOL([DSYMUTIL], [dsymutil], [:]) + AC_CHECK_TOOL([NMEDIT], [nmedit], [:]) + AC_CHECK_TOOL([LIPO], [lipo], [:]) + AC_CHECK_TOOL([OTOOL], [otool], [:]) + AC_CHECK_TOOL([OTOOL64], [otool64], [:]) + _LT_DECL([], [DSYMUTIL], [1], + [Tool to manipulate archived DWARF debug symbol files on Mac OS X]) + _LT_DECL([], [NMEDIT], [1], + [Tool to change global to local symbols on Mac OS X]) + _LT_DECL([], [LIPO], [1], + [Tool to manipulate fat objects and archives on Mac OS X]) + _LT_DECL([], [OTOOL], [1], + [ldd/readelf like tool for Mach-O binaries on Mac OS X]) + _LT_DECL([], [OTOOL64], [1], + [ldd/readelf like tool for 64 bit Mach-O binaries on Mac OS X 10.4]) + + AC_CACHE_CHECK([for -single_module linker flag],[lt_cv_apple_cc_single_mod], + [lt_cv_apple_cc_single_mod=no + if test -z "$LT_MULTI_MODULE"; then + # By default we will add the -single_module flag. You can override + # by either setting the environment variable LT_MULTI_MODULE + # non-empty at configure time, or by adding -multi_module to the + # link flags. + rm -rf libconftest.dylib* + echo "int foo(void){return 1;}" > conftest.c + echo "$LTCC $LTCFLAGS $LDFLAGS -o libconftest.dylib \ +-dynamiclib -Wl,-single_module conftest.c" >&AS_MESSAGE_LOG_FD + $LTCC $LTCFLAGS $LDFLAGS -o libconftest.dylib \ + -dynamiclib -Wl,-single_module conftest.c 2>conftest.err + _lt_result=$? + # If there is a non-empty error log, and "single_module" + # appears in it, assume the flag caused a linker warning + if test -s conftest.err && $GREP single_module conftest.err; then + cat conftest.err >&AS_MESSAGE_LOG_FD + # Otherwise, if the output was created with a 0 exit code from + # the compiler, it worked. + elif test -f libconftest.dylib && test 0 = "$_lt_result"; then + lt_cv_apple_cc_single_mod=yes + else + cat conftest.err >&AS_MESSAGE_LOG_FD + fi + rm -rf libconftest.dylib* + rm -f conftest.* + fi]) + + AC_CACHE_CHECK([for -exported_symbols_list linker flag], + [lt_cv_ld_exported_symbols_list], + [lt_cv_ld_exported_symbols_list=no + save_LDFLAGS=$LDFLAGS + echo "_main" > conftest.sym + LDFLAGS="$LDFLAGS -Wl,-exported_symbols_list,conftest.sym" + AC_LINK_IFELSE([AC_LANG_PROGRAM([],[])], + [lt_cv_ld_exported_symbols_list=yes], + [lt_cv_ld_exported_symbols_list=no]) + LDFLAGS=$save_LDFLAGS + ]) + + AC_CACHE_CHECK([for -force_load linker flag],[lt_cv_ld_force_load], + [lt_cv_ld_force_load=no + cat > conftest.c << _LT_EOF +int forced_loaded() { return 2;} +_LT_EOF + echo "$LTCC $LTCFLAGS -c -o conftest.o conftest.c" >&AS_MESSAGE_LOG_FD + $LTCC $LTCFLAGS -c -o conftest.o conftest.c 2>&AS_MESSAGE_LOG_FD + echo "$AR $AR_FLAGS libconftest.a conftest.o" >&AS_MESSAGE_LOG_FD + $AR $AR_FLAGS libconftest.a conftest.o 2>&AS_MESSAGE_LOG_FD + echo "$RANLIB libconftest.a" >&AS_MESSAGE_LOG_FD + $RANLIB libconftest.a 2>&AS_MESSAGE_LOG_FD + cat > conftest.c << _LT_EOF +int main() { return 0;} +_LT_EOF + echo "$LTCC $LTCFLAGS $LDFLAGS -o conftest conftest.c -Wl,-force_load,./libconftest.a" >&AS_MESSAGE_LOG_FD + $LTCC $LTCFLAGS $LDFLAGS -o conftest conftest.c -Wl,-force_load,./libconftest.a 2>conftest.err + _lt_result=$? + if test -s conftest.err && $GREP force_load conftest.err; then + cat conftest.err >&AS_MESSAGE_LOG_FD + elif test -f conftest && test 0 = "$_lt_result" && $GREP forced_load conftest >/dev/null 2>&1; then + lt_cv_ld_force_load=yes + else + cat conftest.err >&AS_MESSAGE_LOG_FD + fi + rm -f conftest.err libconftest.a conftest conftest.c + rm -rf conftest.dSYM + ]) + case $host_os in + rhapsody* | darwin1.[[012]]) + _lt_dar_allow_undefined='$wl-undefined ${wl}suppress' ;; + darwin1.*) + _lt_dar_allow_undefined='$wl-flat_namespace $wl-undefined ${wl}suppress' ;; + darwin*) + case $MACOSX_DEPLOYMENT_TARGET,$host in + 10.[[012]],*|,*powerpc*-darwin[[5-8]]*) + _lt_dar_allow_undefined='$wl-flat_namespace $wl-undefined ${wl}suppress' ;; + *) + _lt_dar_allow_undefined='$wl-undefined ${wl}dynamic_lookup' ;; + esac + ;; + esac + if test yes = "$lt_cv_apple_cc_single_mod"; then + _lt_dar_single_mod='$single_module' + fi + if test yes = "$lt_cv_ld_exported_symbols_list"; then + _lt_dar_export_syms=' $wl-exported_symbols_list,$output_objdir/$libname-symbols.expsym' + else + _lt_dar_export_syms='~$NMEDIT -s $output_objdir/$libname-symbols.expsym $lib' + fi + if test : != "$DSYMUTIL" && test no = "$lt_cv_ld_force_load"; then + _lt_dsymutil='~$DSYMUTIL $lib || :' + else + _lt_dsymutil= + fi + ;; + esac +]) + + +# _LT_DARWIN_LINKER_FEATURES([TAG]) +# --------------------------------- +# Checks for linker and compiler features on darwin +m4_defun([_LT_DARWIN_LINKER_FEATURES], +[ + m4_require([_LT_REQUIRED_DARWIN_CHECKS]) + _LT_TAGVAR(archive_cmds_need_lc, $1)=no + _LT_TAGVAR(hardcode_direct, $1)=no + _LT_TAGVAR(hardcode_automatic, $1)=yes + _LT_TAGVAR(hardcode_shlibpath_var, $1)=unsupported + if test yes = "$lt_cv_ld_force_load"; then + _LT_TAGVAR(whole_archive_flag_spec, $1)='`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience $wl-force_load,$conv\"; done; func_echo_all \"$new_convenience\"`' + m4_case([$1], [F77], [_LT_TAGVAR(compiler_needs_object, $1)=yes], + [FC], [_LT_TAGVAR(compiler_needs_object, $1)=yes]) + else + _LT_TAGVAR(whole_archive_flag_spec, $1)='' + fi + _LT_TAGVAR(link_all_deplibs, $1)=yes + _LT_TAGVAR(allow_undefined_flag, $1)=$_lt_dar_allow_undefined + case $cc_basename in + ifort*|nagfor*) _lt_dar_can_shared=yes ;; + *) _lt_dar_can_shared=$GCC ;; + esac + if test yes = "$_lt_dar_can_shared"; then + output_verbose_link_cmd=func_echo_all + _LT_TAGVAR(archive_cmds, $1)="\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$libobjs \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring $_lt_dar_single_mod$_lt_dsymutil" + _LT_TAGVAR(module_cmds, $1)="\$CC \$allow_undefined_flag -o \$lib -bundle \$libobjs \$deplibs \$compiler_flags$_lt_dsymutil" + _LT_TAGVAR(archive_expsym_cmds, $1)="$SED 's|^|_|' < \$export_symbols > \$output_objdir/\$libname-symbols.expsym~\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$libobjs \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring $_lt_dar_single_mod$_lt_dar_export_syms$_lt_dsymutil" + _LT_TAGVAR(module_expsym_cmds, $1)="$SED -e 's|^|_|' < \$export_symbols > \$output_objdir/\$libname-symbols.expsym~\$CC \$allow_undefined_flag -o \$lib -bundle \$libobjs \$deplibs \$compiler_flags$_lt_dar_export_syms$_lt_dsymutil" + m4_if([$1], [CXX], +[ if test yes != "$lt_cv_apple_cc_single_mod"; then + _LT_TAGVAR(archive_cmds, $1)="\$CC -r -keep_private_externs -nostdlib -o \$lib-master.o \$libobjs~\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$lib-master.o \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring$_lt_dsymutil" + _LT_TAGVAR(archive_expsym_cmds, $1)="$SED 's|^|_|' < \$export_symbols > \$output_objdir/\$libname-symbols.expsym~\$CC -r -keep_private_externs -nostdlib -o \$lib-master.o \$libobjs~\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$lib-master.o \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring$_lt_dar_export_syms$_lt_dsymutil" + fi +],[]) + else + _LT_TAGVAR(ld_shlibs, $1)=no + fi +]) + +# _LT_SYS_MODULE_PATH_AIX([TAGNAME]) +# ---------------------------------- +# Links a minimal program and checks the executable +# for the system default hardcoded library path. In most cases, +# this is /usr/lib:/lib, but when the MPI compilers are used +# the location of the communication and MPI libs are included too. +# If we don't find anything, use the default library path according +# to the aix ld manual. +# Store the results from the different compilers for each TAGNAME. +# Allow to override them for all tags through lt_cv_aix_libpath. +m4_defun([_LT_SYS_MODULE_PATH_AIX], +[m4_require([_LT_DECL_SED])dnl +if test set = "${lt_cv_aix_libpath+set}"; then + aix_libpath=$lt_cv_aix_libpath +else + AC_CACHE_VAL([_LT_TAGVAR([lt_cv_aix_libpath_], [$1])], + [AC_LINK_IFELSE([AC_LANG_PROGRAM],[ + lt_aix_libpath_sed='[ + /Import File Strings/,/^$/ { + /^0/ { + s/^0 *\([^ ]*\) *$/\1/ + p + } + }]' + _LT_TAGVAR([lt_cv_aix_libpath_], [$1])=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` + # Check for a 64-bit object if we didn't find anything. + if test -z "$_LT_TAGVAR([lt_cv_aix_libpath_], [$1])"; then + _LT_TAGVAR([lt_cv_aix_libpath_], [$1])=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` + fi],[]) + if test -z "$_LT_TAGVAR([lt_cv_aix_libpath_], [$1])"; then + _LT_TAGVAR([lt_cv_aix_libpath_], [$1])=/usr/lib:/lib + fi + ]) + aix_libpath=$_LT_TAGVAR([lt_cv_aix_libpath_], [$1]) +fi +])# _LT_SYS_MODULE_PATH_AIX + + +# _LT_SHELL_INIT(ARG) +# ------------------- +m4_define([_LT_SHELL_INIT], +[m4_divert_text([M4SH-INIT], [$1 +])])# _LT_SHELL_INIT + + + +# _LT_PROG_ECHO_BACKSLASH +# ----------------------- +# Find how we can fake an echo command that does not interpret backslash. +# In particular, with Autoconf 2.60 or later we add some code to the start +# of the generated configure script that will find a shell with a builtin +# printf (that we can use as an echo command). +m4_defun([_LT_PROG_ECHO_BACKSLASH], +[ECHO='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' +ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO +ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO$ECHO + +AC_MSG_CHECKING([how to print strings]) +# Test print first, because it will be a builtin if present. +if test "X`( print -r -- -n ) 2>/dev/null`" = X-n && \ + test "X`print -r -- $ECHO 2>/dev/null`" = "X$ECHO"; then + ECHO='print -r --' +elif test "X`printf %s $ECHO 2>/dev/null`" = "X$ECHO"; then + ECHO='printf %s\n' +else + # Use this function as a fallback that always works. + func_fallback_echo () + { + eval 'cat <<_LTECHO_EOF +$[]1 +_LTECHO_EOF' + } + ECHO='func_fallback_echo' +fi + +# func_echo_all arg... +# Invoke $ECHO with all args, space-separated. +func_echo_all () +{ + $ECHO "$*" +} + +case $ECHO in + printf*) AC_MSG_RESULT([printf]) ;; + print*) AC_MSG_RESULT([print -r]) ;; + *) AC_MSG_RESULT([cat]) ;; +esac + +m4_ifdef([_AS_DETECT_SUGGESTED], +[_AS_DETECT_SUGGESTED([ + test -n "${ZSH_VERSION+set}${BASH_VERSION+set}" || ( + ECHO='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' + ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO + ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO$ECHO + PATH=/empty FPATH=/empty; export PATH FPATH + test "X`printf %s $ECHO`" = "X$ECHO" \ + || test "X`print -r -- $ECHO`" = "X$ECHO" )])]) + +_LT_DECL([], [SHELL], [1], [Shell to use when invoking shell scripts]) +_LT_DECL([], [ECHO], [1], [An echo program that protects backslashes]) +])# _LT_PROG_ECHO_BACKSLASH + + +# _LT_WITH_SYSROOT +# ---------------- +AC_DEFUN([_LT_WITH_SYSROOT], +[m4_require([_LT_DECL_SED])dnl +AC_MSG_CHECKING([for sysroot]) +AC_ARG_WITH([sysroot], +[AS_HELP_STRING([--with-sysroot@<:@=DIR@:>@], + [Search for dependent libraries within DIR (or the compiler's sysroot + if not specified).])], +[], [with_sysroot=no]) + +dnl lt_sysroot will always be passed unquoted. We quote it here +dnl in case the user passed a directory name. +lt_sysroot= +case $with_sysroot in #( + yes) + if test yes = "$GCC"; then + lt_sysroot=`$CC --print-sysroot 2>/dev/null` + fi + ;; #( + /*) + lt_sysroot=`echo "$with_sysroot" | $SED -e "$sed_quote_subst"` + ;; #( + no|'') + ;; #( + *) + AC_MSG_RESULT([$with_sysroot]) + AC_MSG_ERROR([The sysroot must be an absolute path.]) + ;; +esac + + AC_MSG_RESULT([${lt_sysroot:-no}]) +_LT_DECL([], [lt_sysroot], [0], [The root where to search for ]dnl +[dependent libraries, and where our libraries should be installed.])]) + +# _LT_ENABLE_LOCK +# --------------- +m4_defun([_LT_ENABLE_LOCK], +[AC_ARG_ENABLE([libtool-lock], + [AS_HELP_STRING([--disable-libtool-lock], + [avoid locking (might break parallel builds)])]) +test no = "$enable_libtool_lock" || enable_libtool_lock=yes + +# Some flags need to be propagated to the compiler or linker for good +# libtool support. +case $host in +ia64-*-hpux*) + # Find out what ABI is being produced by ac_compile, and set mode + # options accordingly. + echo 'int i;' > conftest.$ac_ext + if AC_TRY_EVAL(ac_compile); then + case `$FILECMD conftest.$ac_objext` in + *ELF-32*) + HPUX_IA64_MODE=32 + ;; + *ELF-64*) + HPUX_IA64_MODE=64 + ;; + esac + fi + rm -rf conftest* + ;; +*-*-irix6*) + # Find out what ABI is being produced by ac_compile, and set linker + # options accordingly. + echo '[#]line '$LINENO' "configure"' > conftest.$ac_ext + if AC_TRY_EVAL(ac_compile); then + if test yes = "$lt_cv_prog_gnu_ld"; then + case `$FILECMD conftest.$ac_objext` in + *32-bit*) + LD="${LD-ld} -melf32bsmip" + ;; + *N32*) + LD="${LD-ld} -melf32bmipn32" + ;; + *64-bit*) + LD="${LD-ld} -melf64bmip" + ;; + esac + else + case `$FILECMD conftest.$ac_objext` in + *32-bit*) + LD="${LD-ld} -32" + ;; + *N32*) + LD="${LD-ld} -n32" + ;; + *64-bit*) + LD="${LD-ld} -64" + ;; + esac + fi + fi + rm -rf conftest* + ;; + +mips64*-*linux*) + # Find out what ABI is being produced by ac_compile, and set linker + # options accordingly. + echo '[#]line '$LINENO' "configure"' > conftest.$ac_ext + if AC_TRY_EVAL(ac_compile); then + emul=elf + case `$FILECMD conftest.$ac_objext` in + *32-bit*) + emul="${emul}32" + ;; + *64-bit*) + emul="${emul}64" + ;; + esac + case `$FILECMD conftest.$ac_objext` in + *MSB*) + emul="${emul}btsmip" + ;; + *LSB*) + emul="${emul}ltsmip" + ;; + esac + case `$FILECMD conftest.$ac_objext` in + *N32*) + emul="${emul}n32" + ;; + esac + LD="${LD-ld} -m $emul" + fi + rm -rf conftest* + ;; + +x86_64-*kfreebsd*-gnu|x86_64-*linux*|powerpc*-*linux*| \ +s390*-*linux*|s390*-*tpf*|sparc*-*linux*) + # Find out what ABI is being produced by ac_compile, and set linker + # options accordingly. Note that the listed cases only cover the + # situations where additional linker options are needed (such as when + # doing 32-bit compilation for a host where ld defaults to 64-bit, or + # vice versa); the common cases where no linker options are needed do + # not appear in the list. + echo 'int i;' > conftest.$ac_ext + if AC_TRY_EVAL(ac_compile); then + case `$FILECMD conftest.o` in + *32-bit*) + case $host in + x86_64-*kfreebsd*-gnu) + LD="${LD-ld} -m elf_i386_fbsd" + ;; + x86_64-*linux*) + case `$FILECMD conftest.o` in + *x86-64*) + LD="${LD-ld} -m elf32_x86_64" + ;; + *) + LD="${LD-ld} -m elf_i386" + ;; + esac + ;; + powerpc64le-*linux*) + LD="${LD-ld} -m elf32lppclinux" + ;; + powerpc64-*linux*) + LD="${LD-ld} -m elf32ppclinux" + ;; + s390x-*linux*) + LD="${LD-ld} -m elf_s390" + ;; + sparc64-*linux*) + LD="${LD-ld} -m elf32_sparc" + ;; + esac + ;; + *64-bit*) + case $host in + x86_64-*kfreebsd*-gnu) + LD="${LD-ld} -m elf_x86_64_fbsd" + ;; + x86_64-*linux*) + LD="${LD-ld} -m elf_x86_64" + ;; + powerpcle-*linux*) + LD="${LD-ld} -m elf64lppc" + ;; + powerpc-*linux*) + LD="${LD-ld} -m elf64ppc" + ;; + s390*-*linux*|s390*-*tpf*) + LD="${LD-ld} -m elf64_s390" + ;; + sparc*-*linux*) + LD="${LD-ld} -m elf64_sparc" + ;; + esac + ;; + esac + fi + rm -rf conftest* + ;; + +*-*-sco3.2v5*) + # On SCO OpenServer 5, we need -belf to get full-featured binaries. + SAVE_CFLAGS=$CFLAGS + CFLAGS="$CFLAGS -belf" + AC_CACHE_CHECK([whether the C compiler needs -belf], lt_cv_cc_needs_belf, + [AC_LANG_PUSH(C) + AC_LINK_IFELSE([AC_LANG_PROGRAM([[]],[[]])],[lt_cv_cc_needs_belf=yes],[lt_cv_cc_needs_belf=no]) + AC_LANG_POP]) + if test yes != "$lt_cv_cc_needs_belf"; then + # this is probably gcc 2.8.0, egcs 1.0 or newer; no need for -belf + CFLAGS=$SAVE_CFLAGS + fi + ;; +*-*solaris*) + # Find out what ABI is being produced by ac_compile, and set linker + # options accordingly. + echo 'int i;' > conftest.$ac_ext + if AC_TRY_EVAL(ac_compile); then + case `$FILECMD conftest.o` in + *64-bit*) + case $lt_cv_prog_gnu_ld in + yes*) + case $host in + i?86-*-solaris*|x86_64-*-solaris*) + LD="${LD-ld} -m elf_x86_64" + ;; + sparc*-*-solaris*) + LD="${LD-ld} -m elf64_sparc" + ;; + esac + # GNU ld 2.21 introduced _sol2 emulations. Use them if available. + if ${LD-ld} -V | grep _sol2 >/dev/null 2>&1; then + LD=${LD-ld}_sol2 + fi + ;; + *) + if ${LD-ld} -64 -r -o conftest2.o conftest.o >/dev/null 2>&1; then + LD="${LD-ld} -64" + fi + ;; + esac + ;; + esac + fi + rm -rf conftest* + ;; +esac + +need_locks=$enable_libtool_lock +])# _LT_ENABLE_LOCK + + +# _LT_PROG_AR +# ----------- +m4_defun([_LT_PROG_AR], +[AC_CHECK_TOOLS(AR, [ar], false) +: ${AR=ar} +_LT_DECL([], [AR], [1], [The archiver]) + +# Use ARFLAGS variable as AR's operation code to sync the variable naming with +# Automake. If both AR_FLAGS and ARFLAGS are specified, AR_FLAGS should have +# higher priority because thats what people were doing historically (setting +# ARFLAGS for automake and AR_FLAGS for libtool). FIXME: Make the AR_FLAGS +# variable obsoleted/removed. + +test ${AR_FLAGS+y} || AR_FLAGS=${ARFLAGS-cr} +lt_ar_flags=$AR_FLAGS +_LT_DECL([], [lt_ar_flags], [0], [Flags to create an archive (by configure)]) + +# Make AR_FLAGS overridable by 'make ARFLAGS='. Don't try to run-time override +# by AR_FLAGS because that was never working and AR_FLAGS is about to die. +_LT_DECL([], [AR_FLAGS], [\@S|@{ARFLAGS-"\@S|@lt_ar_flags"}], + [Flags to create an archive]) + +AC_CACHE_CHECK([for archiver @FILE support], [lt_cv_ar_at_file], + [lt_cv_ar_at_file=no + AC_COMPILE_IFELSE([AC_LANG_PROGRAM], + [echo conftest.$ac_objext > conftest.lst + lt_ar_try='$AR $AR_FLAGS libconftest.a @conftest.lst >&AS_MESSAGE_LOG_FD' + AC_TRY_EVAL([lt_ar_try]) + if test 0 -eq "$ac_status"; then + # Ensure the archiver fails upon bogus file names. + rm -f conftest.$ac_objext libconftest.a + AC_TRY_EVAL([lt_ar_try]) + if test 0 -ne "$ac_status"; then + lt_cv_ar_at_file=@ + fi + fi + rm -f conftest.* libconftest.a + ]) + ]) + +if test no = "$lt_cv_ar_at_file"; then + archiver_list_spec= +else + archiver_list_spec=$lt_cv_ar_at_file +fi +_LT_DECL([], [archiver_list_spec], [1], + [How to feed a file listing to the archiver]) +])# _LT_PROG_AR + + +# _LT_CMD_OLD_ARCHIVE +# ------------------- +m4_defun([_LT_CMD_OLD_ARCHIVE], +[_LT_PROG_AR + +AC_CHECK_TOOL(STRIP, strip, :) +test -z "$STRIP" && STRIP=: +_LT_DECL([], [STRIP], [1], [A symbol stripping program]) + +AC_CHECK_TOOL(RANLIB, ranlib, :) +test -z "$RANLIB" && RANLIB=: +_LT_DECL([], [RANLIB], [1], + [Commands used to install an old-style archive]) + +# Determine commands to create old-style static archives. +old_archive_cmds='$AR $AR_FLAGS $oldlib$oldobjs' +old_postinstall_cmds='chmod 644 $oldlib' +old_postuninstall_cmds= + +if test -n "$RANLIB"; then + case $host_os in + bitrig* | openbsd*) + old_postinstall_cmds="$old_postinstall_cmds~\$RANLIB -t \$tool_oldlib" + ;; + *) + old_postinstall_cmds="$old_postinstall_cmds~\$RANLIB \$tool_oldlib" + ;; + esac + old_archive_cmds="$old_archive_cmds~\$RANLIB \$tool_oldlib" +fi + +case $host_os in + darwin*) + lock_old_archive_extraction=yes ;; + *) + lock_old_archive_extraction=no ;; +esac +_LT_DECL([], [old_postinstall_cmds], [2]) +_LT_DECL([], [old_postuninstall_cmds], [2]) +_LT_TAGDECL([], [old_archive_cmds], [2], + [Commands used to build an old-style archive]) +_LT_DECL([], [lock_old_archive_extraction], [0], + [Whether to use a lock for old archive extraction]) +])# _LT_CMD_OLD_ARCHIVE + + +# _LT_COMPILER_OPTION(MESSAGE, VARIABLE-NAME, FLAGS, +# [OUTPUT-FILE], [ACTION-SUCCESS], [ACTION-FAILURE]) +# ---------------------------------------------------------------- +# Check whether the given compiler option works +AC_DEFUN([_LT_COMPILER_OPTION], +[m4_require([_LT_FILEUTILS_DEFAULTS])dnl +m4_require([_LT_DECL_SED])dnl +AC_CACHE_CHECK([$1], [$2], + [$2=no + m4_if([$4], , [ac_outfile=conftest.$ac_objext], [ac_outfile=$4]) + echo "$lt_simple_compile_test_code" > conftest.$ac_ext + lt_compiler_flag="$3" ## exclude from sc_useless_quotes_in_assignment + # Insert the option either (1) after the last *FLAGS variable, or + # (2) before a word containing "conftest.", or (3) at the end. + # Note that $ac_compile itself does not contain backslashes and begins + # with a dollar sign (not a hyphen), so the echo should work correctly. + # The option is referenced via a variable to avoid confusing sed. + lt_compile=`echo "$ac_compile" | $SED \ + -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ + -e 's: [[^ ]]*conftest\.: $lt_compiler_flag&:; t' \ + -e 's:$: $lt_compiler_flag:'` + (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&AS_MESSAGE_LOG_FD) + (eval "$lt_compile" 2>conftest.err) + ac_status=$? + cat conftest.err >&AS_MESSAGE_LOG_FD + echo "$as_me:$LINENO: \$? = $ac_status" >&AS_MESSAGE_LOG_FD + if (exit $ac_status) && test -s "$ac_outfile"; then + # The compiler can only warn and ignore the option if not recognized + # So say no if there are warnings other than the usual output. + $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' >conftest.exp + $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 + if test ! -s conftest.er2 || diff conftest.exp conftest.er2 >/dev/null; then + $2=yes + fi + fi + $RM conftest* +]) + +if test yes = "[$]$2"; then + m4_if([$5], , :, [$5]) +else + m4_if([$6], , :, [$6]) +fi +])# _LT_COMPILER_OPTION + +# Old name: +AU_ALIAS([AC_LIBTOOL_COMPILER_OPTION], [_LT_COMPILER_OPTION]) +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([AC_LIBTOOL_COMPILER_OPTION], []) + + +# _LT_LINKER_OPTION(MESSAGE, VARIABLE-NAME, FLAGS, +# [ACTION-SUCCESS], [ACTION-FAILURE]) +# ---------------------------------------------------- +# Check whether the given linker option works +AC_DEFUN([_LT_LINKER_OPTION], +[m4_require([_LT_FILEUTILS_DEFAULTS])dnl +m4_require([_LT_DECL_SED])dnl +AC_CACHE_CHECK([$1], [$2], + [$2=no + save_LDFLAGS=$LDFLAGS + LDFLAGS="$LDFLAGS $3" + echo "$lt_simple_link_test_code" > conftest.$ac_ext + if (eval $ac_link 2>conftest.err) && test -s conftest$ac_exeext; then + # The linker can only warn and ignore the option if not recognized + # So say no if there are warnings + if test -s conftest.err; then + # Append any errors to the config.log. + cat conftest.err 1>&AS_MESSAGE_LOG_FD + $ECHO "$_lt_linker_boilerplate" | $SED '/^$/d' > conftest.exp + $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 + if diff conftest.exp conftest.er2 >/dev/null; then + $2=yes + fi + else + $2=yes + fi + fi + $RM -r conftest* + LDFLAGS=$save_LDFLAGS +]) + +if test yes = "[$]$2"; then + m4_if([$4], , :, [$4]) +else + m4_if([$5], , :, [$5]) +fi +])# _LT_LINKER_OPTION + +# Old name: +AU_ALIAS([AC_LIBTOOL_LINKER_OPTION], [_LT_LINKER_OPTION]) +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([AC_LIBTOOL_LINKER_OPTION], []) + + +# LT_CMD_MAX_LEN +#--------------- +AC_DEFUN([LT_CMD_MAX_LEN], +[AC_REQUIRE([AC_CANONICAL_HOST])dnl +# find the maximum length of command line arguments +AC_MSG_CHECKING([the maximum length of command line arguments]) +AC_CACHE_VAL([lt_cv_sys_max_cmd_len], [dnl + i=0 + teststring=ABCD + + case $build_os in + msdosdjgpp*) + # On DJGPP, this test can blow up pretty badly due to problems in libc + # (any single argument exceeding 2000 bytes causes a buffer overrun + # during glob expansion). Even if it were fixed, the result of this + # check would be larger than it should be. + lt_cv_sys_max_cmd_len=12288; # 12K is about right + ;; + + gnu*) + # Under GNU Hurd, this test is not required because there is + # no limit to the length of command line arguments. + # Libtool will interpret -1 as no limit whatsoever + lt_cv_sys_max_cmd_len=-1; + ;; + + cygwin* | mingw* | cegcc*) + # On Win9x/ME, this test blows up -- it succeeds, but takes + # about 5 minutes as the teststring grows exponentially. + # Worse, since 9x/ME are not pre-emptively multitasking, + # you end up with a "frozen" computer, even though with patience + # the test eventually succeeds (with a max line length of 256k). + # Instead, let's just punt: use the minimum linelength reported by + # all of the supported platforms: 8192 (on NT/2K/XP). + lt_cv_sys_max_cmd_len=8192; + ;; + + mint*) + # On MiNT this can take a long time and run out of memory. + lt_cv_sys_max_cmd_len=8192; + ;; + + amigaos*) + # On AmigaOS with pdksh, this test takes hours, literally. + # So we just punt and use a minimum line length of 8192. + lt_cv_sys_max_cmd_len=8192; + ;; + + bitrig* | darwin* | dragonfly* | freebsd* | midnightbsd* | netbsd* | openbsd*) + # This has been around since 386BSD, at least. Likely further. + if test -x /sbin/sysctl; then + lt_cv_sys_max_cmd_len=`/sbin/sysctl -n kern.argmax` + elif test -x /usr/sbin/sysctl; then + lt_cv_sys_max_cmd_len=`/usr/sbin/sysctl -n kern.argmax` + else + lt_cv_sys_max_cmd_len=65536 # usable default for all BSDs + fi + # And add a safety zone + lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \/ 4` + lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \* 3` + ;; + + interix*) + # We know the value 262144 and hardcode it with a safety zone (like BSD) + lt_cv_sys_max_cmd_len=196608 + ;; + + os2*) + # The test takes a long time on OS/2. + lt_cv_sys_max_cmd_len=8192 + ;; + + osf*) + # Dr. Hans Ekkehard Plesser reports seeing a kernel panic running configure + # due to this test when exec_disable_arg_limit is 1 on Tru64. It is not + # nice to cause kernel panics so lets avoid the loop below. + # First set a reasonable default. + lt_cv_sys_max_cmd_len=16384 + # + if test -x /sbin/sysconfig; then + case `/sbin/sysconfig -q proc exec_disable_arg_limit` in + *1*) lt_cv_sys_max_cmd_len=-1 ;; + esac + fi + ;; + sco3.2v5*) + lt_cv_sys_max_cmd_len=102400 + ;; + sysv5* | sco5v6* | sysv4.2uw2*) + kargmax=`grep ARG_MAX /etc/conf/cf.d/stune 2>/dev/null` + if test -n "$kargmax"; then + lt_cv_sys_max_cmd_len=`echo $kargmax | $SED 's/.*[[ ]]//'` + else + lt_cv_sys_max_cmd_len=32768 + fi + ;; + *) + lt_cv_sys_max_cmd_len=`(getconf ARG_MAX) 2> /dev/null` + if test -n "$lt_cv_sys_max_cmd_len" && \ + test undefined != "$lt_cv_sys_max_cmd_len"; then + lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \/ 4` + lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \* 3` + else + # Make teststring a little bigger before we do anything with it. + # a 1K string should be a reasonable start. + for i in 1 2 3 4 5 6 7 8; do + teststring=$teststring$teststring + done + SHELL=${SHELL-${CONFIG_SHELL-/bin/sh}} + # If test is not a shell built-in, we'll probably end up computing a + # maximum length that is only half of the actual maximum length, but + # we can't tell. + while { test X`env echo "$teststring$teststring" 2>/dev/null` \ + = "X$teststring$teststring"; } >/dev/null 2>&1 && + test 17 != "$i" # 1/2 MB should be enough + do + i=`expr $i + 1` + teststring=$teststring$teststring + done + # Only check the string length outside the loop. + lt_cv_sys_max_cmd_len=`expr "X$teststring" : ".*" 2>&1` + teststring= + # Add a significant safety factor because C++ compilers can tack on + # massive amounts of additional arguments before passing them to the + # linker. It appears as though 1/2 is a usable value. + lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \/ 2` + fi + ;; + esac +]) +if test -n "$lt_cv_sys_max_cmd_len"; then + AC_MSG_RESULT($lt_cv_sys_max_cmd_len) +else + AC_MSG_RESULT(none) +fi +max_cmd_len=$lt_cv_sys_max_cmd_len +_LT_DECL([], [max_cmd_len], [0], + [What is the maximum length of a command?]) +])# LT_CMD_MAX_LEN + +# Old name: +AU_ALIAS([AC_LIBTOOL_SYS_MAX_CMD_LEN], [LT_CMD_MAX_LEN]) +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([AC_LIBTOOL_SYS_MAX_CMD_LEN], []) + + +# _LT_HEADER_DLFCN +# ---------------- +m4_defun([_LT_HEADER_DLFCN], +[AC_CHECK_HEADERS([dlfcn.h], [], [], [AC_INCLUDES_DEFAULT])dnl +])# _LT_HEADER_DLFCN + + +# _LT_TRY_DLOPEN_SELF (ACTION-IF-TRUE, ACTION-IF-TRUE-W-USCORE, +# ACTION-IF-FALSE, ACTION-IF-CROSS-COMPILING) +# ---------------------------------------------------------------- +m4_defun([_LT_TRY_DLOPEN_SELF], +[m4_require([_LT_HEADER_DLFCN])dnl +if test yes = "$cross_compiling"; then : + [$4] +else + lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2 + lt_status=$lt_dlunknown + cat > conftest.$ac_ext <<_LT_EOF +[#line $LINENO "configure" +#include "confdefs.h" + +#if HAVE_DLFCN_H +#include +#endif + +#include + +#ifdef RTLD_GLOBAL +# define LT_DLGLOBAL RTLD_GLOBAL +#else +# ifdef DL_GLOBAL +# define LT_DLGLOBAL DL_GLOBAL +# else +# define LT_DLGLOBAL 0 +# endif +#endif + +/* We may have to define LT_DLLAZY_OR_NOW in the command line if we + find out it does not work in some platform. */ +#ifndef LT_DLLAZY_OR_NOW +# ifdef RTLD_LAZY +# define LT_DLLAZY_OR_NOW RTLD_LAZY +# else +# ifdef DL_LAZY +# define LT_DLLAZY_OR_NOW DL_LAZY +# else +# ifdef RTLD_NOW +# define LT_DLLAZY_OR_NOW RTLD_NOW +# else +# ifdef DL_NOW +# define LT_DLLAZY_OR_NOW DL_NOW +# else +# define LT_DLLAZY_OR_NOW 0 +# endif +# endif +# endif +# endif +#endif + +/* When -fvisibility=hidden is used, assume the code has been annotated + correspondingly for the symbols needed. */ +#if defined __GNUC__ && (((__GNUC__ == 3) && (__GNUC_MINOR__ >= 3)) || (__GNUC__ > 3)) +int fnord () __attribute__((visibility("default"))); +#endif + +int fnord () { return 42; } +int main () +{ + void *self = dlopen (0, LT_DLGLOBAL|LT_DLLAZY_OR_NOW); + int status = $lt_dlunknown; + + if (self) + { + if (dlsym (self,"fnord")) status = $lt_dlno_uscore; + else + { + if (dlsym( self,"_fnord")) status = $lt_dlneed_uscore; + else puts (dlerror ()); + } + /* dlclose (self); */ + } + else + puts (dlerror ()); + + return status; +}] +_LT_EOF + if AC_TRY_EVAL(ac_link) && test -s "conftest$ac_exeext" 2>/dev/null; then + (./conftest; exit; ) >&AS_MESSAGE_LOG_FD 2>/dev/null + lt_status=$? + case x$lt_status in + x$lt_dlno_uscore) $1 ;; + x$lt_dlneed_uscore) $2 ;; + x$lt_dlunknown|x*) $3 ;; + esac + else : + # compilation failed + $3 + fi +fi +rm -fr conftest* +])# _LT_TRY_DLOPEN_SELF + + +# LT_SYS_DLOPEN_SELF +# ------------------ +AC_DEFUN([LT_SYS_DLOPEN_SELF], +[m4_require([_LT_HEADER_DLFCN])dnl +if test yes != "$enable_dlopen"; then + enable_dlopen=unknown + enable_dlopen_self=unknown + enable_dlopen_self_static=unknown +else + lt_cv_dlopen=no + lt_cv_dlopen_libs= + + case $host_os in + beos*) + lt_cv_dlopen=load_add_on + lt_cv_dlopen_libs= + lt_cv_dlopen_self=yes + ;; + + mingw* | pw32* | cegcc*) + lt_cv_dlopen=LoadLibrary + lt_cv_dlopen_libs= + ;; + + cygwin*) + lt_cv_dlopen=dlopen + lt_cv_dlopen_libs= + ;; + + darwin*) + # if libdl is installed we need to link against it + AC_CHECK_LIB([dl], [dlopen], + [lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-ldl],[ + lt_cv_dlopen=dyld + lt_cv_dlopen_libs= + lt_cv_dlopen_self=yes + ]) + ;; + + tpf*) + # Don't try to run any link tests for TPF. We know it's impossible + # because TPF is a cross-compiler, and we know how we open DSOs. + lt_cv_dlopen=dlopen + lt_cv_dlopen_libs= + lt_cv_dlopen_self=no + ;; + + *) + AC_CHECK_FUNC([shl_load], + [lt_cv_dlopen=shl_load], + [AC_CHECK_LIB([dld], [shl_load], + [lt_cv_dlopen=shl_load lt_cv_dlopen_libs=-ldld], + [AC_CHECK_FUNC([dlopen], + [lt_cv_dlopen=dlopen], + [AC_CHECK_LIB([dl], [dlopen], + [lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-ldl], + [AC_CHECK_LIB([svld], [dlopen], + [lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-lsvld], + [AC_CHECK_LIB([dld], [dld_link], + [lt_cv_dlopen=dld_link lt_cv_dlopen_libs=-ldld]) + ]) + ]) + ]) + ]) + ]) + ;; + esac + + if test no = "$lt_cv_dlopen"; then + enable_dlopen=no + else + enable_dlopen=yes + fi + + case $lt_cv_dlopen in + dlopen) + save_CPPFLAGS=$CPPFLAGS + test yes = "$ac_cv_header_dlfcn_h" && CPPFLAGS="$CPPFLAGS -DHAVE_DLFCN_H" + + save_LDFLAGS=$LDFLAGS + wl=$lt_prog_compiler_wl eval LDFLAGS=\"\$LDFLAGS $export_dynamic_flag_spec\" + + save_LIBS=$LIBS + LIBS="$lt_cv_dlopen_libs $LIBS" + + AC_CACHE_CHECK([whether a program can dlopen itself], + lt_cv_dlopen_self, [dnl + _LT_TRY_DLOPEN_SELF( + lt_cv_dlopen_self=yes, lt_cv_dlopen_self=yes, + lt_cv_dlopen_self=no, lt_cv_dlopen_self=cross) + ]) + + if test yes = "$lt_cv_dlopen_self"; then + wl=$lt_prog_compiler_wl eval LDFLAGS=\"\$LDFLAGS $lt_prog_compiler_static\" + AC_CACHE_CHECK([whether a statically linked program can dlopen itself], + lt_cv_dlopen_self_static, [dnl + _LT_TRY_DLOPEN_SELF( + lt_cv_dlopen_self_static=yes, lt_cv_dlopen_self_static=yes, + lt_cv_dlopen_self_static=no, lt_cv_dlopen_self_static=cross) + ]) + fi + + CPPFLAGS=$save_CPPFLAGS + LDFLAGS=$save_LDFLAGS + LIBS=$save_LIBS + ;; + esac + + case $lt_cv_dlopen_self in + yes|no) enable_dlopen_self=$lt_cv_dlopen_self ;; + *) enable_dlopen_self=unknown ;; + esac + + case $lt_cv_dlopen_self_static in + yes|no) enable_dlopen_self_static=$lt_cv_dlopen_self_static ;; + *) enable_dlopen_self_static=unknown ;; + esac +fi +_LT_DECL([dlopen_support], [enable_dlopen], [0], + [Whether dlopen is supported]) +_LT_DECL([dlopen_self], [enable_dlopen_self], [0], + [Whether dlopen of programs is supported]) +_LT_DECL([dlopen_self_static], [enable_dlopen_self_static], [0], + [Whether dlopen of statically linked programs is supported]) +])# LT_SYS_DLOPEN_SELF + +# Old name: +AU_ALIAS([AC_LIBTOOL_DLOPEN_SELF], [LT_SYS_DLOPEN_SELF]) +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([AC_LIBTOOL_DLOPEN_SELF], []) + + +# _LT_COMPILER_C_O([TAGNAME]) +# --------------------------- +# Check to see if options -c and -o are simultaneously supported by compiler. +# This macro does not hard code the compiler like AC_PROG_CC_C_O. +m4_defun([_LT_COMPILER_C_O], +[m4_require([_LT_DECL_SED])dnl +m4_require([_LT_FILEUTILS_DEFAULTS])dnl +m4_require([_LT_TAG_COMPILER])dnl +AC_CACHE_CHECK([if $compiler supports -c -o file.$ac_objext], + [_LT_TAGVAR(lt_cv_prog_compiler_c_o, $1)], + [_LT_TAGVAR(lt_cv_prog_compiler_c_o, $1)=no + $RM -r conftest 2>/dev/null + mkdir conftest + cd conftest + mkdir out + echo "$lt_simple_compile_test_code" > conftest.$ac_ext + + lt_compiler_flag="-o out/conftest2.$ac_objext" + # Insert the option either (1) after the last *FLAGS variable, or + # (2) before a word containing "conftest.", or (3) at the end. + # Note that $ac_compile itself does not contain backslashes and begins + # with a dollar sign (not a hyphen), so the echo should work correctly. + lt_compile=`echo "$ac_compile" | $SED \ + -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ + -e 's: [[^ ]]*conftest\.: $lt_compiler_flag&:; t' \ + -e 's:$: $lt_compiler_flag:'` + (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&AS_MESSAGE_LOG_FD) + (eval "$lt_compile" 2>out/conftest.err) + ac_status=$? + cat out/conftest.err >&AS_MESSAGE_LOG_FD + echo "$as_me:$LINENO: \$? = $ac_status" >&AS_MESSAGE_LOG_FD + if (exit $ac_status) && test -s out/conftest2.$ac_objext + then + # The compiler can only warn and ignore the option if not recognized + # So say no if there are warnings + $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' > out/conftest.exp + $SED '/^$/d; /^ *+/d' out/conftest.err >out/conftest.er2 + if test ! -s out/conftest.er2 || diff out/conftest.exp out/conftest.er2 >/dev/null; then + _LT_TAGVAR(lt_cv_prog_compiler_c_o, $1)=yes + fi + fi + chmod u+w . 2>&AS_MESSAGE_LOG_FD + $RM conftest* + # SGI C++ compiler will create directory out/ii_files/ for + # template instantiation + test -d out/ii_files && $RM out/ii_files/* && rmdir out/ii_files + $RM out/* && rmdir out + cd .. + $RM -r conftest + $RM conftest* +]) +_LT_TAGDECL([compiler_c_o], [lt_cv_prog_compiler_c_o], [1], + [Does compiler simultaneously support -c and -o options?]) +])# _LT_COMPILER_C_O + + +# _LT_COMPILER_FILE_LOCKS([TAGNAME]) +# ---------------------------------- +# Check to see if we can do hard links to lock some files if needed +m4_defun([_LT_COMPILER_FILE_LOCKS], +[m4_require([_LT_ENABLE_LOCK])dnl +m4_require([_LT_FILEUTILS_DEFAULTS])dnl +_LT_COMPILER_C_O([$1]) + +hard_links=nottested +if test no = "$_LT_TAGVAR(lt_cv_prog_compiler_c_o, $1)" && test no != "$need_locks"; then + # do not overwrite the value of need_locks provided by the user + AC_MSG_CHECKING([if we can lock with hard links]) + hard_links=yes + $RM conftest* + ln conftest.a conftest.b 2>/dev/null && hard_links=no + touch conftest.a + ln conftest.a conftest.b 2>&5 || hard_links=no + ln conftest.a conftest.b 2>/dev/null && hard_links=no + AC_MSG_RESULT([$hard_links]) + if test no = "$hard_links"; then + AC_MSG_WARN(['$CC' does not support '-c -o', so 'make -j' may be unsafe]) + need_locks=warn + fi +else + need_locks=no +fi +_LT_DECL([], [need_locks], [1], [Must we lock files when doing compilation?]) +])# _LT_COMPILER_FILE_LOCKS + + +# _LT_CHECK_OBJDIR +# ---------------- +m4_defun([_LT_CHECK_OBJDIR], +[AC_CACHE_CHECK([for objdir], [lt_cv_objdir], +[rm -f .libs 2>/dev/null +mkdir .libs 2>/dev/null +if test -d .libs; then + lt_cv_objdir=.libs +else + # MS-DOS does not allow filenames that begin with a dot. + lt_cv_objdir=_libs +fi +rmdir .libs 2>/dev/null]) +objdir=$lt_cv_objdir +_LT_DECL([], [objdir], [0], + [The name of the directory that contains temporary libtool files])dnl +m4_pattern_allow([LT_OBJDIR])dnl +AC_DEFINE_UNQUOTED([LT_OBJDIR], "$lt_cv_objdir/", + [Define to the sub-directory where libtool stores uninstalled libraries.]) +])# _LT_CHECK_OBJDIR + + +# _LT_LINKER_HARDCODE_LIBPATH([TAGNAME]) +# -------------------------------------- +# Check hardcoding attributes. +m4_defun([_LT_LINKER_HARDCODE_LIBPATH], +[AC_MSG_CHECKING([how to hardcode library paths into programs]) +_LT_TAGVAR(hardcode_action, $1)= +if test -n "$_LT_TAGVAR(hardcode_libdir_flag_spec, $1)" || + test -n "$_LT_TAGVAR(runpath_var, $1)" || + test yes = "$_LT_TAGVAR(hardcode_automatic, $1)"; then + + # We can hardcode non-existent directories. + if test no != "$_LT_TAGVAR(hardcode_direct, $1)" && + # If the only mechanism to avoid hardcoding is shlibpath_var, we + # have to relink, otherwise we might link with an installed library + # when we should be linking with a yet-to-be-installed one + ## test no != "$_LT_TAGVAR(hardcode_shlibpath_var, $1)" && + test no != "$_LT_TAGVAR(hardcode_minus_L, $1)"; then + # Linking always hardcodes the temporary library directory. + _LT_TAGVAR(hardcode_action, $1)=relink + else + # We can link without hardcoding, and we can hardcode nonexisting dirs. + _LT_TAGVAR(hardcode_action, $1)=immediate + fi +else + # We cannot hardcode anything, or else we can only hardcode existing + # directories. + _LT_TAGVAR(hardcode_action, $1)=unsupported +fi +AC_MSG_RESULT([$_LT_TAGVAR(hardcode_action, $1)]) + +if test relink = "$_LT_TAGVAR(hardcode_action, $1)" || + test yes = "$_LT_TAGVAR(inherit_rpath, $1)"; then + # Fast installation is not supported + enable_fast_install=no +elif test yes = "$shlibpath_overrides_runpath" || + test no = "$enable_shared"; then + # Fast installation is not necessary + enable_fast_install=needless +fi +_LT_TAGDECL([], [hardcode_action], [0], + [How to hardcode a shared library path into an executable]) +])# _LT_LINKER_HARDCODE_LIBPATH + + +# _LT_CMD_STRIPLIB +# ---------------- +m4_defun([_LT_CMD_STRIPLIB], +[m4_require([_LT_DECL_EGREP]) +striplib= +old_striplib= +AC_MSG_CHECKING([whether stripping libraries is possible]) +if test -z "$STRIP"; then + AC_MSG_RESULT([no]) +else + if $STRIP -V 2>&1 | $GREP "GNU strip" >/dev/null; then + old_striplib="$STRIP --strip-debug" + striplib="$STRIP --strip-unneeded" + AC_MSG_RESULT([yes]) + else + case $host_os in + darwin*) + # FIXME - insert some real tests, host_os isn't really good enough + striplib="$STRIP -x" + old_striplib="$STRIP -S" + AC_MSG_RESULT([yes]) + ;; + freebsd*) + if $STRIP -V 2>&1 | $GREP "elftoolchain" >/dev/null; then + old_striplib="$STRIP --strip-debug" + striplib="$STRIP --strip-unneeded" + AC_MSG_RESULT([yes]) + else + AC_MSG_RESULT([no]) + fi + ;; + *) + AC_MSG_RESULT([no]) + ;; + esac + fi +fi +_LT_DECL([], [old_striplib], [1], [Commands to strip libraries]) +_LT_DECL([], [striplib], [1]) +])# _LT_CMD_STRIPLIB + + +# _LT_PREPARE_MUNGE_PATH_LIST +# --------------------------- +# Make sure func_munge_path_list() is defined correctly. +m4_defun([_LT_PREPARE_MUNGE_PATH_LIST], +[[# func_munge_path_list VARIABLE PATH +# ----------------------------------- +# VARIABLE is name of variable containing _space_ separated list of +# directories to be munged by the contents of PATH, which is string +# having a format: +# "DIR[:DIR]:" +# string "DIR[ DIR]" will be prepended to VARIABLE +# ":DIR[:DIR]" +# string "DIR[ DIR]" will be appended to VARIABLE +# "DIRP[:DIRP]::[DIRA:]DIRA" +# string "DIRP[ DIRP]" will be prepended to VARIABLE and string +# "DIRA[ DIRA]" will be appended to VARIABLE +# "DIR[:DIR]" +# VARIABLE will be replaced by "DIR[ DIR]" +func_munge_path_list () +{ + case x@S|@2 in + x) + ;; + *:) + eval @S|@1=\"`$ECHO @S|@2 | $SED 's/:/ /g'` \@S|@@S|@1\" + ;; + x:*) + eval @S|@1=\"\@S|@@S|@1 `$ECHO @S|@2 | $SED 's/:/ /g'`\" + ;; + *::*) + eval @S|@1=\"\@S|@@S|@1\ `$ECHO @S|@2 | $SED -e 's/.*:://' -e 's/:/ /g'`\" + eval @S|@1=\"`$ECHO @S|@2 | $SED -e 's/::.*//' -e 's/:/ /g'`\ \@S|@@S|@1\" + ;; + *) + eval @S|@1=\"`$ECHO @S|@2 | $SED 's/:/ /g'`\" + ;; + esac +} +]])# _LT_PREPARE_PATH_LIST + + +# _LT_SYS_DYNAMIC_LINKER([TAG]) +# ----------------------------- +# PORTME Fill in your ld.so characteristics +m4_defun([_LT_SYS_DYNAMIC_LINKER], +[AC_REQUIRE([AC_CANONICAL_HOST])dnl +m4_require([_LT_DECL_EGREP])dnl +m4_require([_LT_FILEUTILS_DEFAULTS])dnl +m4_require([_LT_DECL_OBJDUMP])dnl +m4_require([_LT_DECL_SED])dnl +m4_require([_LT_CHECK_SHELL_FEATURES])dnl +m4_require([_LT_PREPARE_MUNGE_PATH_LIST])dnl +AC_MSG_CHECKING([dynamic linker characteristics]) +m4_if([$1], + [], [ +if test yes = "$GCC"; then + case $host_os in + darwin*) lt_awk_arg='/^libraries:/,/LR/' ;; + *) lt_awk_arg='/^libraries:/' ;; + esac + case $host_os in + mingw* | cegcc*) lt_sed_strip_eq='s|=\([[A-Za-z]]:\)|\1|g' ;; + *) lt_sed_strip_eq='s|=/|/|g' ;; + esac + lt_search_path_spec=`$CC -print-search-dirs | awk $lt_awk_arg | $SED -e "s/^libraries://" -e $lt_sed_strip_eq` + case $lt_search_path_spec in + *\;*) + # if the path contains ";" then we assume it to be the separator + # otherwise default to the standard path separator (i.e. ":") - it is + # assumed that no part of a normal pathname contains ";" but that should + # okay in the real world where ";" in dirpaths is itself problematic. + lt_search_path_spec=`$ECHO "$lt_search_path_spec" | $SED 's/;/ /g'` + ;; + *) + lt_search_path_spec=`$ECHO "$lt_search_path_spec" | $SED "s/$PATH_SEPARATOR/ /g"` + ;; + esac + # Ok, now we have the path, separated by spaces, we can step through it + # and add multilib dir if necessary... + lt_tmp_lt_search_path_spec= + lt_multi_os_dir=/`$CC $CPPFLAGS $CFLAGS $LDFLAGS -print-multi-os-directory 2>/dev/null` + # ...but if some path component already ends with the multilib dir we assume + # that all is fine and trust -print-search-dirs as is (GCC 4.2? or newer). + case "$lt_multi_os_dir; $lt_search_path_spec " in + "/; "* | "/.; "* | "/./; "* | *"$lt_multi_os_dir "* | *"$lt_multi_os_dir/ "*) + lt_multi_os_dir= + ;; + esac + for lt_sys_path in $lt_search_path_spec; do + if test -d "$lt_sys_path$lt_multi_os_dir"; then + lt_tmp_lt_search_path_spec="$lt_tmp_lt_search_path_spec $lt_sys_path$lt_multi_os_dir" + elif test -n "$lt_multi_os_dir"; then + test -d "$lt_sys_path" && \ + lt_tmp_lt_search_path_spec="$lt_tmp_lt_search_path_spec $lt_sys_path" + fi + done + lt_search_path_spec=`$ECHO "$lt_tmp_lt_search_path_spec" | awk ' +BEGIN {RS = " "; FS = "/|\n";} { + lt_foo = ""; + lt_count = 0; + for (lt_i = NF; lt_i > 0; lt_i--) { + if ($lt_i != "" && $lt_i != ".") { + if ($lt_i == "..") { + lt_count++; + } else { + if (lt_count == 0) { + lt_foo = "/" $lt_i lt_foo; + } else { + lt_count--; + } + } + } + } + if (lt_foo != "") { lt_freq[[lt_foo]]++; } + if (lt_freq[[lt_foo]] == 1) { print lt_foo; } +}'` + # AWK program above erroneously prepends '/' to C:/dos/paths + # for these hosts. + case $host_os in + mingw* | cegcc*) lt_search_path_spec=`$ECHO "$lt_search_path_spec" |\ + $SED 's|/\([[A-Za-z]]:\)|\1|g'` ;; + esac + sys_lib_search_path_spec=`$ECHO "$lt_search_path_spec" | $lt_NL2SP` +else + sys_lib_search_path_spec="/lib /usr/lib /usr/local/lib" +fi]) +library_names_spec= +libname_spec='lib$name' +soname_spec= +shrext_cmds=.so +postinstall_cmds= +postuninstall_cmds= +finish_cmds= +finish_eval= +shlibpath_var= +shlibpath_overrides_runpath=unknown +version_type=none +dynamic_linker="$host_os ld.so" +sys_lib_dlsearch_path_spec="/lib /usr/lib" +need_lib_prefix=unknown +hardcode_into_libs=no + +# when you set need_version to no, make sure it does not cause -set_version +# flags to be left without arguments +need_version=unknown + +AC_ARG_VAR([LT_SYS_LIBRARY_PATH], +[User-defined run-time library search path.]) + +case $host_os in +aix3*) + version_type=linux # correct to gnu/linux during the next big refactor + library_names_spec='$libname$release$shared_ext$versuffix $libname.a' + shlibpath_var=LIBPATH + + # AIX 3 has no versioning support, so we append a major version to the name. + soname_spec='$libname$release$shared_ext$major' + ;; + +aix[[4-9]]*) + version_type=linux # correct to gnu/linux during the next big refactor + need_lib_prefix=no + need_version=no + hardcode_into_libs=yes + if test ia64 = "$host_cpu"; then + # AIX 5 supports IA64 + library_names_spec='$libname$release$shared_ext$major $libname$release$shared_ext$versuffix $libname$shared_ext' + shlibpath_var=LD_LIBRARY_PATH + else + # With GCC up to 2.95.x, collect2 would create an import file + # for dependence libraries. The import file would start with + # the line '#! .'. This would cause the generated library to + # depend on '.', always an invalid library. This was fixed in + # development snapshots of GCC prior to 3.0. + case $host_os in + aix4 | aix4.[[01]] | aix4.[[01]].*) + if { echo '#if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 97)' + echo ' yes ' + echo '#endif'; } | $CC -E - | $GREP yes > /dev/null; then + : + else + can_build_shared=no + fi + ;; + esac + # Using Import Files as archive members, it is possible to support + # filename-based versioning of shared library archives on AIX. While + # this would work for both with and without runtime linking, it will + # prevent static linking of such archives. So we do filename-based + # shared library versioning with .so extension only, which is used + # when both runtime linking and shared linking is enabled. + # Unfortunately, runtime linking may impact performance, so we do + # not want this to be the default eventually. Also, we use the + # versioned .so libs for executables only if there is the -brtl + # linker flag in LDFLAGS as well, or --with-aix-soname=svr4 only. + # To allow for filename-based versioning support, we need to create + # libNAME.so.V as an archive file, containing: + # *) an Import File, referring to the versioned filename of the + # archive as well as the shared archive member, telling the + # bitwidth (32 or 64) of that shared object, and providing the + # list of exported symbols of that shared object, eventually + # decorated with the 'weak' keyword + # *) the shared object with the F_LOADONLY flag set, to really avoid + # it being seen by the linker. + # At run time we better use the real file rather than another symlink, + # but for link time we create the symlink libNAME.so -> libNAME.so.V + + case $with_aix_soname,$aix_use_runtimelinking in + # AIX (on Power*) has no versioning support, so currently we cannot hardcode correct + # soname into executable. Probably we can add versioning support to + # collect2, so additional links can be useful in future. + aix,yes) # traditional libtool + dynamic_linker='AIX unversionable lib.so' + # If using run time linking (on AIX 4.2 or later) use lib.so + # instead of lib.a to let people know that these are not + # typical AIX shared libraries. + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + ;; + aix,no) # traditional AIX only + dynamic_linker='AIX lib.a[(]lib.so.V[)]' + # We preserve .a as extension for shared libraries through AIX4.2 + # and later when we are not doing run time linking. + library_names_spec='$libname$release.a $libname.a' + soname_spec='$libname$release$shared_ext$major' + ;; + svr4,*) # full svr4 only + dynamic_linker="AIX lib.so.V[(]$shared_archive_member_spec.o[)]" + library_names_spec='$libname$release$shared_ext$major $libname$shared_ext' + # We do not specify a path in Import Files, so LIBPATH fires. + shlibpath_overrides_runpath=yes + ;; + *,yes) # both, prefer svr4 + dynamic_linker="AIX lib.so.V[(]$shared_archive_member_spec.o[)], lib.a[(]lib.so.V[)]" + library_names_spec='$libname$release$shared_ext$major $libname$shared_ext' + # unpreferred sharedlib libNAME.a needs extra handling + postinstall_cmds='test -n "$linkname" || linkname="$realname"~func_stripname "" ".so" "$linkname"~$install_shared_prog "$dir/$func_stripname_result.$libext" "$destdir/$func_stripname_result.$libext"~test -z "$tstripme" || test -z "$striplib" || $striplib "$destdir/$func_stripname_result.$libext"' + postuninstall_cmds='for n in $library_names $old_library; do :; done~func_stripname "" ".so" "$n"~test "$func_stripname_result" = "$n" || func_append rmfiles " $odir/$func_stripname_result.$libext"' + # We do not specify a path in Import Files, so LIBPATH fires. + shlibpath_overrides_runpath=yes + ;; + *,no) # both, prefer aix + dynamic_linker="AIX lib.a[(]lib.so.V[)], lib.so.V[(]$shared_archive_member_spec.o[)]" + library_names_spec='$libname$release.a $libname.a' + soname_spec='$libname$release$shared_ext$major' + # unpreferred sharedlib libNAME.so.V and symlink libNAME.so need extra handling + postinstall_cmds='test -z "$dlname" || $install_shared_prog $dir/$dlname $destdir/$dlname~test -z "$tstripme" || test -z "$striplib" || $striplib $destdir/$dlname~test -n "$linkname" || linkname=$realname~func_stripname "" ".a" "$linkname"~(cd "$destdir" && $LN_S -f $dlname $func_stripname_result.so)' + postuninstall_cmds='test -z "$dlname" || func_append rmfiles " $odir/$dlname"~for n in $old_library $library_names; do :; done~func_stripname "" ".a" "$n"~func_append rmfiles " $odir/$func_stripname_result.so"' + ;; + esac + shlibpath_var=LIBPATH + fi + ;; + +amigaos*) + case $host_cpu in + powerpc) + # Since July 2007 AmigaOS4 officially supports .so libraries. + # When compiling the executable, add -use-dynld -Lsobjs: to the compileline. + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + ;; + m68k) + library_names_spec='$libname.ixlibrary $libname.a' + # Create ${libname}_ixlibrary.a entries in /sys/libs. + finish_eval='for lib in `ls $libdir/*.ixlibrary 2>/dev/null`; do libname=`func_echo_all "$lib" | $SED '\''s%^.*/\([[^/]]*\)\.ixlibrary$%\1%'\''`; $RM /sys/libs/${libname}_ixlibrary.a; $show "cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a"; cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a || exit 1; done' + ;; + esac + ;; + +beos*) + library_names_spec='$libname$shared_ext' + dynamic_linker="$host_os ld.so" + shlibpath_var=LIBRARY_PATH + ;; + +bsdi[[45]]*) + version_type=linux # correct to gnu/linux during the next big refactor + need_version=no + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + finish_cmds='PATH="\$PATH:/sbin" ldconfig $libdir' + shlibpath_var=LD_LIBRARY_PATH + sys_lib_search_path_spec="/shlib /usr/lib /usr/X11/lib /usr/contrib/lib /lib /usr/local/lib" + sys_lib_dlsearch_path_spec="/shlib /usr/lib /usr/local/lib" + # the default ld.so.conf also contains /usr/contrib/lib and + # /usr/X11R6/lib (/usr/X11 is a link to /usr/X11R6), but let us allow + # libtool to hard-code these into programs + ;; + +cygwin* | mingw* | pw32* | cegcc*) + version_type=windows + shrext_cmds=.dll + need_version=no + need_lib_prefix=no + + case $GCC,$cc_basename in + yes,*) + # gcc + library_names_spec='$libname.dll.a' + # DLL is installed to $(libdir)/../bin by postinstall_cmds + postinstall_cmds='base_file=`basename \$file`~ + dlpath=`$SHELL 2>&1 -c '\''. $dir/'\''\$base_file'\''i; echo \$dlname'\''`~ + dldir=$destdir/`dirname \$dlpath`~ + test -d \$dldir || mkdir -p \$dldir~ + $install_prog $dir/$dlname \$dldir/$dlname~ + chmod a+x \$dldir/$dlname~ + if test -n '\''$stripme'\'' && test -n '\''$striplib'\''; then + eval '\''$striplib \$dldir/$dlname'\'' || exit \$?; + fi' + postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\''. $file; echo \$dlname'\''`~ + dlpath=$dir/\$dldll~ + $RM \$dlpath' + shlibpath_overrides_runpath=yes + + case $host_os in + cygwin*) + # Cygwin DLLs use 'cyg' prefix rather than 'lib' + soname_spec='`echo $libname | $SED -e 's/^lib/cyg/'``echo $release | $SED -e 's/[[.]]/-/g'`$versuffix$shared_ext' +m4_if([$1], [],[ + sys_lib_search_path_spec="$sys_lib_search_path_spec /usr/lib/w32api"]) + ;; + mingw* | cegcc*) + # MinGW DLLs use traditional 'lib' prefix + soname_spec='$libname`echo $release | $SED -e 's/[[.]]/-/g'`$versuffix$shared_ext' + ;; + pw32*) + # pw32 DLLs use 'pw' prefix rather than 'lib' + library_names_spec='`echo $libname | $SED -e 's/^lib/pw/'``echo $release | $SED -e 's/[[.]]/-/g'`$versuffix$shared_ext' + ;; + esac + dynamic_linker='Win32 ld.exe' + ;; + + *,cl* | *,icl*) + # Native MSVC or ICC + libname_spec='$name' + soname_spec='$libname`echo $release | $SED -e 's/[[.]]/-/g'`$versuffix$shared_ext' + library_names_spec='$libname.dll.lib' + + case $build_os in + mingw*) + sys_lib_search_path_spec= + lt_save_ifs=$IFS + IFS=';' + for lt_path in $LIB + do + IFS=$lt_save_ifs + # Let DOS variable expansion print the short 8.3 style file name. + lt_path=`cd "$lt_path" 2>/dev/null && cmd //C "for %i in (".") do @echo %~si"` + sys_lib_search_path_spec="$sys_lib_search_path_spec $lt_path" + done + IFS=$lt_save_ifs + # Convert to MSYS style. + sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e 's|\\\\|/|g' -e 's| \\([[a-zA-Z]]\\):| /\\1|g' -e 's|^ ||'` + ;; + cygwin*) + # Convert to unix form, then to dos form, then back to unix form + # but this time dos style (no spaces!) so that the unix form looks + # like /cygdrive/c/PROGRA~1:/cygdr... + sys_lib_search_path_spec=`cygpath --path --unix "$LIB"` + sys_lib_search_path_spec=`cygpath --path --dos "$sys_lib_search_path_spec" 2>/dev/null` + sys_lib_search_path_spec=`cygpath --path --unix "$sys_lib_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` + ;; + *) + sys_lib_search_path_spec=$LIB + if $ECHO "$sys_lib_search_path_spec" | [$GREP ';[c-zC-Z]:/' >/dev/null]; then + # It is most probably a Windows format PATH. + sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e 's/;/ /g'` + else + sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` + fi + # FIXME: find the short name or the path components, as spaces are + # common. (e.g. "Program Files" -> "PROGRA~1") + ;; + esac + + # DLL is installed to $(libdir)/../bin by postinstall_cmds + postinstall_cmds='base_file=`basename \$file`~ + dlpath=`$SHELL 2>&1 -c '\''. $dir/'\''\$base_file'\''i; echo \$dlname'\''`~ + dldir=$destdir/`dirname \$dlpath`~ + test -d \$dldir || mkdir -p \$dldir~ + $install_prog $dir/$dlname \$dldir/$dlname' + postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\''. $file; echo \$dlname'\''`~ + dlpath=$dir/\$dldll~ + $RM \$dlpath' + shlibpath_overrides_runpath=yes + dynamic_linker='Win32 link.exe' + ;; + + *) + # Assume MSVC and ICC wrapper + library_names_spec='$libname`echo $release | $SED -e 's/[[.]]/-/g'`$versuffix$shared_ext $libname.lib' + dynamic_linker='Win32 ld.exe' + ;; + esac + # FIXME: first we should search . and the directory the executable is in + shlibpath_var=PATH + ;; + +darwin* | rhapsody*) + dynamic_linker="$host_os dyld" + version_type=darwin + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$major$shared_ext $libname$shared_ext' + soname_spec='$libname$release$major$shared_ext' + shlibpath_overrides_runpath=yes + shlibpath_var=DYLD_LIBRARY_PATH + shrext_cmds='`test .$module = .yes && echo .so || echo .dylib`' +m4_if([$1], [],[ + sys_lib_search_path_spec="$sys_lib_search_path_spec /usr/local/lib"]) + sys_lib_dlsearch_path_spec='/usr/local/lib /lib /usr/lib' + ;; + +dgux*) + version_type=linux # correct to gnu/linux during the next big refactor + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + shlibpath_var=LD_LIBRARY_PATH + ;; + +freebsd* | dragonfly* | midnightbsd*) + # DragonFly does not have aout. When/if they implement a new + # versioning mechanism, adjust this. + if test -x /usr/bin/objformat; then + objformat=`/usr/bin/objformat` + else + case $host_os in + freebsd[[23]].*) objformat=aout ;; + *) objformat=elf ;; + esac + fi + version_type=freebsd-$objformat + case $version_type in + freebsd-elf*) + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + need_version=no + need_lib_prefix=no + ;; + freebsd-*) + library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix' + need_version=yes + ;; + esac + shlibpath_var=LD_LIBRARY_PATH + case $host_os in + freebsd2.*) + shlibpath_overrides_runpath=yes + ;; + freebsd3.[[01]]* | freebsdelf3.[[01]]*) + shlibpath_overrides_runpath=yes + hardcode_into_libs=yes + ;; + freebsd3.[[2-9]]* | freebsdelf3.[[2-9]]* | \ + freebsd4.[[0-5]] | freebsdelf4.[[0-5]] | freebsd4.1.1 | freebsdelf4.1.1) + shlibpath_overrides_runpath=no + hardcode_into_libs=yes + ;; + *) # from 4.6 on, and DragonFly + shlibpath_overrides_runpath=yes + hardcode_into_libs=yes + ;; + esac + ;; + +haiku*) + version_type=linux # correct to gnu/linux during the next big refactor + need_lib_prefix=no + need_version=no + dynamic_linker="$host_os runtime_loader" + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + shlibpath_var=LIBRARY_PATH + shlibpath_overrides_runpath=no + sys_lib_dlsearch_path_spec='/boot/home/config/lib /boot/common/lib /boot/system/lib' + hardcode_into_libs=yes + ;; + +hpux9* | hpux10* | hpux11*) + # Give a soname corresponding to the major version so that dld.sl refuses to + # link against other versions. + version_type=sunos + need_lib_prefix=no + need_version=no + case $host_cpu in + ia64*) + shrext_cmds='.so' + hardcode_into_libs=yes + dynamic_linker="$host_os dld.so" + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=yes # Unless +noenvvar is specified. + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + if test 32 = "$HPUX_IA64_MODE"; then + sys_lib_search_path_spec="/usr/lib/hpux32 /usr/local/lib/hpux32 /usr/local/lib" + sys_lib_dlsearch_path_spec=/usr/lib/hpux32 + else + sys_lib_search_path_spec="/usr/lib/hpux64 /usr/local/lib/hpux64" + sys_lib_dlsearch_path_spec=/usr/lib/hpux64 + fi + ;; + hppa*64*) + shrext_cmds='.sl' + hardcode_into_libs=yes + dynamic_linker="$host_os dld.sl" + shlibpath_var=LD_LIBRARY_PATH # How should we handle SHLIB_PATH + shlibpath_overrides_runpath=yes # Unless +noenvvar is specified. + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + sys_lib_search_path_spec="/usr/lib/pa20_64 /usr/ccs/lib/pa20_64" + sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec + ;; + *) + shrext_cmds='.sl' + dynamic_linker="$host_os dld.sl" + shlibpath_var=SHLIB_PATH + shlibpath_overrides_runpath=no # +s is required to enable SHLIB_PATH + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + ;; + esac + # HP-UX runs *really* slowly unless shared libraries are mode 555, ... + postinstall_cmds='chmod 555 $lib' + # or fails outright, so override atomically: + install_override_mode=555 + ;; + +interix[[3-9]]*) + version_type=linux # correct to gnu/linux during the next big refactor + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + dynamic_linker='Interix 3.x ld.so.1 (PE, like ELF)' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=no + hardcode_into_libs=yes + ;; + +irix5* | irix6* | nonstopux*) + case $host_os in + nonstopux*) version_type=nonstopux ;; + *) + if test yes = "$lt_cv_prog_gnu_ld"; then + version_type=linux # correct to gnu/linux during the next big refactor + else + version_type=irix + fi ;; + esac + need_lib_prefix=no + need_version=no + soname_spec='$libname$release$shared_ext$major' + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$release$shared_ext $libname$shared_ext' + case $host_os in + irix5* | nonstopux*) + libsuff= shlibsuff= + ;; + *) + case $LD in # libtool.m4 will add one of these switches to LD + *-32|*"-32 "|*-melf32bsmip|*"-melf32bsmip ") + libsuff= shlibsuff= libmagic=32-bit;; + *-n32|*"-n32 "|*-melf32bmipn32|*"-melf32bmipn32 ") + libsuff=32 shlibsuff=N32 libmagic=N32;; + *-64|*"-64 "|*-melf64bmip|*"-melf64bmip ") + libsuff=64 shlibsuff=64 libmagic=64-bit;; + *) libsuff= shlibsuff= libmagic=never-match;; + esac + ;; + esac + shlibpath_var=LD_LIBRARY${shlibsuff}_PATH + shlibpath_overrides_runpath=no + sys_lib_search_path_spec="/usr/lib$libsuff /lib$libsuff /usr/local/lib$libsuff" + sys_lib_dlsearch_path_spec="/usr/lib$libsuff /lib$libsuff" + hardcode_into_libs=yes + ;; + +# No shared lib support for Linux oldld, aout, or coff. +linux*oldld* | linux*aout* | linux*coff*) + dynamic_linker=no + ;; + +linux*android*) + version_type=none # Android doesn't support versioned libraries. + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$shared_ext' + soname_spec='$libname$release$shared_ext' + finish_cmds= + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=yes + + # This implies no fast_install, which is unacceptable. + # Some rework will be needed to allow for fast_install + # before this can be enabled. + hardcode_into_libs=yes + + dynamic_linker='Android linker' + # Don't embed -rpath directories since the linker doesn't support them. + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' + ;; + +# This must be glibc/ELF. +linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) + version_type=linux # correct to gnu/linux during the next big refactor + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + finish_cmds='PATH="\$PATH:/sbin" ldconfig -n $libdir' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=no + + # Some binutils ld are patched to set DT_RUNPATH + AC_CACHE_VAL([lt_cv_shlibpath_overrides_runpath], + [lt_cv_shlibpath_overrides_runpath=no + save_LDFLAGS=$LDFLAGS + save_libdir=$libdir + eval "libdir=/foo; wl=\"$_LT_TAGVAR(lt_prog_compiler_wl, $1)\"; \ + LDFLAGS=\"\$LDFLAGS $_LT_TAGVAR(hardcode_libdir_flag_spec, $1)\"" + AC_LINK_IFELSE([AC_LANG_PROGRAM([],[])], + [AS_IF([ ($OBJDUMP -p conftest$ac_exeext) 2>/dev/null | grep "RUNPATH.*$libdir" >/dev/null], + [lt_cv_shlibpath_overrides_runpath=yes])]) + LDFLAGS=$save_LDFLAGS + libdir=$save_libdir + ]) + shlibpath_overrides_runpath=$lt_cv_shlibpath_overrides_runpath + + # This implies no fast_install, which is unacceptable. + # Some rework will be needed to allow for fast_install + # before this can be enabled. + hardcode_into_libs=yes + + # Ideally, we could use ldconfig to report *all* directores which are + # searched for libraries, however this is still not possible. Aside from not + # being certain /sbin/ldconfig is available, command + # 'ldconfig -N -X -v | grep ^/' on 64bit Fedora does not report /usr/lib64, + # even though it is searched at run-time. Try to do the best guess by + # appending ld.so.conf contents (and includes) to the search path. + if test -f /etc/ld.so.conf; then + lt_ld_extra=`awk '/^include / { system(sprintf("cd /etc; cat %s 2>/dev/null", \[$]2)); skip = 1; } { if (!skip) print \[$]0; skip = 0; }' < /etc/ld.so.conf | $SED -e 's/#.*//;/^[ ]*hwcap[ ]/d;s/[:, ]/ /g;s/=[^=]*$//;s/=[^= ]* / /g;s/"//g;/^$/d' | tr '\n' ' '` + sys_lib_dlsearch_path_spec="/lib /usr/lib $lt_ld_extra" + fi + + # We used to test for /lib/ld.so.1 and disable shared libraries on + # powerpc, because MkLinux only supported shared libraries with the + # GNU dynamic linker. Since this was broken with cross compilers, + # most powerpc-linux boxes support dynamic linking these days and + # people can always --disable-shared, the test was removed, and we + # assume the GNU/Linux dynamic linker is in use. + dynamic_linker='GNU/Linux ld.so' + ;; + +netbsd*) + version_type=sunos + need_lib_prefix=no + need_version=no + if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then + library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix' + finish_cmds='PATH="\$PATH:/sbin" ldconfig -m $libdir' + dynamic_linker='NetBSD (a.out) ld.so' + else + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + dynamic_linker='NetBSD ld.elf_so' + fi + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=yes + hardcode_into_libs=yes + ;; + +newsos6) + version_type=linux # correct to gnu/linux during the next big refactor + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=yes + ;; + +*nto* | *qnx*) + version_type=qnx + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=no + hardcode_into_libs=yes + dynamic_linker='ldqnx.so' + ;; + +openbsd* | bitrig*) + version_type=sunos + sys_lib_dlsearch_path_spec=/usr/lib + need_lib_prefix=no + if test -z "`echo __ELF__ | $CC -E - | $GREP __ELF__`"; then + need_version=no + else + need_version=yes + fi + library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix' + finish_cmds='PATH="\$PATH:/sbin" ldconfig -m $libdir' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=yes + ;; + +os2*) + libname_spec='$name' + version_type=windows + shrext_cmds=.dll + need_version=no + need_lib_prefix=no + # OS/2 can only load a DLL with a base name of 8 characters or less. + soname_spec='`test -n "$os2dllname" && libname="$os2dllname"; + v=$($ECHO $release$versuffix | tr -d .-); + n=$($ECHO $libname | cut -b -$((8 - ${#v})) | tr . _); + $ECHO $n$v`$shared_ext' + library_names_spec='${libname}_dll.$libext' + dynamic_linker='OS/2 ld.exe' + shlibpath_var=BEGINLIBPATH + sys_lib_search_path_spec="/lib /usr/lib /usr/local/lib" + sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec + postinstall_cmds='base_file=`basename \$file`~ + dlpath=`$SHELL 2>&1 -c '\''. $dir/'\''\$base_file'\''i; $ECHO \$dlname'\''`~ + dldir=$destdir/`dirname \$dlpath`~ + test -d \$dldir || mkdir -p \$dldir~ + $install_prog $dir/$dlname \$dldir/$dlname~ + chmod a+x \$dldir/$dlname~ + if test -n '\''$stripme'\'' && test -n '\''$striplib'\''; then + eval '\''$striplib \$dldir/$dlname'\'' || exit \$?; + fi' + postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\''. $file; $ECHO \$dlname'\''`~ + dlpath=$dir/\$dldll~ + $RM \$dlpath' + ;; + +osf3* | osf4* | osf5*) + version_type=osf + need_lib_prefix=no + need_version=no + soname_spec='$libname$release$shared_ext$major' + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + shlibpath_var=LD_LIBRARY_PATH + sys_lib_search_path_spec="/usr/shlib /usr/ccs/lib /usr/lib/cmplrs/cc /usr/lib /usr/local/lib /var/shlib" + sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec + ;; + +rdos*) + dynamic_linker=no + ;; + +solaris*) + version_type=linux # correct to gnu/linux during the next big refactor + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=yes + hardcode_into_libs=yes + # ldd complains unless libraries are executable + postinstall_cmds='chmod +x $lib' + ;; + +sunos4*) + version_type=sunos + library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix' + finish_cmds='PATH="\$PATH:/usr/etc" ldconfig $libdir' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=yes + if test yes = "$with_gnu_ld"; then + need_lib_prefix=no + fi + need_version=yes + ;; + +sysv4 | sysv4.3*) + version_type=linux # correct to gnu/linux during the next big refactor + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + shlibpath_var=LD_LIBRARY_PATH + case $host_vendor in + sni) + shlibpath_overrides_runpath=no + need_lib_prefix=no + runpath_var=LD_RUN_PATH + ;; + siemens) + need_lib_prefix=no + ;; + motorola) + need_lib_prefix=no + need_version=no + shlibpath_overrides_runpath=no + sys_lib_search_path_spec='/lib /usr/lib /usr/ccs/lib' + ;; + esac + ;; + +sysv4*MP*) + if test -d /usr/nec; then + version_type=linux # correct to gnu/linux during the next big refactor + library_names_spec='$libname$shared_ext.$versuffix $libname$shared_ext.$major $libname$shared_ext' + soname_spec='$libname$shared_ext.$major' + shlibpath_var=LD_LIBRARY_PATH + fi + ;; + +sysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX* | sysv4*uw2*) + version_type=sco + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=yes + hardcode_into_libs=yes + if test yes = "$with_gnu_ld"; then + sys_lib_search_path_spec='/usr/local/lib /usr/gnu/lib /usr/ccs/lib /usr/lib /lib' + else + sys_lib_search_path_spec='/usr/ccs/lib /usr/lib' + case $host_os in + sco3.2v5*) + sys_lib_search_path_spec="$sys_lib_search_path_spec /lib" + ;; + esac + fi + sys_lib_dlsearch_path_spec='/usr/lib' + ;; + +tpf*) + # TPF is a cross-target only. Preferred cross-host = GNU/Linux. + version_type=linux # correct to gnu/linux during the next big refactor + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=no + hardcode_into_libs=yes + ;; + +uts4*) + version_type=linux # correct to gnu/linux during the next big refactor + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + shlibpath_var=LD_LIBRARY_PATH + ;; + +*) + dynamic_linker=no + ;; +esac +AC_MSG_RESULT([$dynamic_linker]) +test no = "$dynamic_linker" && can_build_shared=no + +variables_saved_for_relink="PATH $shlibpath_var $runpath_var" +if test yes = "$GCC"; then + variables_saved_for_relink="$variables_saved_for_relink GCC_EXEC_PREFIX COMPILER_PATH LIBRARY_PATH" +fi + +if test set = "${lt_cv_sys_lib_search_path_spec+set}"; then + sys_lib_search_path_spec=$lt_cv_sys_lib_search_path_spec +fi + +if test set = "${lt_cv_sys_lib_dlsearch_path_spec+set}"; then + sys_lib_dlsearch_path_spec=$lt_cv_sys_lib_dlsearch_path_spec +fi + +# remember unaugmented sys_lib_dlsearch_path content for libtool script decls... +configure_time_dlsearch_path=$sys_lib_dlsearch_path_spec + +# ... but it needs LT_SYS_LIBRARY_PATH munging for other configure-time code +func_munge_path_list sys_lib_dlsearch_path_spec "$LT_SYS_LIBRARY_PATH" + +# to be used as default LT_SYS_LIBRARY_PATH value in generated libtool +configure_time_lt_sys_library_path=$LT_SYS_LIBRARY_PATH + +_LT_DECL([], [variables_saved_for_relink], [1], + [Variables whose values should be saved in libtool wrapper scripts and + restored at link time]) +_LT_DECL([], [need_lib_prefix], [0], + [Do we need the "lib" prefix for modules?]) +_LT_DECL([], [need_version], [0], [Do we need a version for libraries?]) +_LT_DECL([], [version_type], [0], [Library versioning type]) +_LT_DECL([], [runpath_var], [0], [Shared library runtime path variable]) +_LT_DECL([], [shlibpath_var], [0],[Shared library path variable]) +_LT_DECL([], [shlibpath_overrides_runpath], [0], + [Is shlibpath searched before the hard-coded library search path?]) +_LT_DECL([], [libname_spec], [1], [Format of library name prefix]) +_LT_DECL([], [library_names_spec], [1], + [[List of archive names. First name is the real one, the rest are links. + The last name is the one that the linker finds with -lNAME]]) +_LT_DECL([], [soname_spec], [1], + [[The coded name of the library, if different from the real name]]) +_LT_DECL([], [install_override_mode], [1], + [Permission mode override for installation of shared libraries]) +_LT_DECL([], [postinstall_cmds], [2], + [Command to use after installation of a shared archive]) +_LT_DECL([], [postuninstall_cmds], [2], + [Command to use after uninstallation of a shared archive]) +_LT_DECL([], [finish_cmds], [2], + [Commands used to finish a libtool library installation in a directory]) +_LT_DECL([], [finish_eval], [1], + [[As "finish_cmds", except a single script fragment to be evaled but + not shown]]) +_LT_DECL([], [hardcode_into_libs], [0], + [Whether we should hardcode library paths into libraries]) +_LT_DECL([], [sys_lib_search_path_spec], [2], + [Compile-time system search path for libraries]) +_LT_DECL([sys_lib_dlsearch_path_spec], [configure_time_dlsearch_path], [2], + [Detected run-time system search path for libraries]) +_LT_DECL([], [configure_time_lt_sys_library_path], [2], + [Explicit LT_SYS_LIBRARY_PATH set during ./configure time]) +])# _LT_SYS_DYNAMIC_LINKER + + +# _LT_PATH_TOOL_PREFIX(TOOL) +# -------------------------- +# find a file program that can recognize shared library +AC_DEFUN([_LT_PATH_TOOL_PREFIX], +[m4_require([_LT_DECL_EGREP])dnl +AC_MSG_CHECKING([for $1]) +AC_CACHE_VAL(lt_cv_path_MAGIC_CMD, +[case $MAGIC_CMD in +[[\\/*] | ?:[\\/]*]) + lt_cv_path_MAGIC_CMD=$MAGIC_CMD # Let the user override the test with a path. + ;; +*) + lt_save_MAGIC_CMD=$MAGIC_CMD + lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR +dnl $ac_dummy forces splitting on constant user-supplied paths. +dnl POSIX.2 word splitting is done only on the output of word expansions, +dnl not every word. This closes a longstanding sh security hole. + ac_dummy="m4_if([$2], , $PATH, [$2])" + for ac_dir in $ac_dummy; do + IFS=$lt_save_ifs + test -z "$ac_dir" && ac_dir=. + if test -f "$ac_dir/$1"; then + lt_cv_path_MAGIC_CMD=$ac_dir/"$1" + if test -n "$file_magic_test_file"; then + case $deplibs_check_method in + "file_magic "*) + file_magic_regex=`expr "$deplibs_check_method" : "file_magic \(.*\)"` + MAGIC_CMD=$lt_cv_path_MAGIC_CMD + if eval $file_magic_cmd \$file_magic_test_file 2> /dev/null | + $EGREP "$file_magic_regex" > /dev/null; then + : + else + cat <<_LT_EOF 1>&2 + +*** Warning: the command libtool uses to detect shared libraries, +*** $file_magic_cmd, produces output that libtool cannot recognize. +*** The result is that libtool may fail to recognize shared libraries +*** as such. This will affect the creation of libtool libraries that +*** depend on shared libraries, but programs linked with such libtool +*** libraries will work regardless of this problem. Nevertheless, you +*** may want to report the problem to your system manager and/or to +*** bug-libtool@gnu.org + +_LT_EOF + fi ;; + esac + fi + break + fi + done + IFS=$lt_save_ifs + MAGIC_CMD=$lt_save_MAGIC_CMD + ;; +esac]) +MAGIC_CMD=$lt_cv_path_MAGIC_CMD +if test -n "$MAGIC_CMD"; then + AC_MSG_RESULT($MAGIC_CMD) +else + AC_MSG_RESULT(no) +fi +_LT_DECL([], [MAGIC_CMD], [0], + [Used to examine libraries when file_magic_cmd begins with "file"])dnl +])# _LT_PATH_TOOL_PREFIX + +# Old name: +AU_ALIAS([AC_PATH_TOOL_PREFIX], [_LT_PATH_TOOL_PREFIX]) +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([AC_PATH_TOOL_PREFIX], []) + + +# _LT_PATH_MAGIC +# -------------- +# find a file program that can recognize a shared library +m4_defun([_LT_PATH_MAGIC], +[_LT_PATH_TOOL_PREFIX(${ac_tool_prefix}file, /usr/bin$PATH_SEPARATOR$PATH) +if test -z "$lt_cv_path_MAGIC_CMD"; then + if test -n "$ac_tool_prefix"; then + _LT_PATH_TOOL_PREFIX(file, /usr/bin$PATH_SEPARATOR$PATH) + else + MAGIC_CMD=: + fi +fi +])# _LT_PATH_MAGIC + + +# LT_PATH_LD +# ---------- +# find the pathname to the GNU or non-GNU linker +AC_DEFUN([LT_PATH_LD], +[AC_REQUIRE([AC_PROG_CC])dnl +AC_REQUIRE([AC_CANONICAL_HOST])dnl +AC_REQUIRE([AC_CANONICAL_BUILD])dnl +m4_require([_LT_DECL_SED])dnl +m4_require([_LT_DECL_EGREP])dnl +m4_require([_LT_PROG_ECHO_BACKSLASH])dnl + +AC_ARG_WITH([gnu-ld], + [AS_HELP_STRING([--with-gnu-ld], + [assume the C compiler uses GNU ld @<:@default=no@:>@])], + [test no = "$withval" || with_gnu_ld=yes], + [with_gnu_ld=no])dnl + +ac_prog=ld +if test yes = "$GCC"; then + # Check if gcc -print-prog-name=ld gives a path. + AC_MSG_CHECKING([for ld used by $CC]) + case $host in + *-*-mingw*) + # gcc leaves a trailing carriage return, which upsets mingw + ac_prog=`($CC -print-prog-name=ld) 2>&5 | tr -d '\015'` ;; + *) + ac_prog=`($CC -print-prog-name=ld) 2>&5` ;; + esac + case $ac_prog in + # Accept absolute paths. + [[\\/]]* | ?:[[\\/]]*) + re_direlt='/[[^/]][[^/]]*/\.\./' + # Canonicalize the pathname of ld + ac_prog=`$ECHO "$ac_prog"| $SED 's%\\\\%/%g'` + while $ECHO "$ac_prog" | $GREP "$re_direlt" > /dev/null 2>&1; do + ac_prog=`$ECHO $ac_prog| $SED "s%$re_direlt%/%"` + done + test -z "$LD" && LD=$ac_prog + ;; + "") + # If it fails, then pretend we aren't using GCC. + ac_prog=ld + ;; + *) + # If it is relative, then search for the first ld in PATH. + with_gnu_ld=unknown + ;; + esac +elif test yes = "$with_gnu_ld"; then + AC_MSG_CHECKING([for GNU ld]) +else + AC_MSG_CHECKING([for non-GNU ld]) +fi +AC_CACHE_VAL(lt_cv_path_LD, +[if test -z "$LD"; then + lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR + for ac_dir in $PATH; do + IFS=$lt_save_ifs + test -z "$ac_dir" && ac_dir=. + if test -f "$ac_dir/$ac_prog" || test -f "$ac_dir/$ac_prog$ac_exeext"; then + lt_cv_path_LD=$ac_dir/$ac_prog + # Check to see if the program is GNU ld. I'd rather use --version, + # but apparently some variants of GNU ld only accept -v. + # Break only if it was the GNU/non-GNU ld that we prefer. + case `"$lt_cv_path_LD" -v 2>&1 &1 conftest.i +cat conftest.i conftest.i >conftest2.i +: ${lt_DD:=$DD} +AC_PATH_PROGS_FEATURE_CHECK([lt_DD], [dd], +[if "$ac_path_lt_DD" bs=32 count=1 conftest.out 2>/dev/null; then + cmp -s conftest.i conftest.out \ + && ac_cv_path_lt_DD="$ac_path_lt_DD" ac_path_lt_DD_found=: +fi]) +rm -f conftest.i conftest2.i conftest.out]) +])# _LT_PATH_DD + + +# _LT_CMD_TRUNCATE +# ---------------- +# find command to truncate a binary pipe +m4_defun([_LT_CMD_TRUNCATE], +[m4_require([_LT_PATH_DD]) +AC_CACHE_CHECK([how to truncate binary pipes], [lt_cv_truncate_bin], +[printf 0123456789abcdef0123456789abcdef >conftest.i +cat conftest.i conftest.i >conftest2.i +lt_cv_truncate_bin= +if "$ac_cv_path_lt_DD" bs=32 count=1 conftest.out 2>/dev/null; then + cmp -s conftest.i conftest.out \ + && lt_cv_truncate_bin="$ac_cv_path_lt_DD bs=4096 count=1" +fi +rm -f conftest.i conftest2.i conftest.out +test -z "$lt_cv_truncate_bin" && lt_cv_truncate_bin="$SED -e 4q"]) +_LT_DECL([lt_truncate_bin], [lt_cv_truncate_bin], [1], + [Command to truncate a binary pipe]) +])# _LT_CMD_TRUNCATE + + +# _LT_CHECK_MAGIC_METHOD +# ---------------------- +# how to check for library dependencies +# -- PORTME fill in with the dynamic library characteristics +m4_defun([_LT_CHECK_MAGIC_METHOD], +[m4_require([_LT_DECL_EGREP]) +m4_require([_LT_DECL_OBJDUMP]) +AC_CACHE_CHECK([how to recognize dependent libraries], +lt_cv_deplibs_check_method, +[lt_cv_file_magic_cmd='$MAGIC_CMD' +lt_cv_file_magic_test_file= +lt_cv_deplibs_check_method='unknown' +# Need to set the preceding variable on all platforms that support +# interlibrary dependencies. +# 'none' -- dependencies not supported. +# 'unknown' -- same as none, but documents that we really don't know. +# 'pass_all' -- all dependencies passed with no checks. +# 'test_compile' -- check by making test program. +# 'file_magic [[regex]]' -- check by looking for files in library path +# that responds to the $file_magic_cmd with a given extended regex. +# If you have 'file' or equivalent on your system and you're not sure +# whether 'pass_all' will *always* work, you probably want this one. + +case $host_os in +aix[[4-9]]*) + lt_cv_deplibs_check_method=pass_all + ;; + +beos*) + lt_cv_deplibs_check_method=pass_all + ;; + +bsdi[[45]]*) + lt_cv_deplibs_check_method='file_magic ELF [[0-9]][[0-9]]*-bit [[ML]]SB (shared object|dynamic lib)' + lt_cv_file_magic_cmd='$FILECMD -L' + lt_cv_file_magic_test_file=/shlib/libc.so + ;; + +cygwin*) + # func_win32_libid is a shell function defined in ltmain.sh + lt_cv_deplibs_check_method='file_magic ^x86 archive import|^x86 DLL' + lt_cv_file_magic_cmd='func_win32_libid' + ;; + +mingw* | pw32*) + # Base MSYS/MinGW do not provide the 'file' command needed by + # func_win32_libid shell function, so use a weaker test based on 'objdump', + # unless we find 'file', for example because we are cross-compiling. + if ( file / ) >/dev/null 2>&1; then + lt_cv_deplibs_check_method='file_magic ^x86 archive import|^x86 DLL' + lt_cv_file_magic_cmd='func_win32_libid' + else + # Keep this pattern in sync with the one in func_win32_libid. + lt_cv_deplibs_check_method='file_magic file format (pei*-i386(.*architecture: i386)?|pe-arm-wince|pe-x86-64)' + lt_cv_file_magic_cmd='$OBJDUMP -f' + fi + ;; + +cegcc*) + # use the weaker test based on 'objdump'. See mingw*. + lt_cv_deplibs_check_method='file_magic file format pe-arm-.*little(.*architecture: arm)?' + lt_cv_file_magic_cmd='$OBJDUMP -f' + ;; + +darwin* | rhapsody*) + lt_cv_deplibs_check_method=pass_all + ;; + +freebsd* | dragonfly* | midnightbsd*) + if echo __ELF__ | $CC -E - | $GREP __ELF__ > /dev/null; then + case $host_cpu in + i*86 ) + # Not sure whether the presence of OpenBSD here was a mistake. + # Let's accept both of them until this is cleared up. + lt_cv_deplibs_check_method='file_magic (FreeBSD|OpenBSD|DragonFly)/i[[3-9]]86 (compact )?demand paged shared library' + lt_cv_file_magic_cmd=$FILECMD + lt_cv_file_magic_test_file=`echo /usr/lib/libc.so.*` + ;; + esac + else + lt_cv_deplibs_check_method=pass_all + fi + ;; + +haiku*) + lt_cv_deplibs_check_method=pass_all + ;; + +hpux10.20* | hpux11*) + lt_cv_file_magic_cmd=$FILECMD + case $host_cpu in + ia64*) + lt_cv_deplibs_check_method='file_magic (s[[0-9]][[0-9]][[0-9]]|ELF-[[0-9]][[0-9]]) shared object file - IA64' + lt_cv_file_magic_test_file=/usr/lib/hpux32/libc.so + ;; + hppa*64*) + [lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|ELF[ -][0-9][0-9])(-bit)?( [LM]SB)? shared object( file)?[, -]* PA-RISC [0-9]\.[0-9]'] + lt_cv_file_magic_test_file=/usr/lib/pa20_64/libc.sl + ;; + *) + lt_cv_deplibs_check_method='file_magic (s[[0-9]][[0-9]][[0-9]]|PA-RISC[[0-9]]\.[[0-9]]) shared library' + lt_cv_file_magic_test_file=/usr/lib/libc.sl + ;; + esac + ;; + +interix[[3-9]]*) + # PIC code is broken on Interix 3.x, that's why |\.a not |_pic\.a here + lt_cv_deplibs_check_method='match_pattern /lib[[^/]]+(\.so|\.a)$' + ;; + +irix5* | irix6* | nonstopux*) + case $LD in + *-32|*"-32 ") libmagic=32-bit;; + *-n32|*"-n32 ") libmagic=N32;; + *-64|*"-64 ") libmagic=64-bit;; + *) libmagic=never-match;; + esac + lt_cv_deplibs_check_method=pass_all + ;; + +# This must be glibc/ELF. +linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) + lt_cv_deplibs_check_method=pass_all + ;; + +netbsd*) + if echo __ELF__ | $CC -E - | $GREP __ELF__ > /dev/null; then + lt_cv_deplibs_check_method='match_pattern /lib[[^/]]+(\.so\.[[0-9]]+\.[[0-9]]+|_pic\.a)$' + else + lt_cv_deplibs_check_method='match_pattern /lib[[^/]]+(\.so|_pic\.a)$' + fi + ;; + +newos6*) + lt_cv_deplibs_check_method='file_magic ELF [[0-9]][[0-9]]*-bit [[ML]]SB (executable|dynamic lib)' + lt_cv_file_magic_cmd=$FILECMD + lt_cv_file_magic_test_file=/usr/lib/libnls.so + ;; + +*nto* | *qnx*) + lt_cv_deplibs_check_method=pass_all + ;; + +openbsd* | bitrig*) + if test -z "`echo __ELF__ | $CC -E - | $GREP __ELF__`"; then + lt_cv_deplibs_check_method='match_pattern /lib[[^/]]+(\.so\.[[0-9]]+\.[[0-9]]+|\.so|_pic\.a)$' + else + lt_cv_deplibs_check_method='match_pattern /lib[[^/]]+(\.so\.[[0-9]]+\.[[0-9]]+|_pic\.a)$' + fi + ;; + +osf3* | osf4* | osf5*) + lt_cv_deplibs_check_method=pass_all + ;; + +rdos*) + lt_cv_deplibs_check_method=pass_all + ;; + +solaris*) + lt_cv_deplibs_check_method=pass_all + ;; + +sysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX* | sysv4*uw2*) + lt_cv_deplibs_check_method=pass_all + ;; + +sysv4 | sysv4.3*) + case $host_vendor in + motorola) + lt_cv_deplibs_check_method='file_magic ELF [[0-9]][[0-9]]*-bit [[ML]]SB (shared object|dynamic lib) M[[0-9]][[0-9]]* Version [[0-9]]' + lt_cv_file_magic_test_file=`echo /usr/lib/libc.so*` + ;; + ncr) + lt_cv_deplibs_check_method=pass_all + ;; + sequent) + lt_cv_file_magic_cmd='/bin/file' + lt_cv_deplibs_check_method='file_magic ELF [[0-9]][[0-9]]*-bit [[LM]]SB (shared object|dynamic lib )' + ;; + sni) + lt_cv_file_magic_cmd='/bin/file' + lt_cv_deplibs_check_method="file_magic ELF [[0-9]][[0-9]]*-bit [[LM]]SB dynamic lib" + lt_cv_file_magic_test_file=/lib/libc.so + ;; + siemens) + lt_cv_deplibs_check_method=pass_all + ;; + pc) + lt_cv_deplibs_check_method=pass_all + ;; + esac + ;; + +tpf*) + lt_cv_deplibs_check_method=pass_all + ;; +os2*) + lt_cv_deplibs_check_method=pass_all + ;; +esac +]) + +file_magic_glob= +want_nocaseglob=no +if test "$build" = "$host"; then + case $host_os in + mingw* | pw32*) + if ( shopt | grep nocaseglob ) >/dev/null 2>&1; then + want_nocaseglob=yes + else + file_magic_glob=`echo aAbBcCdDeEfFgGhHiIjJkKlLmMnNoOpPqQrRsStTuUvVwWxXyYzZ | $SED -e "s/\(..\)/s\/[[\1]]\/[[\1]]\/g;/g"` + fi + ;; + esac +fi + +file_magic_cmd=$lt_cv_file_magic_cmd +deplibs_check_method=$lt_cv_deplibs_check_method +test -z "$deplibs_check_method" && deplibs_check_method=unknown + +_LT_DECL([], [deplibs_check_method], [1], + [Method to check whether dependent libraries are shared objects]) +_LT_DECL([], [file_magic_cmd], [1], + [Command to use when deplibs_check_method = "file_magic"]) +_LT_DECL([], [file_magic_glob], [1], + [How to find potential files when deplibs_check_method = "file_magic"]) +_LT_DECL([], [want_nocaseglob], [1], + [Find potential files using nocaseglob when deplibs_check_method = "file_magic"]) +])# _LT_CHECK_MAGIC_METHOD + + +# LT_PATH_NM +# ---------- +# find the pathname to a BSD- or MS-compatible name lister +AC_DEFUN([LT_PATH_NM], +[AC_REQUIRE([AC_PROG_CC])dnl +AC_CACHE_CHECK([for BSD- or MS-compatible name lister (nm)], lt_cv_path_NM, +[if test -n "$NM"; then + # Let the user override the test. + lt_cv_path_NM=$NM +else + lt_nm_to_check=${ac_tool_prefix}nm + if test -n "$ac_tool_prefix" && test "$build" = "$host"; then + lt_nm_to_check="$lt_nm_to_check nm" + fi + for lt_tmp_nm in $lt_nm_to_check; do + lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR + for ac_dir in $PATH /usr/ccs/bin/elf /usr/ccs/bin /usr/ucb /bin; do + IFS=$lt_save_ifs + test -z "$ac_dir" && ac_dir=. + tmp_nm=$ac_dir/$lt_tmp_nm + if test -f "$tmp_nm" || test -f "$tmp_nm$ac_exeext"; then + # Check to see if the nm accepts a BSD-compat flag. + # Adding the 'sed 1q' prevents false positives on HP-UX, which says: + # nm: unknown option "B" ignored + # Tru64's nm complains that /dev/null is an invalid object file + # MSYS converts /dev/null to NUL, MinGW nm treats NUL as empty + case $build_os in + mingw*) lt_bad_file=conftest.nm/nofile ;; + *) lt_bad_file=/dev/null ;; + esac + case `"$tmp_nm" -B $lt_bad_file 2>&1 | $SED '1q'` in + *$lt_bad_file* | *'Invalid file or object type'*) + lt_cv_path_NM="$tmp_nm -B" + break 2 + ;; + *) + case `"$tmp_nm" -p /dev/null 2>&1 | $SED '1q'` in + */dev/null*) + lt_cv_path_NM="$tmp_nm -p" + break 2 + ;; + *) + lt_cv_path_NM=${lt_cv_path_NM="$tmp_nm"} # keep the first match, but + continue # so that we can try to find one that supports BSD flags + ;; + esac + ;; + esac + fi + done + IFS=$lt_save_ifs + done + : ${lt_cv_path_NM=no} +fi]) +if test no != "$lt_cv_path_NM"; then + NM=$lt_cv_path_NM +else + # Didn't find any BSD compatible name lister, look for dumpbin. + if test -n "$DUMPBIN"; then : + # Let the user override the test. + else + AC_CHECK_TOOLS(DUMPBIN, [dumpbin "link -dump"], :) + case `$DUMPBIN -symbols -headers /dev/null 2>&1 | $SED '1q'` in + *COFF*) + DUMPBIN="$DUMPBIN -symbols -headers" + ;; + *) + DUMPBIN=: + ;; + esac + fi + AC_SUBST([DUMPBIN]) + if test : != "$DUMPBIN"; then + NM=$DUMPBIN + fi +fi +test -z "$NM" && NM=nm +AC_SUBST([NM]) +_LT_DECL([], [NM], [1], [A BSD- or MS-compatible name lister])dnl + +AC_CACHE_CHECK([the name lister ($NM) interface], [lt_cv_nm_interface], + [lt_cv_nm_interface="BSD nm" + echo "int some_variable = 0;" > conftest.$ac_ext + (eval echo "\"\$as_me:$LINENO: $ac_compile\"" >&AS_MESSAGE_LOG_FD) + (eval "$ac_compile" 2>conftest.err) + cat conftest.err >&AS_MESSAGE_LOG_FD + (eval echo "\"\$as_me:$LINENO: $NM \\\"conftest.$ac_objext\\\"\"" >&AS_MESSAGE_LOG_FD) + (eval "$NM \"conftest.$ac_objext\"" 2>conftest.err > conftest.out) + cat conftest.err >&AS_MESSAGE_LOG_FD + (eval echo "\"\$as_me:$LINENO: output\"" >&AS_MESSAGE_LOG_FD) + cat conftest.out >&AS_MESSAGE_LOG_FD + if $GREP 'External.*some_variable' conftest.out > /dev/null; then + lt_cv_nm_interface="MS dumpbin" + fi + rm -f conftest*]) +])# LT_PATH_NM + +# Old names: +AU_ALIAS([AM_PROG_NM], [LT_PATH_NM]) +AU_ALIAS([AC_PROG_NM], [LT_PATH_NM]) +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([AM_PROG_NM], []) +dnl AC_DEFUN([AC_PROG_NM], []) + +# _LT_CHECK_SHAREDLIB_FROM_LINKLIB +# -------------------------------- +# how to determine the name of the shared library +# associated with a specific link library. +# -- PORTME fill in with the dynamic library characteristics +m4_defun([_LT_CHECK_SHAREDLIB_FROM_LINKLIB], +[m4_require([_LT_DECL_EGREP]) +m4_require([_LT_DECL_OBJDUMP]) +m4_require([_LT_DECL_DLLTOOL]) +AC_CACHE_CHECK([how to associate runtime and link libraries], +lt_cv_sharedlib_from_linklib_cmd, +[lt_cv_sharedlib_from_linklib_cmd='unknown' + +case $host_os in +cygwin* | mingw* | pw32* | cegcc*) + # two different shell functions defined in ltmain.sh; + # decide which one to use based on capabilities of $DLLTOOL + case `$DLLTOOL --help 2>&1` in + *--identify-strict*) + lt_cv_sharedlib_from_linklib_cmd=func_cygming_dll_for_implib + ;; + *) + lt_cv_sharedlib_from_linklib_cmd=func_cygming_dll_for_implib_fallback + ;; + esac + ;; +*) + # fallback: assume linklib IS sharedlib + lt_cv_sharedlib_from_linklib_cmd=$ECHO + ;; +esac +]) +sharedlib_from_linklib_cmd=$lt_cv_sharedlib_from_linklib_cmd +test -z "$sharedlib_from_linklib_cmd" && sharedlib_from_linklib_cmd=$ECHO + +_LT_DECL([], [sharedlib_from_linklib_cmd], [1], + [Command to associate shared and link libraries]) +])# _LT_CHECK_SHAREDLIB_FROM_LINKLIB + + +# _LT_PATH_MANIFEST_TOOL +# ---------------------- +# locate the manifest tool +m4_defun([_LT_PATH_MANIFEST_TOOL], +[AC_CHECK_TOOL(MANIFEST_TOOL, mt, :) +test -z "$MANIFEST_TOOL" && MANIFEST_TOOL=mt +AC_CACHE_CHECK([if $MANIFEST_TOOL is a manifest tool], [lt_cv_path_mainfest_tool], + [lt_cv_path_mainfest_tool=no + echo "$as_me:$LINENO: $MANIFEST_TOOL '-?'" >&AS_MESSAGE_LOG_FD + $MANIFEST_TOOL '-?' 2>conftest.err > conftest.out + cat conftest.err >&AS_MESSAGE_LOG_FD + if $GREP 'Manifest Tool' conftest.out > /dev/null; then + lt_cv_path_mainfest_tool=yes + fi + rm -f conftest*]) +if test yes != "$lt_cv_path_mainfest_tool"; then + MANIFEST_TOOL=: +fi +_LT_DECL([], [MANIFEST_TOOL], [1], [Manifest tool])dnl +])# _LT_PATH_MANIFEST_TOOL + + +# _LT_DLL_DEF_P([FILE]) +# --------------------- +# True iff FILE is a Windows DLL '.def' file. +# Keep in sync with func_dll_def_p in the libtool script +AC_DEFUN([_LT_DLL_DEF_P], +[dnl + test DEF = "`$SED -n dnl + -e '\''s/^[[ ]]*//'\'' dnl Strip leading whitespace + -e '\''/^\(;.*\)*$/d'\'' dnl Delete empty lines and comments + -e '\''s/^\(EXPORTS\|LIBRARY\)\([[ ]].*\)*$/DEF/p'\'' dnl + -e q dnl Only consider the first "real" line + $1`" dnl +])# _LT_DLL_DEF_P + + +# LT_LIB_M +# -------- +# check for math library +AC_DEFUN([LT_LIB_M], +[AC_REQUIRE([AC_CANONICAL_HOST])dnl +LIBM= +case $host in +*-*-beos* | *-*-cegcc* | *-*-cygwin* | *-*-haiku* | *-*-pw32* | *-*-darwin*) + # These system don't have libm, or don't need it + ;; +*-ncr-sysv4.3*) + AC_CHECK_LIB(mw, _mwvalidcheckl, LIBM=-lmw) + AC_CHECK_LIB(m, cos, LIBM="$LIBM -lm") + ;; +*) + AC_CHECK_LIB(m, cos, LIBM=-lm) + ;; +esac +AC_SUBST([LIBM]) +])# LT_LIB_M + +# Old name: +AU_ALIAS([AC_CHECK_LIBM], [LT_LIB_M]) +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([AC_CHECK_LIBM], []) + + +# _LT_COMPILER_NO_RTTI([TAGNAME]) +# ------------------------------- +m4_defun([_LT_COMPILER_NO_RTTI], +[m4_require([_LT_TAG_COMPILER])dnl + +_LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)= + +if test yes = "$GCC"; then + case $cc_basename in + nvcc*) + _LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)=' -Xcompiler -fno-builtin' ;; + *) + _LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)=' -fno-builtin' ;; + esac + + _LT_COMPILER_OPTION([if $compiler supports -fno-rtti -fno-exceptions], + lt_cv_prog_compiler_rtti_exceptions, + [-fno-rtti -fno-exceptions], [], + [_LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)="$_LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1) -fno-rtti -fno-exceptions"]) +fi +_LT_TAGDECL([no_builtin_flag], [lt_prog_compiler_no_builtin_flag], [1], + [Compiler flag to turn off builtin functions]) +])# _LT_COMPILER_NO_RTTI + + +# _LT_CMD_GLOBAL_SYMBOLS +# ---------------------- +m4_defun([_LT_CMD_GLOBAL_SYMBOLS], +[AC_REQUIRE([AC_CANONICAL_HOST])dnl +AC_REQUIRE([AC_PROG_CC])dnl +AC_REQUIRE([AC_PROG_AWK])dnl +AC_REQUIRE([LT_PATH_NM])dnl +AC_REQUIRE([LT_PATH_LD])dnl +m4_require([_LT_DECL_SED])dnl +m4_require([_LT_DECL_EGREP])dnl +m4_require([_LT_TAG_COMPILER])dnl + +# Check for command to grab the raw symbol name followed by C symbol from nm. +AC_MSG_CHECKING([command to parse $NM output from $compiler object]) +AC_CACHE_VAL([lt_cv_sys_global_symbol_pipe], +[ +# These are sane defaults that work on at least a few old systems. +# [They come from Ultrix. What could be older than Ultrix?!! ;)] + +# Character class describing NM global symbol codes. +symcode='[[BCDEGRST]]' + +# Regexp to match symbols that can be accessed directly from C. +sympat='\([[_A-Za-z]][[_A-Za-z0-9]]*\)' + +# Define system-specific variables. +case $host_os in +aix*) + symcode='[[BCDT]]' + ;; +cygwin* | mingw* | pw32* | cegcc*) + symcode='[[ABCDGISTW]]' + ;; +hpux*) + if test ia64 = "$host_cpu"; then + symcode='[[ABCDEGRST]]' + fi + ;; +irix* | nonstopux*) + symcode='[[BCDEGRST]]' + ;; +osf*) + symcode='[[BCDEGQRST]]' + ;; +solaris*) + symcode='[[BDRT]]' + ;; +sco3.2v5*) + symcode='[[DT]]' + ;; +sysv4.2uw2*) + symcode='[[DT]]' + ;; +sysv5* | sco5v6* | unixware* | OpenUNIX*) + symcode='[[ABDT]]' + ;; +sysv4) + symcode='[[DFNSTU]]' + ;; +esac + +# If we're using GNU nm, then use its standard symbol codes. +case `$NM -V 2>&1` in +*GNU* | *'with BFD'*) + symcode='[[ABCDGIRSTW]]' ;; +esac + +if test "$lt_cv_nm_interface" = "MS dumpbin"; then + # Gets list of data symbols to import. + lt_cv_sys_global_symbol_to_import="$SED -n -e 's/^I .* \(.*\)$/\1/p'" + # Adjust the below global symbol transforms to fixup imported variables. + lt_cdecl_hook=" -e 's/^I .* \(.*\)$/extern __declspec(dllimport) char \1;/p'" + lt_c_name_hook=" -e 's/^I .* \(.*\)$/ {\"\1\", (void *) 0},/p'" + lt_c_name_lib_hook="\ + -e 's/^I .* \(lib.*\)$/ {\"\1\", (void *) 0},/p'\ + -e 's/^I .* \(.*\)$/ {\"lib\1\", (void *) 0},/p'" +else + # Disable hooks by default. + lt_cv_sys_global_symbol_to_import= + lt_cdecl_hook= + lt_c_name_hook= + lt_c_name_lib_hook= +fi + +# Transform an extracted symbol line into a proper C declaration. +# Some systems (esp. on ia64) link data and code symbols differently, +# so use this general approach. +lt_cv_sys_global_symbol_to_cdecl="$SED -n"\ +$lt_cdecl_hook\ +" -e 's/^T .* \(.*\)$/extern int \1();/p'"\ +" -e 's/^$symcode$symcode* .* \(.*\)$/extern char \1;/p'" + +# Transform an extracted symbol line into symbol name and symbol address +lt_cv_sys_global_symbol_to_c_name_address="$SED -n"\ +$lt_c_name_hook\ +" -e 's/^: \(.*\) .*$/ {\"\1\", (void *) 0},/p'"\ +" -e 's/^$symcode$symcode* .* \(.*\)$/ {\"\1\", (void *) \&\1},/p'" + +# Transform an extracted symbol line into symbol name with lib prefix and +# symbol address. +lt_cv_sys_global_symbol_to_c_name_address_lib_prefix="$SED -n"\ +$lt_c_name_lib_hook\ +" -e 's/^: \(.*\) .*$/ {\"\1\", (void *) 0},/p'"\ +" -e 's/^$symcode$symcode* .* \(lib.*\)$/ {\"\1\", (void *) \&\1},/p'"\ +" -e 's/^$symcode$symcode* .* \(.*\)$/ {\"lib\1\", (void *) \&\1},/p'" + +# Handle CRLF in mingw tool chain +opt_cr= +case $build_os in +mingw*) + opt_cr=`$ECHO 'x\{0,1\}' | tr x '\015'` # option cr in regexp + ;; +esac + +# Try without a prefix underscore, then with it. +for ac_symprfx in "" "_"; do + + # Transform symcode, sympat, and symprfx into a raw symbol and a C symbol. + symxfrm="\\1 $ac_symprfx\\2 \\2" + + # Write the raw and C identifiers. + if test "$lt_cv_nm_interface" = "MS dumpbin"; then + # Fake it for dumpbin and say T for any non-static function, + # D for any global variable and I for any imported variable. + # Also find C++ and __fastcall symbols from MSVC++ or ICC, + # which start with @ or ?. + lt_cv_sys_global_symbol_pipe="$AWK ['"\ +" {last_section=section; section=\$ 3};"\ +" /^COFF SYMBOL TABLE/{for(i in hide) delete hide[i]};"\ +" /Section length .*#relocs.*(pick any)/{hide[last_section]=1};"\ +" /^ *Symbol name *: /{split(\$ 0,sn,\":\"); si=substr(sn[2],2)};"\ +" /^ *Type *: code/{print \"T\",si,substr(si,length(prfx))};"\ +" /^ *Type *: data/{print \"I\",si,substr(si,length(prfx))};"\ +" \$ 0!~/External *\|/{next};"\ +" / 0+ UNDEF /{next}; / UNDEF \([^|]\)*()/{next};"\ +" {if(hide[section]) next};"\ +" {f=\"D\"}; \$ 0~/\(\).*\|/{f=\"T\"};"\ +" {split(\$ 0,a,/\||\r/); split(a[2],s)};"\ +" s[1]~/^[@?]/{print f,s[1],s[1]; next};"\ +" s[1]~prfx {split(s[1],t,\"@\"); print f,t[1],substr(t[1],length(prfx))}"\ +" ' prfx=^$ac_symprfx]" + else + lt_cv_sys_global_symbol_pipe="$SED -n -e 's/^.*[[ ]]\($symcode$symcode*\)[[ ]][[ ]]*$ac_symprfx$sympat$opt_cr$/$symxfrm/p'" + fi + lt_cv_sys_global_symbol_pipe="$lt_cv_sys_global_symbol_pipe | $SED '/ __gnu_lto/d'" + + # Check to see that the pipe works correctly. + pipe_works=no + + rm -f conftest* + cat > conftest.$ac_ext <<_LT_EOF +#ifdef __cplusplus +extern "C" { +#endif +char nm_test_var; +void nm_test_func(void); +void nm_test_func(void){} +#ifdef __cplusplus +} +#endif +int main(){nm_test_var='a';nm_test_func();return(0);} +_LT_EOF + + if AC_TRY_EVAL(ac_compile); then + # Now try to grab the symbols. + nlist=conftest.nm + if AC_TRY_EVAL(NM conftest.$ac_objext \| "$lt_cv_sys_global_symbol_pipe" \> $nlist) && test -s "$nlist"; then + # Try sorting and uniquifying the output. + if sort "$nlist" | uniq > "$nlist"T; then + mv -f "$nlist"T "$nlist" + else + rm -f "$nlist"T + fi + + # Make sure that we snagged all the symbols we need. + if $GREP ' nm_test_var$' "$nlist" >/dev/null; then + if $GREP ' nm_test_func$' "$nlist" >/dev/null; then + cat <<_LT_EOF > conftest.$ac_ext +/* Keep this code in sync between libtool.m4, ltmain, lt_system.h, and tests. */ +#if defined _WIN32 || defined __CYGWIN__ || defined _WIN32_WCE +/* DATA imports from DLLs on WIN32 can't be const, because runtime + relocations are performed -- see ld's documentation on pseudo-relocs. */ +# define LT@&t@_DLSYM_CONST +#elif defined __osf__ +/* This system does not cope well with relocations in const data. */ +# define LT@&t@_DLSYM_CONST +#else +# define LT@&t@_DLSYM_CONST const +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +_LT_EOF + # Now generate the symbol file. + eval "$lt_cv_sys_global_symbol_to_cdecl"' < "$nlist" | $GREP -v main >> conftest.$ac_ext' + + cat <<_LT_EOF >> conftest.$ac_ext + +/* The mapping between symbol names and symbols. */ +LT@&t@_DLSYM_CONST struct { + const char *name; + void *address; +} +lt__PROGRAM__LTX_preloaded_symbols[[]] = +{ + { "@PROGRAM@", (void *) 0 }, +_LT_EOF + $SED "s/^$symcode$symcode* .* \(.*\)$/ {\"\1\", (void *) \&\1},/" < "$nlist" | $GREP -v main >> conftest.$ac_ext + cat <<\_LT_EOF >> conftest.$ac_ext + {0, (void *) 0} +}; + +/* This works around a problem in FreeBSD linker */ +#ifdef FREEBSD_WORKAROUND +static const void *lt_preloaded_setup() { + return lt__PROGRAM__LTX_preloaded_symbols; +} +#endif + +#ifdef __cplusplus +} +#endif +_LT_EOF + # Now try linking the two files. + mv conftest.$ac_objext conftstm.$ac_objext + lt_globsym_save_LIBS=$LIBS + lt_globsym_save_CFLAGS=$CFLAGS + LIBS=conftstm.$ac_objext + CFLAGS="$CFLAGS$_LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)" + if AC_TRY_EVAL(ac_link) && test -s conftest$ac_exeext; then + pipe_works=yes + fi + LIBS=$lt_globsym_save_LIBS + CFLAGS=$lt_globsym_save_CFLAGS + else + echo "cannot find nm_test_func in $nlist" >&AS_MESSAGE_LOG_FD + fi + else + echo "cannot find nm_test_var in $nlist" >&AS_MESSAGE_LOG_FD + fi + else + echo "cannot run $lt_cv_sys_global_symbol_pipe" >&AS_MESSAGE_LOG_FD + fi + else + echo "$progname: failed program was:" >&AS_MESSAGE_LOG_FD + cat conftest.$ac_ext >&5 + fi + rm -rf conftest* conftst* + + # Do not use the global_symbol_pipe unless it works. + if test yes = "$pipe_works"; then + break + else + lt_cv_sys_global_symbol_pipe= + fi +done +]) +if test -z "$lt_cv_sys_global_symbol_pipe"; then + lt_cv_sys_global_symbol_to_cdecl= +fi +if test -z "$lt_cv_sys_global_symbol_pipe$lt_cv_sys_global_symbol_to_cdecl"; then + AC_MSG_RESULT(failed) +else + AC_MSG_RESULT(ok) +fi + +# Response file support. +if test "$lt_cv_nm_interface" = "MS dumpbin"; then + nm_file_list_spec='@' +elif $NM --help 2>/dev/null | grep '[[@]]FILE' >/dev/null; then + nm_file_list_spec='@' +fi + +_LT_DECL([global_symbol_pipe], [lt_cv_sys_global_symbol_pipe], [1], + [Take the output of nm and produce a listing of raw symbols and C names]) +_LT_DECL([global_symbol_to_cdecl], [lt_cv_sys_global_symbol_to_cdecl], [1], + [Transform the output of nm in a proper C declaration]) +_LT_DECL([global_symbol_to_import], [lt_cv_sys_global_symbol_to_import], [1], + [Transform the output of nm into a list of symbols to manually relocate]) +_LT_DECL([global_symbol_to_c_name_address], + [lt_cv_sys_global_symbol_to_c_name_address], [1], + [Transform the output of nm in a C name address pair]) +_LT_DECL([global_symbol_to_c_name_address_lib_prefix], + [lt_cv_sys_global_symbol_to_c_name_address_lib_prefix], [1], + [Transform the output of nm in a C name address pair when lib prefix is needed]) +_LT_DECL([nm_interface], [lt_cv_nm_interface], [1], + [The name lister interface]) +_LT_DECL([], [nm_file_list_spec], [1], + [Specify filename containing input files for $NM]) +]) # _LT_CMD_GLOBAL_SYMBOLS + + +# _LT_COMPILER_PIC([TAGNAME]) +# --------------------------- +m4_defun([_LT_COMPILER_PIC], +[m4_require([_LT_TAG_COMPILER])dnl +_LT_TAGVAR(lt_prog_compiler_wl, $1)= +_LT_TAGVAR(lt_prog_compiler_pic, $1)= +_LT_TAGVAR(lt_prog_compiler_static, $1)= + +m4_if([$1], [CXX], [ + # C++ specific cases for pic, static, wl, etc. + if test yes = "$GXX"; then + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-static' + + case $host_os in + aix*) + # All AIX code is PIC. + if test ia64 = "$host_cpu"; then + # AIX 5 now supports IA64 processor + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + fi + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' + ;; + + amigaos*) + case $host_cpu in + powerpc) + # see comment about AmigaOS4 .so support + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' + ;; + m68k) + # FIXME: we need at least 68020 code to build shared libraries, but + # adding the '-m68020' flag to GCC prevents building anything better, + # like '-m68040'. + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-m68020 -resident32 -malways-restore-a4' + ;; + esac + ;; + + beos* | irix5* | irix6* | nonstopux* | osf3* | osf4* | osf5*) + # PIC is the default for these OSes. + ;; + mingw* | cygwin* | os2* | pw32* | cegcc*) + # This hack is so that the source file can tell whether it is being + # built for inclusion in a dll (and should export symbols for example). + # Although the cygwin gcc ignores -fPIC, still need this for old-style + # (--disable-auto-import) libraries + m4_if([$1], [GCJ], [], + [_LT_TAGVAR(lt_prog_compiler_pic, $1)='-DDLL_EXPORT']) + case $host_os in + os2*) + _LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-static' + ;; + esac + ;; + darwin* | rhapsody*) + # PIC is the default on this platform + # Common symbols not allowed in MH_DYLIB files + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fno-common' + ;; + *djgpp*) + # DJGPP does not support shared libraries at all + _LT_TAGVAR(lt_prog_compiler_pic, $1)= + ;; + haiku*) + # PIC is the default for Haiku. + # The "-static" flag exists, but is broken. + _LT_TAGVAR(lt_prog_compiler_static, $1)= + ;; + interix[[3-9]]*) + # Interix 3.x gcc -fpic/-fPIC options generate broken code. + # Instead, we relocate shared libraries at runtime. + ;; + sysv4*MP*) + if test -d /usr/nec; then + _LT_TAGVAR(lt_prog_compiler_pic, $1)=-Kconform_pic + fi + ;; + hpux*) + # PIC is the default for 64-bit PA HP-UX, but not for 32-bit + # PA HP-UX. On IA64 HP-UX, PIC is the default but the pic flag + # sets the default TLS model and affects inlining. + case $host_cpu in + hppa*64*) + ;; + *) + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' + ;; + esac + ;; + *qnx* | *nto*) + # QNX uses GNU C++, but need to define -shared option too, otherwise + # it will coredump. + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC -shared' + ;; + *) + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' + ;; + esac + else + case $host_os in + aix[[4-9]]*) + # All AIX code is PIC. + if test ia64 = "$host_cpu"; then + # AIX 5 now supports IA64 processor + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + else + _LT_TAGVAR(lt_prog_compiler_static, $1)='-bnso -bI:/lib/syscalls.exp' + fi + ;; + chorus*) + case $cc_basename in + cxch68*) + # Green Hills C++ Compiler + # _LT_TAGVAR(lt_prog_compiler_static, $1)="--no_auto_instantiation -u __main -u __premain -u _abort -r $COOL_DIR/lib/libOrb.a $MVME_DIR/lib/CC/libC.a $MVME_DIR/lib/classix/libcx.s.a" + ;; + esac + ;; + mingw* | cygwin* | os2* | pw32* | cegcc*) + # This hack is so that the source file can tell whether it is being + # built for inclusion in a dll (and should export symbols for example). + m4_if([$1], [GCJ], [], + [_LT_TAGVAR(lt_prog_compiler_pic, $1)='-DDLL_EXPORT']) + ;; + dgux*) + case $cc_basename in + ec++*) + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' + ;; + ghcx*) + # Green Hills C++ Compiler + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-pic' + ;; + *) + ;; + esac + ;; + freebsd* | dragonfly* | midnightbsd*) + # FreeBSD uses GNU C++ + ;; + hpux9* | hpux10* | hpux11*) + case $cc_basename in + CC*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-a ${wl}archive' + if test ia64 != "$host_cpu"; then + _LT_TAGVAR(lt_prog_compiler_pic, $1)='+Z' + fi + ;; + aCC*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-a ${wl}archive' + case $host_cpu in + hppa*64*|ia64*) + # +Z the default + ;; + *) + _LT_TAGVAR(lt_prog_compiler_pic, $1)='+Z' + ;; + esac + ;; + *) + ;; + esac + ;; + interix*) + # This is c89, which is MS Visual C++ (no shared libs) + # Anyone wants to do a port? + ;; + irix5* | irix6* | nonstopux*) + case $cc_basename in + CC*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared' + # CC pic flag -KPIC is the default. + ;; + *) + ;; + esac + ;; + linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) + case $cc_basename in + KCC*) + # KAI C++ Compiler + _LT_TAGVAR(lt_prog_compiler_wl, $1)='--backend -Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' + ;; + ecpc* ) + # old Intel C++ for x86_64, which still supported -KPIC. + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-static' + ;; + icpc* ) + # Intel C++, used to be incompatible with GCC. + # ICC 10 doesn't accept -KPIC any more. + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-static' + ;; + pgCC* | pgcpp*) + # Portland Group C++ compiler + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fpic' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + ;; + cxx*) + # Compaq C++ + # Make sure the PIC flag is empty. It appears that all Alpha + # Linux and Compaq Tru64 Unix objects are PIC. + _LT_TAGVAR(lt_prog_compiler_pic, $1)= + _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared' + ;; + xlc* | xlC* | bgxl[[cC]]* | mpixl[[cC]]*) + # IBM XL 8.0, 9.0 on PPC and BlueGene + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-qpic' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-qstaticlink' + ;; + *) + case `$CC -V 2>&1 | $SED 5q` in + *Sun\ C*) + # Sun C++ 5.9 + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Qoption ld ' + ;; + esac + ;; + esac + ;; + lynxos*) + ;; + m88k*) + ;; + mvs*) + case $cc_basename in + cxx*) + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-W c,exportall' + ;; + *) + ;; + esac + ;; + netbsd*) + ;; + *qnx* | *nto*) + # QNX uses GNU C++, but need to define -shared option too, otherwise + # it will coredump. + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC -shared' + ;; + osf3* | osf4* | osf5*) + case $cc_basename in + KCC*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='--backend -Wl,' + ;; + RCC*) + # Rational C++ 2.4.1 + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-pic' + ;; + cxx*) + # Digital/Compaq C++ + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + # Make sure the PIC flag is empty. It appears that all Alpha + # Linux and Compaq Tru64 Unix objects are PIC. + _LT_TAGVAR(lt_prog_compiler_pic, $1)= + _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared' + ;; + *) + ;; + esac + ;; + psos*) + ;; + solaris*) + case $cc_basename in + CC* | sunCC*) + # Sun C++ 4.2, 5.x and Centerline C++ + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Qoption ld ' + ;; + gcx*) + # Green Hills C++ Compiler + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-PIC' + ;; + *) + ;; + esac + ;; + sunos4*) + case $cc_basename in + CC*) + # Sun C++ 4.x + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-pic' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + ;; + lcc*) + # Lucid + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-pic' + ;; + *) + ;; + esac + ;; + sysv5* | unixware* | sco3.2v5* | sco5v6* | OpenUNIX*) + case $cc_basename in + CC*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + ;; + esac + ;; + tandem*) + case $cc_basename in + NCC*) + # NonStop-UX NCC 3.20 + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' + ;; + *) + ;; + esac + ;; + vxworks*) + ;; + *) + _LT_TAGVAR(lt_prog_compiler_can_build_shared, $1)=no + ;; + esac + fi +], +[ + if test yes = "$GCC"; then + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-static' + + case $host_os in + aix*) + # All AIX code is PIC. + if test ia64 = "$host_cpu"; then + # AIX 5 now supports IA64 processor + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + fi + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' + ;; + + amigaos*) + case $host_cpu in + powerpc) + # see comment about AmigaOS4 .so support + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' + ;; + m68k) + # FIXME: we need at least 68020 code to build shared libraries, but + # adding the '-m68020' flag to GCC prevents building anything better, + # like '-m68040'. + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-m68020 -resident32 -malways-restore-a4' + ;; + esac + ;; + + beos* | irix5* | irix6* | nonstopux* | osf3* | osf4* | osf5*) + # PIC is the default for these OSes. + ;; + + mingw* | cygwin* | pw32* | os2* | cegcc*) + # This hack is so that the source file can tell whether it is being + # built for inclusion in a dll (and should export symbols for example). + # Although the cygwin gcc ignores -fPIC, still need this for old-style + # (--disable-auto-import) libraries + m4_if([$1], [GCJ], [], + [_LT_TAGVAR(lt_prog_compiler_pic, $1)='-DDLL_EXPORT']) + case $host_os in + os2*) + _LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-static' + ;; + esac + ;; + + darwin* | rhapsody*) + # PIC is the default on this platform + # Common symbols not allowed in MH_DYLIB files + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fno-common' + ;; + + haiku*) + # PIC is the default for Haiku. + # The "-static" flag exists, but is broken. + _LT_TAGVAR(lt_prog_compiler_static, $1)= + ;; + + hpux*) + # PIC is the default for 64-bit PA HP-UX, but not for 32-bit + # PA HP-UX. On IA64 HP-UX, PIC is the default but the pic flag + # sets the default TLS model and affects inlining. + case $host_cpu in + hppa*64*) + # +Z the default + ;; + *) + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' + ;; + esac + ;; + + interix[[3-9]]*) + # Interix 3.x gcc -fpic/-fPIC options generate broken code. + # Instead, we relocate shared libraries at runtime. + ;; + + msdosdjgpp*) + # Just because we use GCC doesn't mean we suddenly get shared libraries + # on systems that don't support them. + _LT_TAGVAR(lt_prog_compiler_can_build_shared, $1)=no + enable_shared=no + ;; + + *nto* | *qnx*) + # QNX uses GNU C++, but need to define -shared option too, otherwise + # it will coredump. + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC -shared' + ;; + + sysv4*MP*) + if test -d /usr/nec; then + _LT_TAGVAR(lt_prog_compiler_pic, $1)=-Kconform_pic + fi + ;; + + *) + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' + ;; + esac + + case $cc_basename in + nvcc*) # Cuda Compiler Driver 2.2 + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Xlinker ' + if test -n "$_LT_TAGVAR(lt_prog_compiler_pic, $1)"; then + _LT_TAGVAR(lt_prog_compiler_pic, $1)="-Xcompiler $_LT_TAGVAR(lt_prog_compiler_pic, $1)" + fi + ;; + esac + else + # PORTME Check for flag to pass linker flags through the system compiler. + case $host_os in + aix*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + if test ia64 = "$host_cpu"; then + # AIX 5 now supports IA64 processor + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + else + _LT_TAGVAR(lt_prog_compiler_static, $1)='-bnso -bI:/lib/syscalls.exp' + fi + ;; + + darwin* | rhapsody*) + # PIC is the default on this platform + # Common symbols not allowed in MH_DYLIB files + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fno-common' + case $cc_basename in + nagfor*) + # NAG Fortran compiler + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,-Wl,,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-PIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + ;; + esac + ;; + + mingw* | cygwin* | pw32* | os2* | cegcc*) + # This hack is so that the source file can tell whether it is being + # built for inclusion in a dll (and should export symbols for example). + m4_if([$1], [GCJ], [], + [_LT_TAGVAR(lt_prog_compiler_pic, $1)='-DDLL_EXPORT']) + case $host_os in + os2*) + _LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-static' + ;; + esac + ;; + + hpux9* | hpux10* | hpux11*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + # PIC is the default for IA64 HP-UX and 64-bit HP-UX, but + # not for PA HP-UX. + case $host_cpu in + hppa*64*|ia64*) + # +Z the default + ;; + *) + _LT_TAGVAR(lt_prog_compiler_pic, $1)='+Z' + ;; + esac + # Is there a better lt_prog_compiler_static that works with the bundled CC? + _LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-a ${wl}archive' + ;; + + irix5* | irix6* | nonstopux*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + # PIC (with -KPIC) is the default. + _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared' + ;; + + linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) + case $cc_basename in + # old Intel for x86_64, which still supported -KPIC. + ecc*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-static' + ;; + # icc used to be incompatible with GCC. + # ICC 10 doesn't accept -KPIC any more. + icc* | ifort*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-static' + ;; + # Lahey Fortran 8.1. + lf95*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='--shared' + _LT_TAGVAR(lt_prog_compiler_static, $1)='--static' + ;; + nagfor*) + # NAG Fortran compiler + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,-Wl,,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-PIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + ;; + tcc*) + # Fabrice Bellard et al's Tiny C Compiler + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-static' + ;; + pgcc* | pgf77* | pgf90* | pgf95* | pgfortran*) + # Portland Group compilers (*not* the Pentium gcc compiler, + # which looks to be a dead project) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fpic' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + ;; + ccc*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + # All Alpha code is PIC. + _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared' + ;; + xl* | bgxl* | bgf* | mpixl*) + # IBM XL C 8.0/Fortran 10.1, 11.1 on PPC and BlueGene + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-qpic' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-qstaticlink' + ;; + *) + case `$CC -V 2>&1 | $SED 5q` in + *Sun\ Ceres\ Fortran* | *Sun*Fortran*\ [[1-7]].* | *Sun*Fortran*\ 8.[[0-3]]*) + # Sun Fortran 8.3 passes all unrecognized flags to the linker + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + _LT_TAGVAR(lt_prog_compiler_wl, $1)='' + ;; + *Sun\ F* | *Sun*Fortran*) + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Qoption ld ' + ;; + *Sun\ C*) + # Sun C 5.9 + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + ;; + *Intel*\ [[CF]]*Compiler*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-static' + ;; + *Portland\ Group*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fpic' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + ;; + esac + ;; + esac + ;; + + newsos6) + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + ;; + + *nto* | *qnx*) + # QNX uses GNU C++, but need to define -shared option too, otherwise + # it will coredump. + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC -shared' + ;; + + osf3* | osf4* | osf5*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + # All OSF/1 code is PIC. + _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared' + ;; + + rdos*) + _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared' + ;; + + solaris*) + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + case $cc_basename in + f77* | f90* | f95* | sunf77* | sunf90* | sunf95*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Qoption ld ';; + *) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,';; + esac + ;; + + sunos4*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Qoption ld ' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-PIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + ;; + + sysv4 | sysv4.2uw2* | sysv4.3*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + ;; + + sysv4*MP*) + if test -d /usr/nec; then + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-Kconform_pic' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + fi + ;; + + sysv5* | unixware* | sco3.2v5* | sco5v6* | OpenUNIX*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + ;; + + unicos*) + _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' + _LT_TAGVAR(lt_prog_compiler_can_build_shared, $1)=no + ;; + + uts4*) + _LT_TAGVAR(lt_prog_compiler_pic, $1)='-pic' + _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' + ;; + + *) + _LT_TAGVAR(lt_prog_compiler_can_build_shared, $1)=no + ;; + esac + fi +]) +case $host_os in + # For platforms that do not support PIC, -DPIC is meaningless: + *djgpp*) + _LT_TAGVAR(lt_prog_compiler_pic, $1)= + ;; + *) + _LT_TAGVAR(lt_prog_compiler_pic, $1)="$_LT_TAGVAR(lt_prog_compiler_pic, $1)@&t@m4_if([$1],[],[ -DPIC],[m4_if([$1],[CXX],[ -DPIC],[])])" + ;; +esac + +AC_CACHE_CHECK([for $compiler option to produce PIC], + [_LT_TAGVAR(lt_cv_prog_compiler_pic, $1)], + [_LT_TAGVAR(lt_cv_prog_compiler_pic, $1)=$_LT_TAGVAR(lt_prog_compiler_pic, $1)]) +_LT_TAGVAR(lt_prog_compiler_pic, $1)=$_LT_TAGVAR(lt_cv_prog_compiler_pic, $1) + +# +# Check to make sure the PIC flag actually works. +# +if test -n "$_LT_TAGVAR(lt_prog_compiler_pic, $1)"; then + _LT_COMPILER_OPTION([if $compiler PIC flag $_LT_TAGVAR(lt_prog_compiler_pic, $1) works], + [_LT_TAGVAR(lt_cv_prog_compiler_pic_works, $1)], + [$_LT_TAGVAR(lt_prog_compiler_pic, $1)@&t@m4_if([$1],[],[ -DPIC],[m4_if([$1],[CXX],[ -DPIC],[])])], [], + [case $_LT_TAGVAR(lt_prog_compiler_pic, $1) in + "" | " "*) ;; + *) _LT_TAGVAR(lt_prog_compiler_pic, $1)=" $_LT_TAGVAR(lt_prog_compiler_pic, $1)" ;; + esac], + [_LT_TAGVAR(lt_prog_compiler_pic, $1)= + _LT_TAGVAR(lt_prog_compiler_can_build_shared, $1)=no]) +fi +_LT_TAGDECL([pic_flag], [lt_prog_compiler_pic], [1], + [Additional compiler flags for building library objects]) + +_LT_TAGDECL([wl], [lt_prog_compiler_wl], [1], + [How to pass a linker flag through the compiler]) +# +# Check to make sure the static flag actually works. +# +wl=$_LT_TAGVAR(lt_prog_compiler_wl, $1) eval lt_tmp_static_flag=\"$_LT_TAGVAR(lt_prog_compiler_static, $1)\" +_LT_LINKER_OPTION([if $compiler static flag $lt_tmp_static_flag works], + _LT_TAGVAR(lt_cv_prog_compiler_static_works, $1), + $lt_tmp_static_flag, + [], + [_LT_TAGVAR(lt_prog_compiler_static, $1)=]) +_LT_TAGDECL([link_static_flag], [lt_prog_compiler_static], [1], + [Compiler flag to prevent dynamic linking]) +])# _LT_COMPILER_PIC + + +# _LT_LINKER_SHLIBS([TAGNAME]) +# ---------------------------- +# See if the linker supports building shared libraries. +m4_defun([_LT_LINKER_SHLIBS], +[AC_REQUIRE([LT_PATH_LD])dnl +AC_REQUIRE([LT_PATH_NM])dnl +m4_require([_LT_PATH_MANIFEST_TOOL])dnl +m4_require([_LT_FILEUTILS_DEFAULTS])dnl +m4_require([_LT_DECL_EGREP])dnl +m4_require([_LT_DECL_SED])dnl +m4_require([_LT_CMD_GLOBAL_SYMBOLS])dnl +m4_require([_LT_TAG_COMPILER])dnl +AC_MSG_CHECKING([whether the $compiler linker ($LD) supports shared libraries]) +m4_if([$1], [CXX], [ + _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\''s/.* //'\'' | sort | uniq > $export_symbols' + _LT_TAGVAR(exclude_expsyms, $1)=['_GLOBAL_OFFSET_TABLE_|_GLOBAL__F[ID]_.*'] + case $host_os in + aix[[4-9]]*) + # If we're using GNU nm, then we don't want the "-C" option. + # -C means demangle to GNU nm, but means don't demangle to AIX nm. + # Without the "-l" option, or with the "-B" option, AIX nm treats + # weak defined symbols like other global defined symbols, whereas + # GNU nm marks them as "W". + # While the 'weak' keyword is ignored in the Export File, we need + # it in the Import File for the 'aix-soname' feature, so we have + # to replace the "-B" option with "-P" for AIX nm. + if $NM -V 2>&1 | $GREP 'GNU' > /dev/null; then + _LT_TAGVAR(export_symbols_cmds, $1)='$NM -Bpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B") || (\$ 2 == "W")) && ([substr](\$ 3,1,1) != ".")) { if (\$ 2 == "W") { print \$ 3 " weak" } else { print \$ 3 } } }'\'' | sort -u > $export_symbols' + else + _LT_TAGVAR(export_symbols_cmds, $1)='`func_echo_all $NM | $SED -e '\''s/B\([[^B]]*\)$/P\1/'\''` -PCpgl $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B") || (\$ 2 == "L") || (\$ 2 == "W") || (\$ 2 == "V") || (\$ 2 == "Z")) && ([substr](\$ 1,1,1) != ".")) { if ((\$ 2 == "W") || (\$ 2 == "V") || (\$ 2 == "Z")) { print \$ 1 " weak" } else { print \$ 1 } } }'\'' | sort -u > $export_symbols' + fi + ;; + pw32*) + _LT_TAGVAR(export_symbols_cmds, $1)=$ltdll_cmds + ;; + cygwin* | mingw* | cegcc*) + case $cc_basename in + cl* | icl*) + _LT_TAGVAR(exclude_expsyms, $1)='_NULL_IMPORT_DESCRIPTOR|_IMPORT_DESCRIPTOR_.*' + ;; + *) + _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[[BCDGRS]][[ ]]/s/.*[[ ]]\([[^ ]]*\)/\1 DATA/;s/^.*[[ ]]__nm__\([[^ ]]*\)[[ ]][[^ ]]*/\1 DATA/;/^I[[ ]]/d;/^[[AITW]][[ ]]/s/.* //'\'' | sort | uniq > $export_symbols' + _LT_TAGVAR(exclude_expsyms, $1)=['[_]+GLOBAL_OFFSET_TABLE_|[_]+GLOBAL__[FID]_.*|[_]+head_[A-Za-z0-9_]+_dll|[A-Za-z0-9_]+_dll_iname'] + ;; + esac + ;; + *) + _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\''s/.* //'\'' | sort | uniq > $export_symbols' + ;; + esac +], [ + runpath_var= + _LT_TAGVAR(allow_undefined_flag, $1)= + _LT_TAGVAR(always_export_symbols, $1)=no + _LT_TAGVAR(archive_cmds, $1)= + _LT_TAGVAR(archive_expsym_cmds, $1)= + _LT_TAGVAR(compiler_needs_object, $1)=no + _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=no + _LT_TAGVAR(export_dynamic_flag_spec, $1)= + _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\''s/.* //'\'' | sort | uniq > $export_symbols' + _LT_TAGVAR(hardcode_automatic, $1)=no + _LT_TAGVAR(hardcode_direct, $1)=no + _LT_TAGVAR(hardcode_direct_absolute, $1)=no + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)= + _LT_TAGVAR(hardcode_libdir_separator, $1)= + _LT_TAGVAR(hardcode_minus_L, $1)=no + _LT_TAGVAR(hardcode_shlibpath_var, $1)=unsupported + _LT_TAGVAR(inherit_rpath, $1)=no + _LT_TAGVAR(link_all_deplibs, $1)=unknown + _LT_TAGVAR(module_cmds, $1)= + _LT_TAGVAR(module_expsym_cmds, $1)= + _LT_TAGVAR(old_archive_from_new_cmds, $1)= + _LT_TAGVAR(old_archive_from_expsyms_cmds, $1)= + _LT_TAGVAR(thread_safe_flag_spec, $1)= + _LT_TAGVAR(whole_archive_flag_spec, $1)= + # include_expsyms should be a list of space-separated symbols to be *always* + # included in the symbol list + _LT_TAGVAR(include_expsyms, $1)= + # exclude_expsyms can be an extended regexp of symbols to exclude + # it will be wrapped by ' (' and ')$', so one must not match beginning or + # end of line. Example: 'a|bc|.*d.*' will exclude the symbols 'a' and 'bc', + # as well as any symbol that contains 'd'. + _LT_TAGVAR(exclude_expsyms, $1)=['_GLOBAL_OFFSET_TABLE_|_GLOBAL__F[ID]_.*'] + # Although _GLOBAL_OFFSET_TABLE_ is a valid symbol C name, most a.out + # platforms (ab)use it in PIC code, but their linkers get confused if + # the symbol is explicitly referenced. Since portable code cannot + # rely on this symbol name, it's probably fine to never include it in + # preloaded symbol tables. + # Exclude shared library initialization/finalization symbols. +dnl Note also adjust exclude_expsyms for C++ above. + extract_expsyms_cmds= + + case $host_os in + cygwin* | mingw* | pw32* | cegcc*) + # FIXME: the MSVC++ and ICC port hasn't been tested in a loooong time + # When not using gcc, we currently assume that we are using + # Microsoft Visual C++ or Intel C++ Compiler. + if test yes != "$GCC"; then + with_gnu_ld=no + fi + ;; + interix*) + # we just hope/assume this is gcc and not c89 (= MSVC++ or ICC) + with_gnu_ld=yes + ;; + openbsd* | bitrig*) + with_gnu_ld=no + ;; + esac + + _LT_TAGVAR(ld_shlibs, $1)=yes + + # On some targets, GNU ld is compatible enough with the native linker + # that we're better off using the native interface for both. + lt_use_gnu_ld_interface=no + if test yes = "$with_gnu_ld"; then + case $host_os in + aix*) + # The AIX port of GNU ld has always aspired to compatibility + # with the native linker. However, as the warning in the GNU ld + # block says, versions before 2.19.5* couldn't really create working + # shared libraries, regardless of the interface used. + case `$LD -v 2>&1` in + *\ \(GNU\ Binutils\)\ 2.19.5*) ;; + *\ \(GNU\ Binutils\)\ 2.[[2-9]]*) ;; + *\ \(GNU\ Binutils\)\ [[3-9]]*) ;; + *) + lt_use_gnu_ld_interface=yes + ;; + esac + ;; + *) + lt_use_gnu_ld_interface=yes + ;; + esac + fi + + if test yes = "$lt_use_gnu_ld_interface"; then + # If archive_cmds runs LD, not CC, wlarc should be empty + wlarc='$wl' + + # Set some defaults for GNU ld with shared library support. These + # are reset later if shared libraries are not supported. Putting them + # here allows them to be overridden if necessary. + runpath_var=LD_RUN_PATH + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic' + # ancient GNU ld didn't support --whole-archive et. al. + if $LD --help 2>&1 | $GREP 'no-whole-archive' > /dev/null; then + _LT_TAGVAR(whole_archive_flag_spec, $1)=$wlarc'--whole-archive$convenience '$wlarc'--no-whole-archive' + else + _LT_TAGVAR(whole_archive_flag_spec, $1)= + fi + supports_anon_versioning=no + case `$LD -v | $SED -e 's/([[^)]]\+)\s\+//' 2>&1` in + *GNU\ gold*) supports_anon_versioning=yes ;; + *\ [[01]].* | *\ 2.[[0-9]].* | *\ 2.10.*) ;; # catch versions < 2.11 + *\ 2.11.93.0.2\ *) supports_anon_versioning=yes ;; # RH7.3 ... + *\ 2.11.92.0.12\ *) supports_anon_versioning=yes ;; # Mandrake 8.2 ... + *\ 2.11.*) ;; # other 2.11 versions + *) supports_anon_versioning=yes ;; + esac + + # See if GNU ld supports shared libraries. + case $host_os in + aix[[3-9]]*) + # On AIX/PPC, the GNU linker is very broken + if test ia64 != "$host_cpu"; then + _LT_TAGVAR(ld_shlibs, $1)=no + cat <<_LT_EOF 1>&2 + +*** Warning: the GNU linker, at least up to release 2.19, is reported +*** to be unable to reliably create shared libraries on AIX. +*** Therefore, libtool is disabling shared libraries support. If you +*** really care for shared libraries, you may want to install binutils +*** 2.20 or above, or modify your PATH so that a non-GNU linker is found. +*** You will then need to restart the configuration process. + +_LT_EOF + fi + ;; + + amigaos*) + case $host_cpu in + powerpc) + # see comment about AmigaOS4 .so support + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='' + ;; + m68k) + _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/a2ixlibrary.data~$ECHO "#define NAME $libname" > $output_objdir/a2ixlibrary.data~$ECHO "#define LIBRARY_ID 1" >> $output_objdir/a2ixlibrary.data~$ECHO "#define VERSION $major" >> $output_objdir/a2ixlibrary.data~$ECHO "#define REVISION $revision" >> $output_objdir/a2ixlibrary.data~$AR $AR_FLAGS $lib $libobjs~$RANLIB $lib~(cd $output_objdir && a2ixlibrary -32)' + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' + _LT_TAGVAR(hardcode_minus_L, $1)=yes + ;; + esac + ;; + + beos*) + if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then + _LT_TAGVAR(allow_undefined_flag, $1)=unsupported + # Joseph Beckenbach says some releases of gcc + # support --undefined. This deserves some investigation. FIXME + _LT_TAGVAR(archive_cmds, $1)='$CC -nostart $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + else + _LT_TAGVAR(ld_shlibs, $1)=no + fi + ;; + + cygwin* | mingw* | pw32* | cegcc*) + # _LT_TAGVAR(hardcode_libdir_flag_spec, $1) is actually meaningless, + # as there is no search path for DLLs. + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-all-symbols' + _LT_TAGVAR(allow_undefined_flag, $1)=unsupported + _LT_TAGVAR(always_export_symbols, $1)=no + _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes + _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[[BCDGRS]][[ ]]/s/.*[[ ]]\([[^ ]]*\)/\1 DATA/;s/^.*[[ ]]__nm__\([[^ ]]*\)[[ ]][[^ ]]*/\1 DATA/;/^I[[ ]]/d;/^[[AITW]][[ ]]/s/.* //'\'' | sort | uniq > $export_symbols' + _LT_TAGVAR(exclude_expsyms, $1)=['[_]+GLOBAL_OFFSET_TABLE_|[_]+GLOBAL__[FID]_.*|[_]+head_[A-Za-z0-9_]+_dll|[A-Za-z0-9_]+_dll_iname'] + + if $LD --help 2>&1 | $GREP 'auto-import' > /dev/null; then + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' + # If the export-symbols file already is a .def file, use it as + # is; otherwise, prepend EXPORTS... + _LT_TAGVAR(archive_expsym_cmds, $1)='if _LT_DLL_DEF_P([$export_symbols]); then + cp $export_symbols $output_objdir/$soname.def; + else + echo EXPORTS > $output_objdir/$soname.def; + cat $export_symbols >> $output_objdir/$soname.def; + fi~ + $CC -shared $output_objdir/$soname.def $libobjs $deplibs $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' + else + _LT_TAGVAR(ld_shlibs, $1)=no + fi + ;; + + haiku*) + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + _LT_TAGVAR(link_all_deplibs, $1)=yes + ;; + + os2*) + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' + _LT_TAGVAR(hardcode_minus_L, $1)=yes + _LT_TAGVAR(allow_undefined_flag, $1)=unsupported + shrext_cmds=.dll + _LT_TAGVAR(archive_cmds, $1)='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ + $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ + $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ + $ECHO EXPORTS >> $output_objdir/$libname.def~ + emxexp $libobjs | $SED /"_DLL_InitTerm"/d >> $output_objdir/$libname.def~ + $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ + emximp -o $lib $output_objdir/$libname.def' + _LT_TAGVAR(archive_expsym_cmds, $1)='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ + $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ + $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ + $ECHO EXPORTS >> $output_objdir/$libname.def~ + prefix_cmds="$SED"~ + if test EXPORTS = "`$SED 1q $export_symbols`"; then + prefix_cmds="$prefix_cmds -e 1d"; + fi~ + prefix_cmds="$prefix_cmds -e \"s/^\(.*\)$/_\1/g\""~ + cat $export_symbols | $prefix_cmds >> $output_objdir/$libname.def~ + $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ + emximp -o $lib $output_objdir/$libname.def' + _LT_TAGVAR(old_archive_From_new_cmds, $1)='emximp -o $output_objdir/${libname}_dll.a $output_objdir/$libname.def' + _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes + _LT_TAGVAR(file_list_spec, $1)='@' + ;; + + interix[[3-9]]*) + _LT_TAGVAR(hardcode_direct, $1)=no + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir' + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' + # Hack: On Interix 3.x, we cannot compile PIC because of a broken gcc. + # Instead, shared libraries are loaded at an image base (0x10000000 by + # default) and relocated if they conflict, which is a slow very memory + # consuming and fragmenting process. To avoid this, we pick a random, + # 256 KiB-aligned image base between 0x50000000 and 0x6FFC0000 at link + # time. Moving up from 0x10000000 also allows more sbrk(2) space. + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \* 262144 + 1342177280` -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='$SED "s|^|_|" $export_symbols >$output_objdir/$soname.expsym~$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--retain-symbols-file,$output_objdir/$soname.expsym $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \* 262144 + 1342177280` -o $lib' + ;; + + gnu* | linux* | tpf* | k*bsd*-gnu | kopensolaris*-gnu) + tmp_diet=no + if test linux-dietlibc = "$host_os"; then + case $cc_basename in + diet\ *) tmp_diet=yes;; # linux-dietlibc with static linking (!diet-dyn) + esac + fi + if $LD --help 2>&1 | $EGREP ': supported targets:.* elf' > /dev/null \ + && test no = "$tmp_diet" + then + tmp_addflag=' $pic_flag' + tmp_sharedflag='-shared' + case $cc_basename,$host_cpu in + pgcc*) # Portland Group C compiler + _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' + tmp_addflag=' $pic_flag' + ;; + pgf77* | pgf90* | pgf95* | pgfortran*) + # Portland Group f77 and f90 compilers + _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' + tmp_addflag=' $pic_flag -Mnomain' ;; + ecc*,ia64* | icc*,ia64*) # Intel C compiler on ia64 + tmp_addflag=' -i_dynamic' ;; + efc*,ia64* | ifort*,ia64*) # Intel Fortran compiler on ia64 + tmp_addflag=' -i_dynamic -nofor_main' ;; + ifc* | ifort*) # Intel Fortran compiler + tmp_addflag=' -nofor_main' ;; + lf95*) # Lahey Fortran 8.1 + _LT_TAGVAR(whole_archive_flag_spec, $1)= + tmp_sharedflag='--shared' ;; + nagfor*) # NAGFOR 5.3 + tmp_sharedflag='-Wl,-shared' ;; + xl[[cC]]* | bgxl[[cC]]* | mpixl[[cC]]*) # IBM XL C 8.0 on PPC (deal with xlf below) + tmp_sharedflag='-qmkshrobj' + tmp_addflag= ;; + nvcc*) # Cuda Compiler Driver 2.2 + _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' + _LT_TAGVAR(compiler_needs_object, $1)=yes + ;; + esac + case `$CC -V 2>&1 | $SED 5q` in + *Sun\ C*) # Sun C 5.9 + _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`new_convenience=; for conv in $convenience\"\"; do test -z \"$conv\" || new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' + _LT_TAGVAR(compiler_needs_object, $1)=yes + tmp_sharedflag='-G' ;; + *Sun\ F*) # Sun Fortran 8.3 + tmp_sharedflag='-G' ;; + esac + _LT_TAGVAR(archive_cmds, $1)='$CC '"$tmp_sharedflag""$tmp_addflag"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + + if test yes = "$supports_anon_versioning"; then + _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $output_objdir/$libname.ver~ + cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $output_objdir/$libname.ver~ + echo "local: *; };" >> $output_objdir/$libname.ver~ + $CC '"$tmp_sharedflag""$tmp_addflag"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-version-script $wl$output_objdir/$libname.ver -o $lib' + fi + + case $cc_basename in + tcc*) + _LT_TAGVAR(export_dynamic_flag_spec, $1)='-rdynamic' + ;; + xlf* | bgf* | bgxlf* | mpixlf*) + # IBM XL Fortran 10.1 on PPC cannot create shared libs itself + _LT_TAGVAR(whole_archive_flag_spec, $1)='--whole-archive$convenience --no-whole-archive' + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' + _LT_TAGVAR(archive_cmds, $1)='$LD -shared $libobjs $deplibs $linker_flags -soname $soname -o $lib' + if test yes = "$supports_anon_versioning"; then + _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $output_objdir/$libname.ver~ + cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $output_objdir/$libname.ver~ + echo "local: *; };" >> $output_objdir/$libname.ver~ + $LD -shared $libobjs $deplibs $linker_flags -soname $soname -version-script $output_objdir/$libname.ver -o $lib' + fi + ;; + esac + else + _LT_TAGVAR(ld_shlibs, $1)=no + fi + ;; + + netbsd*) + if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then + _LT_TAGVAR(archive_cmds, $1)='$LD -Bshareable $libobjs $deplibs $linker_flags -o $lib' + wlarc= + else + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' + fi + ;; + + solaris*) + if $LD -v 2>&1 | $GREP 'BFD 2\.8' > /dev/null; then + _LT_TAGVAR(ld_shlibs, $1)=no + cat <<_LT_EOF 1>&2 + +*** Warning: The releases 2.8.* of the GNU linker cannot reliably +*** create shared libraries on Solaris systems. Therefore, libtool +*** is disabling shared libraries support. We urge you to upgrade GNU +*** binutils to release 2.9.1 or newer. Another option is to modify +*** your PATH or compiler configuration so that the native linker is +*** used, and then restart. + +_LT_EOF + elif $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' + else + _LT_TAGVAR(ld_shlibs, $1)=no + fi + ;; + + sysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX*) + case `$LD -v 2>&1` in + *\ [[01]].* | *\ 2.[[0-9]].* | *\ 2.1[[0-5]].*) + _LT_TAGVAR(ld_shlibs, $1)=no + cat <<_LT_EOF 1>&2 + +*** Warning: Releases of the GNU linker prior to 2.16.91.0.3 cannot +*** reliably create shared libraries on SCO systems. Therefore, libtool +*** is disabling shared libraries support. We urge you to upgrade GNU +*** binutils to release 2.16.91.0.3 or newer. Another option is to modify +*** your PATH or compiler configuration so that the native linker is +*** used, and then restart. + +_LT_EOF + ;; + *) + # For security reasons, it is highly recommended that you always + # use absolute paths for naming shared libraries, and exclude the + # DT_RUNPATH tag from executables and libraries. But doing so + # requires that you compile everything twice, which is a pain. + if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' + else + _LT_TAGVAR(ld_shlibs, $1)=no + fi + ;; + esac + ;; + + sunos4*) + _LT_TAGVAR(archive_cmds, $1)='$LD -assert pure-text -Bshareable -o $lib $libobjs $deplibs $linker_flags' + wlarc= + _LT_TAGVAR(hardcode_direct, $1)=yes + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + ;; + + *) + if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' + else + _LT_TAGVAR(ld_shlibs, $1)=no + fi + ;; + esac + + if test no = "$_LT_TAGVAR(ld_shlibs, $1)"; then + runpath_var= + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)= + _LT_TAGVAR(export_dynamic_flag_spec, $1)= + _LT_TAGVAR(whole_archive_flag_spec, $1)= + fi + else + # PORTME fill in a description of your system's linker (not GNU ld) + case $host_os in + aix3*) + _LT_TAGVAR(allow_undefined_flag, $1)=unsupported + _LT_TAGVAR(always_export_symbols, $1)=yes + _LT_TAGVAR(archive_expsym_cmds, $1)='$LD -o $output_objdir/$soname $libobjs $deplibs $linker_flags -bE:$export_symbols -T512 -H512 -bM:SRE~$AR $AR_FLAGS $lib $output_objdir/$soname' + # Note: this linker hardcodes the directories in LIBPATH if there + # are no directories specified by -L. + _LT_TAGVAR(hardcode_minus_L, $1)=yes + if test yes = "$GCC" && test -z "$lt_prog_compiler_static"; then + # Neither direct hardcoding nor static linking is supported with a + # broken collect2. + _LT_TAGVAR(hardcode_direct, $1)=unsupported + fi + ;; + + aix[[4-9]]*) + if test ia64 = "$host_cpu"; then + # On IA64, the linker does run time linking by default, so we don't + # have to do anything special. + aix_use_runtimelinking=no + exp_sym_flag='-Bexport' + no_entry_flag= + else + # If we're using GNU nm, then we don't want the "-C" option. + # -C means demangle to GNU nm, but means don't demangle to AIX nm. + # Without the "-l" option, or with the "-B" option, AIX nm treats + # weak defined symbols like other global defined symbols, whereas + # GNU nm marks them as "W". + # While the 'weak' keyword is ignored in the Export File, we need + # it in the Import File for the 'aix-soname' feature, so we have + # to replace the "-B" option with "-P" for AIX nm. + if $NM -V 2>&1 | $GREP 'GNU' > /dev/null; then + _LT_TAGVAR(export_symbols_cmds, $1)='$NM -Bpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B") || (\$ 2 == "W")) && ([substr](\$ 3,1,1) != ".")) { if (\$ 2 == "W") { print \$ 3 " weak" } else { print \$ 3 } } }'\'' | sort -u > $export_symbols' + else + _LT_TAGVAR(export_symbols_cmds, $1)='`func_echo_all $NM | $SED -e '\''s/B\([[^B]]*\)$/P\1/'\''` -PCpgl $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B") || (\$ 2 == "L") || (\$ 2 == "W") || (\$ 2 == "V") || (\$ 2 == "Z")) && ([substr](\$ 1,1,1) != ".")) { if ((\$ 2 == "W") || (\$ 2 == "V") || (\$ 2 == "Z")) { print \$ 1 " weak" } else { print \$ 1 } } }'\'' | sort -u > $export_symbols' + fi + aix_use_runtimelinking=no + + # Test if we are trying to use run time linking or normal + # AIX style linking. If -brtl is somewhere in LDFLAGS, we + # have runtime linking enabled, and use it for executables. + # For shared libraries, we enable/disable runtime linking + # depending on the kind of the shared library created - + # when "with_aix_soname,aix_use_runtimelinking" is: + # "aix,no" lib.a(lib.so.V) shared, rtl:no, for executables + # "aix,yes" lib.so shared, rtl:yes, for executables + # lib.a static archive + # "both,no" lib.so.V(shr.o) shared, rtl:yes + # lib.a(lib.so.V) shared, rtl:no, for executables + # "both,yes" lib.so.V(shr.o) shared, rtl:yes, for executables + # lib.a(lib.so.V) shared, rtl:no + # "svr4,*" lib.so.V(shr.o) shared, rtl:yes, for executables + # lib.a static archive + case $host_os in aix4.[[23]]|aix4.[[23]].*|aix[[5-9]]*) + for ld_flag in $LDFLAGS; do + if (test x-brtl = "x$ld_flag" || test x-Wl,-brtl = "x$ld_flag"); then + aix_use_runtimelinking=yes + break + fi + done + if test svr4,no = "$with_aix_soname,$aix_use_runtimelinking"; then + # With aix-soname=svr4, we create the lib.so.V shared archives only, + # so we don't have lib.a shared libs to link our executables. + # We have to force runtime linking in this case. + aix_use_runtimelinking=yes + LDFLAGS="$LDFLAGS -Wl,-brtl" + fi + ;; + esac + + exp_sym_flag='-bexport' + no_entry_flag='-bnoentry' + fi + + # When large executables or shared objects are built, AIX ld can + # have problems creating the table of contents. If linking a library + # or program results in "error TOC overflow" add -mminimal-toc to + # CXXFLAGS/CFLAGS for g++/gcc. In the cases where that is not + # enough to fix the problem, add -Wl,-bbigtoc to LDFLAGS. + + _LT_TAGVAR(archive_cmds, $1)='' + _LT_TAGVAR(hardcode_direct, $1)=yes + _LT_TAGVAR(hardcode_direct_absolute, $1)=yes + _LT_TAGVAR(hardcode_libdir_separator, $1)=':' + _LT_TAGVAR(link_all_deplibs, $1)=yes + _LT_TAGVAR(file_list_spec, $1)='$wl-f,' + case $with_aix_soname,$aix_use_runtimelinking in + aix,*) ;; # traditional, no import file + svr4,* | *,yes) # use import file + # The Import File defines what to hardcode. + _LT_TAGVAR(hardcode_direct, $1)=no + _LT_TAGVAR(hardcode_direct_absolute, $1)=no + ;; + esac + + if test yes = "$GCC"; then + case $host_os in aix4.[[012]]|aix4.[[012]].*) + # We only want to do this on AIX 4.2 and lower, the check + # below for broken collect2 doesn't work under 4.3+ + collect2name=`$CC -print-prog-name=collect2` + if test -f "$collect2name" && + strings "$collect2name" | $GREP resolve_lib_name >/dev/null + then + # We have reworked collect2 + : + else + # We have old collect2 + _LT_TAGVAR(hardcode_direct, $1)=unsupported + # It fails to find uninstalled libraries when the uninstalled + # path is not listed in the libpath. Setting hardcode_minus_L + # to unsupported forces relinking + _LT_TAGVAR(hardcode_minus_L, $1)=yes + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' + _LT_TAGVAR(hardcode_libdir_separator, $1)= + fi + ;; + esac + shared_flag='-shared' + if test yes = "$aix_use_runtimelinking"; then + shared_flag="$shared_flag "'$wl-G' + fi + # Need to ensure runtime linking is disabled for the traditional + # shared library, or the linker may eventually find shared libraries + # /with/ Import File - we do not want to mix them. + shared_flag_aix='-shared' + shared_flag_svr4='-shared $wl-G' + else + # not using gcc + if test ia64 = "$host_cpu"; then + # VisualAge C++, Version 5.5 for AIX 5L for IA-64, Beta 3 Release + # chokes on -Wl,-G. The following line is correct: + shared_flag='-G' + else + if test yes = "$aix_use_runtimelinking"; then + shared_flag='$wl-G' + else + shared_flag='$wl-bM:SRE' + fi + shared_flag_aix='$wl-bM:SRE' + shared_flag_svr4='$wl-G' + fi + fi + + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-bexpall' + # It seems that -bexpall does not export symbols beginning with + # underscore (_), so it is better to generate a list of symbols to export. + _LT_TAGVAR(always_export_symbols, $1)=yes + if test aix,yes = "$with_aix_soname,$aix_use_runtimelinking"; then + # Warning - without using the other runtime loading flags (-brtl), + # -berok will link without error, but may produce a broken library. + _LT_TAGVAR(allow_undefined_flag, $1)='-berok' + # Determine the default libpath from the value encoded in an + # empty executable. + _LT_SYS_MODULE_PATH_AIX([$1]) + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-blibpath:$libdir:'"$aix_libpath" + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $deplibs $wl'$no_entry_flag' $compiler_flags `if test -n "$allow_undefined_flag"; then func_echo_all "$wl$allow_undefined_flag"; else :; fi` $wl'$exp_sym_flag:\$export_symbols' '$shared_flag + else + if test ia64 = "$host_cpu"; then + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-R $libdir:/usr/lib:/lib' + _LT_TAGVAR(allow_undefined_flag, $1)="-z nodefs" + _LT_TAGVAR(archive_expsym_cmds, $1)="\$CC $shared_flag"' -o $output_objdir/$soname $libobjs $deplibs '"\$wl$no_entry_flag"' $compiler_flags $wl$allow_undefined_flag '"\$wl$exp_sym_flag:\$export_symbols" + else + # Determine the default libpath from the value encoded in an + # empty executable. + _LT_SYS_MODULE_PATH_AIX([$1]) + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-blibpath:$libdir:'"$aix_libpath" + # Warning - without using the other run time loading flags, + # -berok will link without error, but may produce a broken library. + _LT_TAGVAR(no_undefined_flag, $1)=' $wl-bernotok' + _LT_TAGVAR(allow_undefined_flag, $1)=' $wl-berok' + if test yes = "$with_gnu_ld"; then + # We only use this code for GNU lds that support --whole-archive. + _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive$convenience $wl--no-whole-archive' + else + # Exported symbols can be pulled into shared objects from archives + _LT_TAGVAR(whole_archive_flag_spec, $1)='$convenience' + fi + _LT_TAGVAR(archive_cmds_need_lc, $1)=yes + _LT_TAGVAR(archive_expsym_cmds, $1)='$RM -r $output_objdir/$realname.d~$MKDIR $output_objdir/$realname.d' + # -brtl affects multiple linker settings, -berok does not and is overridden later + compiler_flags_filtered='`func_echo_all "$compiler_flags " | $SED -e "s%-brtl\\([[, ]]\\)%-berok\\1%g"`' + if test svr4 != "$with_aix_soname"; then + # This is similar to how AIX traditionally builds its shared libraries. + _LT_TAGVAR(archive_expsym_cmds, $1)="$_LT_TAGVAR(archive_expsym_cmds, $1)"'~$CC '$shared_flag_aix' -o $output_objdir/$realname.d/$soname $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$AR $AR_FLAGS $output_objdir/$libname$release.a $output_objdir/$realname.d/$soname' + fi + if test aix != "$with_aix_soname"; then + _LT_TAGVAR(archive_expsym_cmds, $1)="$_LT_TAGVAR(archive_expsym_cmds, $1)"'~$CC '$shared_flag_svr4' -o $output_objdir/$realname.d/$shared_archive_member_spec.o $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$STRIP -e $output_objdir/$realname.d/$shared_archive_member_spec.o~( func_echo_all "#! $soname($shared_archive_member_spec.o)"; if test shr_64 = "$shared_archive_member_spec"; then func_echo_all "# 64"; else func_echo_all "# 32"; fi; cat $export_symbols ) > $output_objdir/$realname.d/$shared_archive_member_spec.imp~$AR $AR_FLAGS $output_objdir/$soname $output_objdir/$realname.d/$shared_archive_member_spec.o $output_objdir/$realname.d/$shared_archive_member_spec.imp' + else + # used by -dlpreopen to get the symbols + _LT_TAGVAR(archive_expsym_cmds, $1)="$_LT_TAGVAR(archive_expsym_cmds, $1)"'~$MV $output_objdir/$realname.d/$soname $output_objdir' + fi + _LT_TAGVAR(archive_expsym_cmds, $1)="$_LT_TAGVAR(archive_expsym_cmds, $1)"'~$RM -r $output_objdir/$realname.d' + fi + fi + ;; + + amigaos*) + case $host_cpu in + powerpc) + # see comment about AmigaOS4 .so support + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='' + ;; + m68k) + _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/a2ixlibrary.data~$ECHO "#define NAME $libname" > $output_objdir/a2ixlibrary.data~$ECHO "#define LIBRARY_ID 1" >> $output_objdir/a2ixlibrary.data~$ECHO "#define VERSION $major" >> $output_objdir/a2ixlibrary.data~$ECHO "#define REVISION $revision" >> $output_objdir/a2ixlibrary.data~$AR $AR_FLAGS $lib $libobjs~$RANLIB $lib~(cd $output_objdir && a2ixlibrary -32)' + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' + _LT_TAGVAR(hardcode_minus_L, $1)=yes + ;; + esac + ;; + + bsdi[[45]]*) + _LT_TAGVAR(export_dynamic_flag_spec, $1)=-rdynamic + ;; + + cygwin* | mingw* | pw32* | cegcc*) + # When not using gcc, we currently assume that we are using + # Microsoft Visual C++ or Intel C++ Compiler. + # hardcode_libdir_flag_spec is actually meaningless, as there is + # no search path for DLLs. + case $cc_basename in + cl* | icl*) + # Native MSVC or ICC + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)=' ' + _LT_TAGVAR(allow_undefined_flag, $1)=unsupported + _LT_TAGVAR(always_export_symbols, $1)=yes + _LT_TAGVAR(file_list_spec, $1)='@' + # Tell ltmain to make .lib files, not .a files. + libext=lib + # Tell ltmain to make .dll files, not .so files. + shrext_cmds=.dll + # FIXME: Setting linknames here is a bad hack. + _LT_TAGVAR(archive_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $compiler_flags $deplibs -Wl,-DLL,-IMPLIB:"$tool_output_objdir$libname.dll.lib"~linknames=' + _LT_TAGVAR(archive_expsym_cmds, $1)='if _LT_DLL_DEF_P([$export_symbols]); then + cp "$export_symbols" "$output_objdir/$soname.def"; + echo "$tool_output_objdir$soname.def" > "$output_objdir/$soname.exp"; + else + $SED -e '\''s/^/-link -EXPORT:/'\'' < $export_symbols > $output_objdir/$soname.exp; + fi~ + $CC -o $tool_output_objdir$soname $libobjs $compiler_flags $deplibs "@$tool_output_objdir$soname.exp" -Wl,-DLL,-IMPLIB:"$tool_output_objdir$libname.dll.lib"~ + linknames=' + # The linker will not automatically build a static lib if we build a DLL. + # _LT_TAGVAR(old_archive_from_new_cmds, $1)='true' + _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes + _LT_TAGVAR(exclude_expsyms, $1)='_NULL_IMPORT_DESCRIPTOR|_IMPORT_DESCRIPTOR_.*' + _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[[BCDGRS]][[ ]]/s/.*[[ ]]\([[^ ]]*\)/\1,DATA/'\'' | $SED -e '\''/^[[AITW]][[ ]]/s/.*[[ ]]//'\'' | sort | uniq > $export_symbols' + # Don't use ranlib + _LT_TAGVAR(old_postinstall_cmds, $1)='chmod 644 $oldlib' + _LT_TAGVAR(postlink_cmds, $1)='lt_outputfile="@OUTPUT@"~ + lt_tool_outputfile="@TOOL_OUTPUT@"~ + case $lt_outputfile in + *.exe|*.EXE) ;; + *) + lt_outputfile=$lt_outputfile.exe + lt_tool_outputfile=$lt_tool_outputfile.exe + ;; + esac~ + if test : != "$MANIFEST_TOOL" && test -f "$lt_outputfile.manifest"; then + $MANIFEST_TOOL -manifest "$lt_tool_outputfile.manifest" -outputresource:"$lt_tool_outputfile" || exit 1; + $RM "$lt_outputfile.manifest"; + fi' + ;; + *) + # Assume MSVC and ICC wrapper + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)=' ' + _LT_TAGVAR(allow_undefined_flag, $1)=unsupported + # Tell ltmain to make .lib files, not .a files. + libext=lib + # Tell ltmain to make .dll files, not .so files. + shrext_cmds=.dll + # FIXME: Setting linknames here is a bad hack. + _LT_TAGVAR(archive_cmds, $1)='$CC -o $lib $libobjs $compiler_flags `func_echo_all "$deplibs" | $SED '\''s/ -lc$//'\''` -link -dll~linknames=' + # The linker will automatically build a .lib file if we build a DLL. + _LT_TAGVAR(old_archive_from_new_cmds, $1)='true' + # FIXME: Should let the user specify the lib program. + _LT_TAGVAR(old_archive_cmds, $1)='lib -OUT:$oldlib$oldobjs$old_deplibs' + _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes + ;; + esac + ;; + + darwin* | rhapsody*) + _LT_DARWIN_LINKER_FEATURES($1) + ;; + + dgux*) + _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + ;; + + # FreeBSD 2.2.[012] allows us to include c++rt0.o to get C++ constructor + # support. Future versions do this automatically, but an explicit c++rt0.o + # does not break anything, and helps significantly (at the cost of a little + # extra space). + freebsd2.2*) + _LT_TAGVAR(archive_cmds, $1)='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags /usr/lib/c++rt0.o' + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir' + _LT_TAGVAR(hardcode_direct, $1)=yes + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + ;; + + # Unfortunately, older versions of FreeBSD 2 do not have this feature. + freebsd2.*) + _LT_TAGVAR(archive_cmds, $1)='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags' + _LT_TAGVAR(hardcode_direct, $1)=yes + _LT_TAGVAR(hardcode_minus_L, $1)=yes + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + ;; + + # FreeBSD 3 and greater uses gcc -shared to do shared libraries. + freebsd* | dragonfly* | midnightbsd*) + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir' + _LT_TAGVAR(hardcode_direct, $1)=yes + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + ;; + + hpux9*) + if test yes = "$GCC"; then + _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/$soname~$CC -shared $pic_flag $wl+b $wl$install_libdir -o $output_objdir/$soname $libobjs $deplibs $compiler_flags~test "x$output_objdir/$soname" = "x$lib" || mv $output_objdir/$soname $lib' + else + _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/$soname~$LD -b +b $install_libdir -o $output_objdir/$soname $libobjs $deplibs $linker_flags~test "x$output_objdir/$soname" = "x$lib" || mv $output_objdir/$soname $lib' + fi + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl+b $wl$libdir' + _LT_TAGVAR(hardcode_libdir_separator, $1)=: + _LT_TAGVAR(hardcode_direct, $1)=yes + + # hardcode_minus_L: Not really in the search PATH, + # but as the default location of the library. + _LT_TAGVAR(hardcode_minus_L, $1)=yes + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' + ;; + + hpux10*) + if test yes,no = "$GCC,$with_gnu_ld"; then + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags' + else + _LT_TAGVAR(archive_cmds, $1)='$LD -b +h $soname +b $install_libdir -o $lib $libobjs $deplibs $linker_flags' + fi + if test no = "$with_gnu_ld"; then + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl+b $wl$libdir' + _LT_TAGVAR(hardcode_libdir_separator, $1)=: + _LT_TAGVAR(hardcode_direct, $1)=yes + _LT_TAGVAR(hardcode_direct_absolute, $1)=yes + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' + # hardcode_minus_L: Not really in the search PATH, + # but as the default location of the library. + _LT_TAGVAR(hardcode_minus_L, $1)=yes + fi + ;; + + hpux11*) + if test yes,no = "$GCC,$with_gnu_ld"; then + case $host_cpu in + hppa*64*) + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $wl+h $wl$soname -o $lib $libobjs $deplibs $compiler_flags' + ;; + ia64*) + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $wl+h $wl$soname $wl+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags' + ;; + *) + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags' + ;; + esac + else + case $host_cpu in + hppa*64*) + _LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname -o $lib $libobjs $deplibs $compiler_flags' + ;; + ia64*) + _LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname $wl+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags' + ;; + *) + m4_if($1, [], [ + # Older versions of the 11.00 compiler do not understand -b yet + # (HP92453-01 A.11.01.20 doesn't, HP92453-01 B.11.X.35175-35176.GP does) + _LT_LINKER_OPTION([if $CC understands -b], + _LT_TAGVAR(lt_cv_prog_compiler__b, $1), [-b], + [_LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags'], + [_LT_TAGVAR(archive_cmds, $1)='$LD -b +h $soname +b $install_libdir -o $lib $libobjs $deplibs $linker_flags'])], + [_LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags']) + ;; + esac + fi + if test no = "$with_gnu_ld"; then + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl+b $wl$libdir' + _LT_TAGVAR(hardcode_libdir_separator, $1)=: + + case $host_cpu in + hppa*64*|ia64*) + _LT_TAGVAR(hardcode_direct, $1)=no + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + ;; + *) + _LT_TAGVAR(hardcode_direct, $1)=yes + _LT_TAGVAR(hardcode_direct_absolute, $1)=yes + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' + + # hardcode_minus_L: Not really in the search PATH, + # but as the default location of the library. + _LT_TAGVAR(hardcode_minus_L, $1)=yes + ;; + esac + fi + ;; + + irix5* | irix6* | nonstopux*) + if test yes = "$GCC"; then + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' + # Try to use the -exported_symbol ld option, if it does not + # work, assume that -exports_file does not work either and + # implicitly export all symbols. + # This should be the same for all languages, so no per-tag cache variable. + AC_CACHE_CHECK([whether the $host_os linker accepts -exported_symbol], + [lt_cv_irix_exported_symbol], + [save_LDFLAGS=$LDFLAGS + LDFLAGS="$LDFLAGS -shared $wl-exported_symbol ${wl}foo $wl-update_registry $wl/dev/null" + AC_LINK_IFELSE( + [AC_LANG_SOURCE( + [AC_LANG_CASE([C], [[int foo (void) { return 0; }]], + [C++], [[int foo (void) { return 0; }]], + [Fortran 77], [[ + subroutine foo + end]], + [Fortran], [[ + subroutine foo + end]])])], + [lt_cv_irix_exported_symbol=yes], + [lt_cv_irix_exported_symbol=no]) + LDFLAGS=$save_LDFLAGS]) + if test yes = "$lt_cv_irix_exported_symbol"; then + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations $wl-exports_file $wl$export_symbols -o $lib' + fi + else + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -exports_file $export_symbols -o $lib' + fi + _LT_TAGVAR(archive_cmds_need_lc, $1)='no' + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' + _LT_TAGVAR(hardcode_libdir_separator, $1)=: + _LT_TAGVAR(inherit_rpath, $1)=yes + _LT_TAGVAR(link_all_deplibs, $1)=yes + ;; + + linux*) + case $cc_basename in + tcc*) + # Fabrice Bellard et al's Tiny C Compiler + _LT_TAGVAR(ld_shlibs, $1)=yes + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' + ;; + esac + ;; + + netbsd*) + if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then + _LT_TAGVAR(archive_cmds, $1)='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags' # a.out + else + _LT_TAGVAR(archive_cmds, $1)='$LD -shared -o $lib $libobjs $deplibs $linker_flags' # ELF + fi + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir' + _LT_TAGVAR(hardcode_direct, $1)=yes + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + ;; + + newsos6) + _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' + _LT_TAGVAR(hardcode_direct, $1)=yes + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' + _LT_TAGVAR(hardcode_libdir_separator, $1)=: + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + ;; + + *nto* | *qnx*) + ;; + + openbsd* | bitrig*) + if test -f /usr/libexec/ld.so; then + _LT_TAGVAR(hardcode_direct, $1)=yes + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + _LT_TAGVAR(hardcode_direct_absolute, $1)=yes + if test -z "`echo __ELF__ | $CC -E - | $GREP __ELF__`"; then + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags $wl-retain-symbols-file,$export_symbols' + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir' + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' + else + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir' + fi + else + _LT_TAGVAR(ld_shlibs, $1)=no + fi + ;; + + os2*) + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' + _LT_TAGVAR(hardcode_minus_L, $1)=yes + _LT_TAGVAR(allow_undefined_flag, $1)=unsupported + shrext_cmds=.dll + _LT_TAGVAR(archive_cmds, $1)='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ + $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ + $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ + $ECHO EXPORTS >> $output_objdir/$libname.def~ + emxexp $libobjs | $SED /"_DLL_InitTerm"/d >> $output_objdir/$libname.def~ + $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ + emximp -o $lib $output_objdir/$libname.def' + _LT_TAGVAR(archive_expsym_cmds, $1)='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ + $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ + $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ + $ECHO EXPORTS >> $output_objdir/$libname.def~ + prefix_cmds="$SED"~ + if test EXPORTS = "`$SED 1q $export_symbols`"; then + prefix_cmds="$prefix_cmds -e 1d"; + fi~ + prefix_cmds="$prefix_cmds -e \"s/^\(.*\)$/_\1/g\""~ + cat $export_symbols | $prefix_cmds >> $output_objdir/$libname.def~ + $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ + emximp -o $lib $output_objdir/$libname.def' + _LT_TAGVAR(old_archive_From_new_cmds, $1)='emximp -o $output_objdir/${libname}_dll.a $output_objdir/$libname.def' + _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes + _LT_TAGVAR(file_list_spec, $1)='@' + ;; + + osf3*) + if test yes = "$GCC"; then + _LT_TAGVAR(allow_undefined_flag, $1)=' $wl-expect_unresolved $wl\*' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' + else + _LT_TAGVAR(allow_undefined_flag, $1)=' -expect_unresolved \*' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' + fi + _LT_TAGVAR(archive_cmds_need_lc, $1)='no' + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' + _LT_TAGVAR(hardcode_libdir_separator, $1)=: + ;; + + osf4* | osf5*) # as osf3* with the addition of -msym flag + if test yes = "$GCC"; then + _LT_TAGVAR(allow_undefined_flag, $1)=' $wl-expect_unresolved $wl\*' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $pic_flag $libobjs $deplibs $compiler_flags $wl-msym $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' + else + _LT_TAGVAR(allow_undefined_flag, $1)=' -expect_unresolved \*' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags -msym -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='for i in `cat $export_symbols`; do printf "%s %s\\n" -exported_symbol "\$i" >> $lib.exp; done; printf "%s\\n" "-hidden">> $lib.exp~ + $CC -shared$allow_undefined_flag $wl-input $wl$lib.exp $compiler_flags $libobjs $deplibs -soname $soname `test -n "$verstring" && $ECHO "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib~$RM $lib.exp' + + # Both c and cxx compiler support -rpath directly + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-rpath $libdir' + fi + _LT_TAGVAR(archive_cmds_need_lc, $1)='no' + _LT_TAGVAR(hardcode_libdir_separator, $1)=: + ;; + + solaris*) + _LT_TAGVAR(no_undefined_flag, $1)=' -z defs' + if test yes = "$GCC"; then + wlarc='$wl' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $wl-z ${wl}text $wl-h $wl$soname -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ + $CC -shared $pic_flag $wl-z ${wl}text $wl-M $wl$lib.exp $wl-h $wl$soname -o $lib $libobjs $deplibs $compiler_flags~$RM $lib.exp' + else + case `$CC -V 2>&1` in + *"Compilers 5.0"*) + wlarc='' + _LT_TAGVAR(archive_cmds, $1)='$LD -G$allow_undefined_flag -h $soname -o $lib $libobjs $deplibs $linker_flags' + _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ + $LD -G$allow_undefined_flag -M $lib.exp -h $soname -o $lib $libobjs $deplibs $linker_flags~$RM $lib.exp' + ;; + *) + wlarc='$wl' + _LT_TAGVAR(archive_cmds, $1)='$CC -G$allow_undefined_flag -h $soname -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ + $CC -G$allow_undefined_flag -M $lib.exp -h $soname -o $lib $libobjs $deplibs $compiler_flags~$RM $lib.exp' + ;; + esac + fi + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir' + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + case $host_os in + solaris2.[[0-5]] | solaris2.[[0-5]].*) ;; + *) + # The compiler driver will combine and reorder linker options, + # but understands '-z linker_flag'. GCC discards it without '$wl', + # but is careful enough not to reorder. + # Supported since Solaris 2.6 (maybe 2.5.1?) + if test yes = "$GCC"; then + _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl-z ${wl}allextract$convenience $wl-z ${wl}defaultextract' + else + _LT_TAGVAR(whole_archive_flag_spec, $1)='-z allextract$convenience -z defaultextract' + fi + ;; + esac + _LT_TAGVAR(link_all_deplibs, $1)=yes + ;; + + sunos4*) + if test sequent = "$host_vendor"; then + # Use $CC to link under sequent, because it throws in some extra .o + # files that make .init and .fini sections work. + _LT_TAGVAR(archive_cmds, $1)='$CC -G $wl-h $soname -o $lib $libobjs $deplibs $compiler_flags' + else + _LT_TAGVAR(archive_cmds, $1)='$LD -assert pure-text -Bstatic -o $lib $libobjs $deplibs $linker_flags' + fi + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' + _LT_TAGVAR(hardcode_direct, $1)=yes + _LT_TAGVAR(hardcode_minus_L, $1)=yes + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + ;; + + sysv4) + case $host_vendor in + sni) + _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' + _LT_TAGVAR(hardcode_direct, $1)=yes # is this really true??? + ;; + siemens) + ## LD is ld it makes a PLAMLIB + ## CC just makes a GrossModule. + _LT_TAGVAR(archive_cmds, $1)='$LD -G -o $lib $libobjs $deplibs $linker_flags' + _LT_TAGVAR(reload_cmds, $1)='$CC -r -o $output$reload_objs' + _LT_TAGVAR(hardcode_direct, $1)=no + ;; + motorola) + _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' + _LT_TAGVAR(hardcode_direct, $1)=no #Motorola manual says yes, but my tests say they lie + ;; + esac + runpath_var='LD_RUN_PATH' + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + ;; + + sysv4.3*) + _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + _LT_TAGVAR(export_dynamic_flag_spec, $1)='-Bexport' + ;; + + sysv4*MP*) + if test -d /usr/nec; then + _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + runpath_var=LD_RUN_PATH + hardcode_runpath_var=yes + _LT_TAGVAR(ld_shlibs, $1)=yes + fi + ;; + + sysv4*uw2* | sysv5OpenUNIX* | sysv5UnixWare7.[[01]].[[10]]* | unixware7* | sco3.2v5.0.[[024]]*) + _LT_TAGVAR(no_undefined_flag, $1)='$wl-z,text' + _LT_TAGVAR(archive_cmds_need_lc, $1)=no + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + runpath_var='LD_RUN_PATH' + + if test yes = "$GCC"; then + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + else + _LT_TAGVAR(archive_cmds, $1)='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + fi + ;; + + sysv5* | sco3.2v5* | sco5v6*) + # Note: We CANNOT use -z defs as we might desire, because we do not + # link with -lc, and that would cause any symbols used from libc to + # always be unresolved, which means just about no library would + # ever link correctly. If we're not using GNU ld we use -z text + # though, which does catch some bad symbols but isn't as heavy-handed + # as -z defs. + _LT_TAGVAR(no_undefined_flag, $1)='$wl-z,text' + _LT_TAGVAR(allow_undefined_flag, $1)='$wl-z,nodefs' + _LT_TAGVAR(archive_cmds_need_lc, $1)=no + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-R,$libdir' + _LT_TAGVAR(hardcode_libdir_separator, $1)=':' + _LT_TAGVAR(link_all_deplibs, $1)=yes + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-Bexport' + runpath_var='LD_RUN_PATH' + + if test yes = "$GCC"; then + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + else + _LT_TAGVAR(archive_cmds, $1)='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + fi + ;; + + uts4*) + _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + ;; + + *) + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + esac + + if test sni = "$host_vendor"; then + case $host in + sysv4 | sysv4.2uw2* | sysv4.3* | sysv5*) + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-Blargedynsym' + ;; + esac + fi + fi +]) +AC_MSG_RESULT([$_LT_TAGVAR(ld_shlibs, $1)]) +test no = "$_LT_TAGVAR(ld_shlibs, $1)" && can_build_shared=no + +_LT_TAGVAR(with_gnu_ld, $1)=$with_gnu_ld + +_LT_DECL([], [libext], [0], [Old archive suffix (normally "a")])dnl +_LT_DECL([], [shrext_cmds], [1], [Shared library suffix (normally ".so")])dnl +_LT_DECL([], [extract_expsyms_cmds], [2], + [The commands to extract the exported symbol list from a shared archive]) + +# +# Do we need to explicitly link libc? +# +case "x$_LT_TAGVAR(archive_cmds_need_lc, $1)" in +x|xyes) + # Assume -lc should be added + _LT_TAGVAR(archive_cmds_need_lc, $1)=yes + + if test yes,yes = "$GCC,$enable_shared"; then + case $_LT_TAGVAR(archive_cmds, $1) in + *'~'*) + # FIXME: we may have to deal with multi-command sequences. + ;; + '$CC '*) + # Test whether the compiler implicitly links with -lc since on some + # systems, -lgcc has to come before -lc. If gcc already passes -lc + # to ld, don't add -lc before -lgcc. + AC_CACHE_CHECK([whether -lc should be explicitly linked in], + [lt_cv_]_LT_TAGVAR(archive_cmds_need_lc, $1), + [$RM conftest* + echo "$lt_simple_compile_test_code" > conftest.$ac_ext + + if AC_TRY_EVAL(ac_compile) 2>conftest.err; then + soname=conftest + lib=conftest + libobjs=conftest.$ac_objext + deplibs= + wl=$_LT_TAGVAR(lt_prog_compiler_wl, $1) + pic_flag=$_LT_TAGVAR(lt_prog_compiler_pic, $1) + compiler_flags=-v + linker_flags=-v + verstring= + output_objdir=. + libname=conftest + lt_save_allow_undefined_flag=$_LT_TAGVAR(allow_undefined_flag, $1) + _LT_TAGVAR(allow_undefined_flag, $1)= + if AC_TRY_EVAL(_LT_TAGVAR(archive_cmds, $1) 2\>\&1 \| $GREP \" -lc \" \>/dev/null 2\>\&1) + then + lt_cv_[]_LT_TAGVAR(archive_cmds_need_lc, $1)=no + else + lt_cv_[]_LT_TAGVAR(archive_cmds_need_lc, $1)=yes + fi + _LT_TAGVAR(allow_undefined_flag, $1)=$lt_save_allow_undefined_flag + else + cat conftest.err 1>&5 + fi + $RM conftest* + ]) + _LT_TAGVAR(archive_cmds_need_lc, $1)=$lt_cv_[]_LT_TAGVAR(archive_cmds_need_lc, $1) + ;; + esac + fi + ;; +esac + +_LT_TAGDECL([build_libtool_need_lc], [archive_cmds_need_lc], [0], + [Whether or not to add -lc for building shared libraries]) +_LT_TAGDECL([allow_libtool_libs_with_static_runtimes], + [enable_shared_with_static_runtimes], [0], + [Whether or not to disallow shared libs when runtime libs are static]) +_LT_TAGDECL([], [export_dynamic_flag_spec], [1], + [Compiler flag to allow reflexive dlopens]) +_LT_TAGDECL([], [whole_archive_flag_spec], [1], + [Compiler flag to generate shared objects directly from archives]) +_LT_TAGDECL([], [compiler_needs_object], [1], + [Whether the compiler copes with passing no objects directly]) +_LT_TAGDECL([], [old_archive_from_new_cmds], [2], + [Create an old-style archive from a shared archive]) +_LT_TAGDECL([], [old_archive_from_expsyms_cmds], [2], + [Create a temporary old-style archive to link instead of a shared archive]) +_LT_TAGDECL([], [archive_cmds], [2], [Commands used to build a shared archive]) +_LT_TAGDECL([], [archive_expsym_cmds], [2]) +_LT_TAGDECL([], [module_cmds], [2], + [Commands used to build a loadable module if different from building + a shared archive.]) +_LT_TAGDECL([], [module_expsym_cmds], [2]) +_LT_TAGDECL([], [with_gnu_ld], [1], + [Whether we are building with GNU ld or not]) +_LT_TAGDECL([], [allow_undefined_flag], [1], + [Flag that allows shared libraries with undefined symbols to be built]) +_LT_TAGDECL([], [no_undefined_flag], [1], + [Flag that enforces no undefined symbols]) +_LT_TAGDECL([], [hardcode_libdir_flag_spec], [1], + [Flag to hardcode $libdir into a binary during linking. + This must work even if $libdir does not exist]) +_LT_TAGDECL([], [hardcode_libdir_separator], [1], + [Whether we need a single "-rpath" flag with a separated argument]) +_LT_TAGDECL([], [hardcode_direct], [0], + [Set to "yes" if using DIR/libNAME$shared_ext during linking hardcodes + DIR into the resulting binary]) +_LT_TAGDECL([], [hardcode_direct_absolute], [0], + [Set to "yes" if using DIR/libNAME$shared_ext during linking hardcodes + DIR into the resulting binary and the resulting library dependency is + "absolute", i.e impossible to change by setting $shlibpath_var if the + library is relocated]) +_LT_TAGDECL([], [hardcode_minus_L], [0], + [Set to "yes" if using the -LDIR flag during linking hardcodes DIR + into the resulting binary]) +_LT_TAGDECL([], [hardcode_shlibpath_var], [0], + [Set to "yes" if using SHLIBPATH_VAR=DIR during linking hardcodes DIR + into the resulting binary]) +_LT_TAGDECL([], [hardcode_automatic], [0], + [Set to "yes" if building a shared library automatically hardcodes DIR + into the library and all subsequent libraries and executables linked + against it]) +_LT_TAGDECL([], [inherit_rpath], [0], + [Set to yes if linker adds runtime paths of dependent libraries + to runtime path list]) +_LT_TAGDECL([], [link_all_deplibs], [0], + [Whether libtool must link a program against all its dependency libraries]) +_LT_TAGDECL([], [always_export_symbols], [0], + [Set to "yes" if exported symbols are required]) +_LT_TAGDECL([], [export_symbols_cmds], [2], + [The commands to list exported symbols]) +_LT_TAGDECL([], [exclude_expsyms], [1], + [Symbols that should not be listed in the preloaded symbols]) +_LT_TAGDECL([], [include_expsyms], [1], + [Symbols that must always be exported]) +_LT_TAGDECL([], [prelink_cmds], [2], + [Commands necessary for linking programs (against libraries) with templates]) +_LT_TAGDECL([], [postlink_cmds], [2], + [Commands necessary for finishing linking programs]) +_LT_TAGDECL([], [file_list_spec], [1], + [Specify filename containing input files]) +dnl FIXME: Not yet implemented +dnl _LT_TAGDECL([], [thread_safe_flag_spec], [1], +dnl [Compiler flag to generate thread safe objects]) +])# _LT_LINKER_SHLIBS + + +# _LT_LANG_C_CONFIG([TAG]) +# ------------------------ +# Ensure that the configuration variables for a C compiler are suitably +# defined. These variables are subsequently used by _LT_CONFIG to write +# the compiler configuration to 'libtool'. +m4_defun([_LT_LANG_C_CONFIG], +[m4_require([_LT_DECL_EGREP])dnl +lt_save_CC=$CC +AC_LANG_PUSH(C) + +# Source file extension for C test sources. +ac_ext=c + +# Object file extension for compiled C test sources. +objext=o +_LT_TAGVAR(objext, $1)=$objext + +# Code to be used in simple compile tests +lt_simple_compile_test_code="int some_variable = 0;" + +# Code to be used in simple link tests +lt_simple_link_test_code='int main(){return(0);}' + +_LT_TAG_COMPILER +# Save the default compiler, since it gets overwritten when the other +# tags are being tested, and _LT_TAGVAR(compiler, []) is a NOP. +compiler_DEFAULT=$CC + +# save warnings/boilerplate of simple test code +_LT_COMPILER_BOILERPLATE +_LT_LINKER_BOILERPLATE + +if test -n "$compiler"; then + _LT_COMPILER_NO_RTTI($1) + _LT_COMPILER_PIC($1) + _LT_COMPILER_C_O($1) + _LT_COMPILER_FILE_LOCKS($1) + _LT_LINKER_SHLIBS($1) + _LT_SYS_DYNAMIC_LINKER($1) + _LT_LINKER_HARDCODE_LIBPATH($1) + LT_SYS_DLOPEN_SELF + _LT_CMD_STRIPLIB + + # Report what library types will actually be built + AC_MSG_CHECKING([if libtool supports shared libraries]) + AC_MSG_RESULT([$can_build_shared]) + + AC_MSG_CHECKING([whether to build shared libraries]) + test no = "$can_build_shared" && enable_shared=no + + # On AIX, shared libraries and static libraries use the same namespace, and + # are all built from PIC. + case $host_os in + aix3*) + test yes = "$enable_shared" && enable_static=no + if test -n "$RANLIB"; then + archive_cmds="$archive_cmds~\$RANLIB \$lib" + postinstall_cmds='$RANLIB $lib' + fi + ;; + + aix[[4-9]]*) + if test ia64 != "$host_cpu"; then + case $enable_shared,$with_aix_soname,$aix_use_runtimelinking in + yes,aix,yes) ;; # shared object as lib.so file only + yes,svr4,*) ;; # shared object as lib.so archive member only + yes,*) enable_static=no ;; # shared object in lib.a archive as well + esac + fi + ;; + esac + AC_MSG_RESULT([$enable_shared]) + + AC_MSG_CHECKING([whether to build static libraries]) + # Make sure either enable_shared or enable_static is yes. + test yes = "$enable_shared" || enable_static=yes + AC_MSG_RESULT([$enable_static]) + + _LT_CONFIG($1) +fi +AC_LANG_POP +CC=$lt_save_CC +])# _LT_LANG_C_CONFIG + + +# _LT_LANG_CXX_CONFIG([TAG]) +# -------------------------- +# Ensure that the configuration variables for a C++ compiler are suitably +# defined. These variables are subsequently used by _LT_CONFIG to write +# the compiler configuration to 'libtool'. +m4_defun([_LT_LANG_CXX_CONFIG], +[m4_require([_LT_FILEUTILS_DEFAULTS])dnl +m4_require([_LT_DECL_EGREP])dnl +m4_require([_LT_PATH_MANIFEST_TOOL])dnl +if test -n "$CXX" && ( test no != "$CXX" && + ( (test g++ = "$CXX" && `g++ -v >/dev/null 2>&1` ) || + (test g++ != "$CXX"))); then + AC_PROG_CXXCPP +else + _lt_caught_CXX_error=yes +fi + +AC_LANG_PUSH(C++) +_LT_TAGVAR(archive_cmds_need_lc, $1)=no +_LT_TAGVAR(allow_undefined_flag, $1)= +_LT_TAGVAR(always_export_symbols, $1)=no +_LT_TAGVAR(archive_expsym_cmds, $1)= +_LT_TAGVAR(compiler_needs_object, $1)=no +_LT_TAGVAR(export_dynamic_flag_spec, $1)= +_LT_TAGVAR(hardcode_direct, $1)=no +_LT_TAGVAR(hardcode_direct_absolute, $1)=no +_LT_TAGVAR(hardcode_libdir_flag_spec, $1)= +_LT_TAGVAR(hardcode_libdir_separator, $1)= +_LT_TAGVAR(hardcode_minus_L, $1)=no +_LT_TAGVAR(hardcode_shlibpath_var, $1)=unsupported +_LT_TAGVAR(hardcode_automatic, $1)=no +_LT_TAGVAR(inherit_rpath, $1)=no +_LT_TAGVAR(module_cmds, $1)= +_LT_TAGVAR(module_expsym_cmds, $1)= +_LT_TAGVAR(link_all_deplibs, $1)=unknown +_LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds +_LT_TAGVAR(reload_flag, $1)=$reload_flag +_LT_TAGVAR(reload_cmds, $1)=$reload_cmds +_LT_TAGVAR(no_undefined_flag, $1)= +_LT_TAGVAR(whole_archive_flag_spec, $1)= +_LT_TAGVAR(enable_shared_with_static_runtimes, $1)=no + +# Source file extension for C++ test sources. +ac_ext=cpp + +# Object file extension for compiled C++ test sources. +objext=o +_LT_TAGVAR(objext, $1)=$objext + +# No sense in running all these tests if we already determined that +# the CXX compiler isn't working. Some variables (like enable_shared) +# are currently assumed to apply to all compilers on this platform, +# and will be corrupted by setting them based on a non-working compiler. +if test yes != "$_lt_caught_CXX_error"; then + # Code to be used in simple compile tests + lt_simple_compile_test_code="int some_variable = 0;" + + # Code to be used in simple link tests + lt_simple_link_test_code='int main(int, char *[[]]) { return(0); }' + + # ltmain only uses $CC for tagged configurations so make sure $CC is set. + _LT_TAG_COMPILER + + # save warnings/boilerplate of simple test code + _LT_COMPILER_BOILERPLATE + _LT_LINKER_BOILERPLATE + + # Allow CC to be a program name with arguments. + lt_save_CC=$CC + lt_save_CFLAGS=$CFLAGS + lt_save_LD=$LD + lt_save_GCC=$GCC + GCC=$GXX + lt_save_with_gnu_ld=$with_gnu_ld + lt_save_path_LD=$lt_cv_path_LD + if test -n "${lt_cv_prog_gnu_ldcxx+set}"; then + lt_cv_prog_gnu_ld=$lt_cv_prog_gnu_ldcxx + else + $as_unset lt_cv_prog_gnu_ld + fi + if test -n "${lt_cv_path_LDCXX+set}"; then + lt_cv_path_LD=$lt_cv_path_LDCXX + else + $as_unset lt_cv_path_LD + fi + test -z "${LDCXX+set}" || LD=$LDCXX + CC=${CXX-"c++"} + CFLAGS=$CXXFLAGS + compiler=$CC + _LT_TAGVAR(compiler, $1)=$CC + _LT_CC_BASENAME([$compiler]) + + if test -n "$compiler"; then + # We don't want -fno-exception when compiling C++ code, so set the + # no_builtin_flag separately + if test yes = "$GXX"; then + _LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)=' -fno-builtin' + else + _LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)= + fi + + if test yes = "$GXX"; then + # Set up default GNU C++ configuration + + LT_PATH_LD + + # Check if GNU C++ uses GNU ld as the underlying linker, since the + # archiving commands below assume that GNU ld is being used. + if test yes = "$with_gnu_ld"; then + _LT_TAGVAR(archive_cmds, $1)='$CC $pic_flag -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC $pic_flag -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' + + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic' + + # If archive_cmds runs LD, not CC, wlarc should be empty + # XXX I think wlarc can be eliminated in ltcf-cxx, but I need to + # investigate it a little bit more. (MM) + wlarc='$wl' + + # ancient GNU ld didn't support --whole-archive et. al. + if eval "`$CC -print-prog-name=ld` --help 2>&1" | + $GREP 'no-whole-archive' > /dev/null; then + _LT_TAGVAR(whole_archive_flag_spec, $1)=$wlarc'--whole-archive$convenience '$wlarc'--no-whole-archive' + else + _LT_TAGVAR(whole_archive_flag_spec, $1)= + fi + else + with_gnu_ld=no + wlarc= + + # A generic and very simple default shared library creation + # command for GNU C++ for the case where it uses the native + # linker, instead of GNU ld. If possible, this setting should + # overridden to take advantage of the native linker features on + # the platform it is being used on. + _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $lib' + fi + + # Commands to make compiler produce verbose output that lists + # what "hidden" libraries, object files and flags are used when + # linking a shared library. + output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v "^Configured with:" | $GREP "\-L"' + + else + GXX=no + with_gnu_ld=no + wlarc= + fi + + # PORTME: fill in a description of your system's C++ link characteristics + AC_MSG_CHECKING([whether the $compiler linker ($LD) supports shared libraries]) + _LT_TAGVAR(ld_shlibs, $1)=yes + case $host_os in + aix3*) + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + aix[[4-9]]*) + if test ia64 = "$host_cpu"; then + # On IA64, the linker does run time linking by default, so we don't + # have to do anything special. + aix_use_runtimelinking=no + exp_sym_flag='-Bexport' + no_entry_flag= + else + aix_use_runtimelinking=no + + # Test if we are trying to use run time linking or normal + # AIX style linking. If -brtl is somewhere in LDFLAGS, we + # have runtime linking enabled, and use it for executables. + # For shared libraries, we enable/disable runtime linking + # depending on the kind of the shared library created - + # when "with_aix_soname,aix_use_runtimelinking" is: + # "aix,no" lib.a(lib.so.V) shared, rtl:no, for executables + # "aix,yes" lib.so shared, rtl:yes, for executables + # lib.a static archive + # "both,no" lib.so.V(shr.o) shared, rtl:yes + # lib.a(lib.so.V) shared, rtl:no, for executables + # "both,yes" lib.so.V(shr.o) shared, rtl:yes, for executables + # lib.a(lib.so.V) shared, rtl:no + # "svr4,*" lib.so.V(shr.o) shared, rtl:yes, for executables + # lib.a static archive + case $host_os in aix4.[[23]]|aix4.[[23]].*|aix[[5-9]]*) + for ld_flag in $LDFLAGS; do + case $ld_flag in + *-brtl*) + aix_use_runtimelinking=yes + break + ;; + esac + done + if test svr4,no = "$with_aix_soname,$aix_use_runtimelinking"; then + # With aix-soname=svr4, we create the lib.so.V shared archives only, + # so we don't have lib.a shared libs to link our executables. + # We have to force runtime linking in this case. + aix_use_runtimelinking=yes + LDFLAGS="$LDFLAGS -Wl,-brtl" + fi + ;; + esac + + exp_sym_flag='-bexport' + no_entry_flag='-bnoentry' + fi + + # When large executables or shared objects are built, AIX ld can + # have problems creating the table of contents. If linking a library + # or program results in "error TOC overflow" add -mminimal-toc to + # CXXFLAGS/CFLAGS for g++/gcc. In the cases where that is not + # enough to fix the problem, add -Wl,-bbigtoc to LDFLAGS. + + _LT_TAGVAR(archive_cmds, $1)='' + _LT_TAGVAR(hardcode_direct, $1)=yes + _LT_TAGVAR(hardcode_direct_absolute, $1)=yes + _LT_TAGVAR(hardcode_libdir_separator, $1)=':' + _LT_TAGVAR(link_all_deplibs, $1)=yes + _LT_TAGVAR(file_list_spec, $1)='$wl-f,' + case $with_aix_soname,$aix_use_runtimelinking in + aix,*) ;; # no import file + svr4,* | *,yes) # use import file + # The Import File defines what to hardcode. + _LT_TAGVAR(hardcode_direct, $1)=no + _LT_TAGVAR(hardcode_direct_absolute, $1)=no + ;; + esac + + if test yes = "$GXX"; then + case $host_os in aix4.[[012]]|aix4.[[012]].*) + # We only want to do this on AIX 4.2 and lower, the check + # below for broken collect2 doesn't work under 4.3+ + collect2name=`$CC -print-prog-name=collect2` + if test -f "$collect2name" && + strings "$collect2name" | $GREP resolve_lib_name >/dev/null + then + # We have reworked collect2 + : + else + # We have old collect2 + _LT_TAGVAR(hardcode_direct, $1)=unsupported + # It fails to find uninstalled libraries when the uninstalled + # path is not listed in the libpath. Setting hardcode_minus_L + # to unsupported forces relinking + _LT_TAGVAR(hardcode_minus_L, $1)=yes + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' + _LT_TAGVAR(hardcode_libdir_separator, $1)= + fi + esac + shared_flag='-shared' + if test yes = "$aix_use_runtimelinking"; then + shared_flag=$shared_flag' $wl-G' + fi + # Need to ensure runtime linking is disabled for the traditional + # shared library, or the linker may eventually find shared libraries + # /with/ Import File - we do not want to mix them. + shared_flag_aix='-shared' + shared_flag_svr4='-shared $wl-G' + else + # not using gcc + if test ia64 = "$host_cpu"; then + # VisualAge C++, Version 5.5 for AIX 5L for IA-64, Beta 3 Release + # chokes on -Wl,-G. The following line is correct: + shared_flag='-G' + else + if test yes = "$aix_use_runtimelinking"; then + shared_flag='$wl-G' + else + shared_flag='$wl-bM:SRE' + fi + shared_flag_aix='$wl-bM:SRE' + shared_flag_svr4='$wl-G' + fi + fi + + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-bexpall' + # It seems that -bexpall does not export symbols beginning with + # underscore (_), so it is better to generate a list of symbols to + # export. + _LT_TAGVAR(always_export_symbols, $1)=yes + if test aix,yes = "$with_aix_soname,$aix_use_runtimelinking"; then + # Warning - without using the other runtime loading flags (-brtl), + # -berok will link without error, but may produce a broken library. + # The "-G" linker flag allows undefined symbols. + _LT_TAGVAR(no_undefined_flag, $1)='-bernotok' + # Determine the default libpath from the value encoded in an empty + # executable. + _LT_SYS_MODULE_PATH_AIX([$1]) + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-blibpath:$libdir:'"$aix_libpath" + + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $deplibs $wl'$no_entry_flag' $compiler_flags `if test -n "$allow_undefined_flag"; then func_echo_all "$wl$allow_undefined_flag"; else :; fi` $wl'$exp_sym_flag:\$export_symbols' '$shared_flag + else + if test ia64 = "$host_cpu"; then + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-R $libdir:/usr/lib:/lib' + _LT_TAGVAR(allow_undefined_flag, $1)="-z nodefs" + _LT_TAGVAR(archive_expsym_cmds, $1)="\$CC $shared_flag"' -o $output_objdir/$soname $libobjs $deplibs '"\$wl$no_entry_flag"' $compiler_flags $wl$allow_undefined_flag '"\$wl$exp_sym_flag:\$export_symbols" + else + # Determine the default libpath from the value encoded in an + # empty executable. + _LT_SYS_MODULE_PATH_AIX([$1]) + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-blibpath:$libdir:'"$aix_libpath" + # Warning - without using the other run time loading flags, + # -berok will link without error, but may produce a broken library. + _LT_TAGVAR(no_undefined_flag, $1)=' $wl-bernotok' + _LT_TAGVAR(allow_undefined_flag, $1)=' $wl-berok' + if test yes = "$with_gnu_ld"; then + # We only use this code for GNU lds that support --whole-archive. + _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive$convenience $wl--no-whole-archive' + else + # Exported symbols can be pulled into shared objects from archives + _LT_TAGVAR(whole_archive_flag_spec, $1)='$convenience' + fi + _LT_TAGVAR(archive_cmds_need_lc, $1)=yes + _LT_TAGVAR(archive_expsym_cmds, $1)='$RM -r $output_objdir/$realname.d~$MKDIR $output_objdir/$realname.d' + # -brtl affects multiple linker settings, -berok does not and is overridden later + compiler_flags_filtered='`func_echo_all "$compiler_flags " | $SED -e "s%-brtl\\([[, ]]\\)%-berok\\1%g"`' + if test svr4 != "$with_aix_soname"; then + # This is similar to how AIX traditionally builds its shared + # libraries. Need -bnortl late, we may have -brtl in LDFLAGS. + _LT_TAGVAR(archive_expsym_cmds, $1)="$_LT_TAGVAR(archive_expsym_cmds, $1)"'~$CC '$shared_flag_aix' -o $output_objdir/$realname.d/$soname $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$AR $AR_FLAGS $output_objdir/$libname$release.a $output_objdir/$realname.d/$soname' + fi + if test aix != "$with_aix_soname"; then + _LT_TAGVAR(archive_expsym_cmds, $1)="$_LT_TAGVAR(archive_expsym_cmds, $1)"'~$CC '$shared_flag_svr4' -o $output_objdir/$realname.d/$shared_archive_member_spec.o $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$STRIP -e $output_objdir/$realname.d/$shared_archive_member_spec.o~( func_echo_all "#! $soname($shared_archive_member_spec.o)"; if test shr_64 = "$shared_archive_member_spec"; then func_echo_all "# 64"; else func_echo_all "# 32"; fi; cat $export_symbols ) > $output_objdir/$realname.d/$shared_archive_member_spec.imp~$AR $AR_FLAGS $output_objdir/$soname $output_objdir/$realname.d/$shared_archive_member_spec.o $output_objdir/$realname.d/$shared_archive_member_spec.imp' + else + # used by -dlpreopen to get the symbols + _LT_TAGVAR(archive_expsym_cmds, $1)="$_LT_TAGVAR(archive_expsym_cmds, $1)"'~$MV $output_objdir/$realname.d/$soname $output_objdir' + fi + _LT_TAGVAR(archive_expsym_cmds, $1)="$_LT_TAGVAR(archive_expsym_cmds, $1)"'~$RM -r $output_objdir/$realname.d' + fi + fi + ;; + + beos*) + if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then + _LT_TAGVAR(allow_undefined_flag, $1)=unsupported + # Joseph Beckenbach says some releases of gcc + # support --undefined. This deserves some investigation. FIXME + _LT_TAGVAR(archive_cmds, $1)='$CC -nostart $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + else + _LT_TAGVAR(ld_shlibs, $1)=no + fi + ;; + + chorus*) + case $cc_basename in + *) + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + esac + ;; + + cygwin* | mingw* | pw32* | cegcc*) + case $GXX,$cc_basename in + ,cl* | no,cl* | ,icl* | no,icl*) + # Native MSVC or ICC + # hardcode_libdir_flag_spec is actually meaningless, as there is + # no search path for DLLs. + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)=' ' + _LT_TAGVAR(allow_undefined_flag, $1)=unsupported + _LT_TAGVAR(always_export_symbols, $1)=yes + _LT_TAGVAR(file_list_spec, $1)='@' + # Tell ltmain to make .lib files, not .a files. + libext=lib + # Tell ltmain to make .dll files, not .so files. + shrext_cmds=.dll + # FIXME: Setting linknames here is a bad hack. + _LT_TAGVAR(archive_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $compiler_flags $deplibs -Wl,-DLL,-IMPLIB:"$tool_output_objdir$libname.dll.lib"~linknames=' + _LT_TAGVAR(archive_expsym_cmds, $1)='if _LT_DLL_DEF_P([$export_symbols]); then + cp "$export_symbols" "$output_objdir/$soname.def"; + echo "$tool_output_objdir$soname.def" > "$output_objdir/$soname.exp"; + else + $SED -e '\''s/^/-link -EXPORT:/'\'' < $export_symbols > $output_objdir/$soname.exp; + fi~ + $CC -o $tool_output_objdir$soname $libobjs $compiler_flags $deplibs "@$tool_output_objdir$soname.exp" -Wl,-DLL,-IMPLIB:"$tool_output_objdir$libname.dll.lib"~ + linknames=' + # The linker will not automatically build a static lib if we build a DLL. + # _LT_TAGVAR(old_archive_from_new_cmds, $1)='true' + _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes + # Don't use ranlib + _LT_TAGVAR(old_postinstall_cmds, $1)='chmod 644 $oldlib' + _LT_TAGVAR(postlink_cmds, $1)='lt_outputfile="@OUTPUT@"~ + lt_tool_outputfile="@TOOL_OUTPUT@"~ + case $lt_outputfile in + *.exe|*.EXE) ;; + *) + lt_outputfile=$lt_outputfile.exe + lt_tool_outputfile=$lt_tool_outputfile.exe + ;; + esac~ + func_to_tool_file "$lt_outputfile"~ + if test : != "$MANIFEST_TOOL" && test -f "$lt_outputfile.manifest"; then + $MANIFEST_TOOL -manifest "$lt_tool_outputfile.manifest" -outputresource:"$lt_tool_outputfile" || exit 1; + $RM "$lt_outputfile.manifest"; + fi' + ;; + *) + # g++ + # _LT_TAGVAR(hardcode_libdir_flag_spec, $1) is actually meaningless, + # as there is no search path for DLLs. + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-all-symbols' + _LT_TAGVAR(allow_undefined_flag, $1)=unsupported + _LT_TAGVAR(always_export_symbols, $1)=no + _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes + + if $LD --help 2>&1 | $GREP 'auto-import' > /dev/null; then + _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' + # If the export-symbols file already is a .def file, use it as + # is; otherwise, prepend EXPORTS... + _LT_TAGVAR(archive_expsym_cmds, $1)='if _LT_DLL_DEF_P([$export_symbols]); then + cp $export_symbols $output_objdir/$soname.def; + else + echo EXPORTS > $output_objdir/$soname.def; + cat $export_symbols >> $output_objdir/$soname.def; + fi~ + $CC -shared -nostdlib $output_objdir/$soname.def $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' + else + _LT_TAGVAR(ld_shlibs, $1)=no + fi + ;; + esac + ;; + darwin* | rhapsody*) + _LT_DARWIN_LINKER_FEATURES($1) + ;; + + os2*) + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' + _LT_TAGVAR(hardcode_minus_L, $1)=yes + _LT_TAGVAR(allow_undefined_flag, $1)=unsupported + shrext_cmds=.dll + _LT_TAGVAR(archive_cmds, $1)='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ + $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ + $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ + $ECHO EXPORTS >> $output_objdir/$libname.def~ + emxexp $libobjs | $SED /"_DLL_InitTerm"/d >> $output_objdir/$libname.def~ + $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ + emximp -o $lib $output_objdir/$libname.def' + _LT_TAGVAR(archive_expsym_cmds, $1)='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ + $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ + $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ + $ECHO EXPORTS >> $output_objdir/$libname.def~ + prefix_cmds="$SED"~ + if test EXPORTS = "`$SED 1q $export_symbols`"; then + prefix_cmds="$prefix_cmds -e 1d"; + fi~ + prefix_cmds="$prefix_cmds -e \"s/^\(.*\)$/_\1/g\""~ + cat $export_symbols | $prefix_cmds >> $output_objdir/$libname.def~ + $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ + emximp -o $lib $output_objdir/$libname.def' + _LT_TAGVAR(old_archive_From_new_cmds, $1)='emximp -o $output_objdir/${libname}_dll.a $output_objdir/$libname.def' + _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes + _LT_TAGVAR(file_list_spec, $1)='@' + ;; + + dgux*) + case $cc_basename in + ec++*) + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + ghcx*) + # Green Hills C++ Compiler + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + *) + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + esac + ;; + + freebsd2.*) + # C++ shared libraries reported to be fairly broken before + # switch to ELF + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + + freebsd-elf*) + _LT_TAGVAR(archive_cmds_need_lc, $1)=no + ;; + + freebsd* | dragonfly* | midnightbsd*) + # FreeBSD 3 and later use GNU C++ and GNU ld with standard ELF + # conventions + _LT_TAGVAR(ld_shlibs, $1)=yes + ;; + + haiku*) + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + _LT_TAGVAR(link_all_deplibs, $1)=yes + ;; + + hpux9*) + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl+b $wl$libdir' + _LT_TAGVAR(hardcode_libdir_separator, $1)=: + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' + _LT_TAGVAR(hardcode_direct, $1)=yes + _LT_TAGVAR(hardcode_minus_L, $1)=yes # Not in the search PATH, + # but as the default + # location of the library. + + case $cc_basename in + CC*) + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + aCC*) + _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/$soname~$CC -b $wl+b $wl$install_libdir -o $output_objdir/$soname $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~test "x$output_objdir/$soname" = "x$lib" || mv $output_objdir/$soname $lib' + # Commands to make compiler produce verbose output that lists + # what "hidden" libraries, object files and flags are used when + # linking a shared library. + # + # There doesn't appear to be a way to prevent this compiler from + # explicitly linking system object files so we need to strip them + # from the output so that they don't get included in the library + # dependencies. + output_verbose_link_cmd='templist=`($CC -b $CFLAGS -v conftest.$objext 2>&1) | $EGREP "\-L"`; list= ; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "$list"' + ;; + *) + if test yes = "$GXX"; then + _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/$soname~$CC -shared -nostdlib $pic_flag $wl+b $wl$install_libdir -o $output_objdir/$soname $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~test "x$output_objdir/$soname" = "x$lib" || mv $output_objdir/$soname $lib' + else + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + fi + ;; + esac + ;; + + hpux10*|hpux11*) + if test no = "$with_gnu_ld"; then + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl+b $wl$libdir' + _LT_TAGVAR(hardcode_libdir_separator, $1)=: + + case $host_cpu in + hppa*64*|ia64*) + ;; + *) + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' + ;; + esac + fi + case $host_cpu in + hppa*64*|ia64*) + _LT_TAGVAR(hardcode_direct, $1)=no + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + ;; + *) + _LT_TAGVAR(hardcode_direct, $1)=yes + _LT_TAGVAR(hardcode_direct_absolute, $1)=yes + _LT_TAGVAR(hardcode_minus_L, $1)=yes # Not in the search PATH, + # but as the default + # location of the library. + ;; + esac + + case $cc_basename in + CC*) + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + aCC*) + case $host_cpu in + hppa*64*) + _LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' + ;; + ia64*) + _LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname $wl+nodefaultrpath -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' + ;; + *) + _LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' + ;; + esac + # Commands to make compiler produce verbose output that lists + # what "hidden" libraries, object files and flags are used when + # linking a shared library. + # + # There doesn't appear to be a way to prevent this compiler from + # explicitly linking system object files so we need to strip them + # from the output so that they don't get included in the library + # dependencies. + output_verbose_link_cmd='templist=`($CC -b $CFLAGS -v conftest.$objext 2>&1) | $GREP "\-L"`; list= ; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "$list"' + ;; + *) + if test yes = "$GXX"; then + if test no = "$with_gnu_ld"; then + case $host_cpu in + hppa*64*) + _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib -fPIC $wl+h $wl$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' + ;; + ia64*) + _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $pic_flag $wl+h $wl$soname $wl+nodefaultrpath -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' + ;; + *) + _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $pic_flag $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' + ;; + esac + fi + else + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + fi + ;; + esac + ;; + + interix[[3-9]]*) + _LT_TAGVAR(hardcode_direct, $1)=no + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir' + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' + # Hack: On Interix 3.x, we cannot compile PIC because of a broken gcc. + # Instead, shared libraries are loaded at an image base (0x10000000 by + # default) and relocated if they conflict, which is a slow very memory + # consuming and fragmenting process. To avoid this, we pick a random, + # 256 KiB-aligned image base between 0x50000000 and 0x6FFC0000 at link + # time. Moving up from 0x10000000 also allows more sbrk(2) space. + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \* 262144 + 1342177280` -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='$SED "s|^|_|" $export_symbols >$output_objdir/$soname.expsym~$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--retain-symbols-file,$output_objdir/$soname.expsym $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \* 262144 + 1342177280` -o $lib' + ;; + irix5* | irix6*) + case $cc_basename in + CC*) + # SGI C++ + _LT_TAGVAR(archive_cmds, $1)='$CC -shared -all -multigot $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' + + # Archives containing C++ object files must be created using + # "CC -ar", where "CC" is the IRIX C++ compiler. This is + # necessary to make sure instantiated templates are included + # in the archive. + _LT_TAGVAR(old_archive_cmds, $1)='$CC -ar -WR,-u -o $oldlib $oldobjs' + ;; + *) + if test yes = "$GXX"; then + if test no = "$with_gnu_ld"; then + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' + else + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` -o $lib' + fi + fi + _LT_TAGVAR(link_all_deplibs, $1)=yes + ;; + esac + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' + _LT_TAGVAR(hardcode_libdir_separator, $1)=: + _LT_TAGVAR(inherit_rpath, $1)=yes + ;; + + linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) + case $cc_basename in + KCC*) + # Kuck and Associates, Inc. (KAI) C++ Compiler + + # KCC will only create a shared library if the output file + # ends with ".so" (or ".sl" for HP-UX), so rename the library + # to its proper name (with version) after linking. + _LT_TAGVAR(archive_cmds, $1)='tempext=`echo $shared_ext | $SED -e '\''s/\([[^()0-9A-Za-z{}]]\)/\\\\\1/g'\''`; templib=`echo $lib | $SED -e "s/\$tempext\..*/.so/"`; $CC $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags --soname $soname -o \$templib; mv \$templib $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='tempext=`echo $shared_ext | $SED -e '\''s/\([[^()0-9A-Za-z{}]]\)/\\\\\1/g'\''`; templib=`echo $lib | $SED -e "s/\$tempext\..*/.so/"`; $CC $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags --soname $soname -o \$templib $wl-retain-symbols-file,$export_symbols; mv \$templib $lib' + # Commands to make compiler produce verbose output that lists + # what "hidden" libraries, object files and flags are used when + # linking a shared library. + # + # There doesn't appear to be a way to prevent this compiler from + # explicitly linking system object files so we need to strip them + # from the output so that they don't get included in the library + # dependencies. + output_verbose_link_cmd='templist=`$CC $CFLAGS -v conftest.$objext -o libconftest$shared_ext 2>&1 | $GREP "ld"`; rm -f libconftest$shared_ext; list= ; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "$list"' + + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir' + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic' + + # Archives containing C++ object files must be created using + # "CC -Bstatic", where "CC" is the KAI C++ compiler. + _LT_TAGVAR(old_archive_cmds, $1)='$CC -Bstatic -o $oldlib $oldobjs' + ;; + icpc* | ecpc* ) + # Intel C++ + with_gnu_ld=yes + # version 8.0 and above of icpc choke on multiply defined symbols + # if we add $predep_objects and $postdep_objects, however 7.1 and + # earlier do not add the objects themselves. + case `$CC -V 2>&1` in + *"Version 7."*) + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' + ;; + *) # Version 8.0 or newer + tmp_idyn= + case $host_cpu in + ia64*) tmp_idyn=' -i_dynamic';; + esac + _LT_TAGVAR(archive_cmds, $1)='$CC -shared'"$tmp_idyn"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared'"$tmp_idyn"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' + ;; + esac + _LT_TAGVAR(archive_cmds_need_lc, $1)=no + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir' + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic' + _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive$convenience $wl--no-whole-archive' + ;; + pgCC* | pgcpp*) + # Portland Group C++ compiler + case `$CC -V` in + *pgCC\ [[1-5]].* | *pgcpp\ [[1-5]].*) + _LT_TAGVAR(prelink_cmds, $1)='tpldir=Template.dir~ + rm -rf $tpldir~ + $CC --prelink_objects --instantiation_dir $tpldir $objs $libobjs $compile_deplibs~ + compile_command="$compile_command `find $tpldir -name \*.o | sort | $NL2SP`"' + _LT_TAGVAR(old_archive_cmds, $1)='tpldir=Template.dir~ + rm -rf $tpldir~ + $CC --prelink_objects --instantiation_dir $tpldir $oldobjs$old_deplibs~ + $AR $AR_FLAGS $oldlib$oldobjs$old_deplibs `find $tpldir -name \*.o | sort | $NL2SP`~ + $RANLIB $oldlib' + _LT_TAGVAR(archive_cmds, $1)='tpldir=Template.dir~ + rm -rf $tpldir~ + $CC --prelink_objects --instantiation_dir $tpldir $predep_objects $libobjs $deplibs $convenience $postdep_objects~ + $CC -shared $pic_flag $predep_objects $libobjs $deplibs `find $tpldir -name \*.o | sort | $NL2SP` $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='tpldir=Template.dir~ + rm -rf $tpldir~ + $CC --prelink_objects --instantiation_dir $tpldir $predep_objects $libobjs $deplibs $convenience $postdep_objects~ + $CC -shared $pic_flag $predep_objects $libobjs $deplibs `find $tpldir -name \*.o | sort | $NL2SP` $postdep_objects $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' + ;; + *) # Version 6 and above use weak symbols + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' + ;; + esac + + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl--rpath $wl$libdir' + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic' + _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' + ;; + cxx*) + # Compaq C++ + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib $wl-retain-symbols-file $wl$export_symbols' + + runpath_var=LD_RUN_PATH + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-rpath $libdir' + _LT_TAGVAR(hardcode_libdir_separator, $1)=: + + # Commands to make compiler produce verbose output that lists + # what "hidden" libraries, object files and flags are used when + # linking a shared library. + # + # There doesn't appear to be a way to prevent this compiler from + # explicitly linking system object files so we need to strip them + # from the output so that they don't get included in the library + # dependencies. + output_verbose_link_cmd='templist=`$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "ld"`; templist=`func_echo_all "$templist" | $SED "s/\(^.*ld.*\)\( .*ld .*$\)/\1/"`; list= ; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "X$list" | $Xsed' + ;; + xl* | mpixl* | bgxl*) + # IBM XL 8.0 on PPC, with GNU ld + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic' + _LT_TAGVAR(archive_cmds, $1)='$CC -qmkshrobj $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + if test yes = "$supports_anon_versioning"; then + _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $output_objdir/$libname.ver~ + cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $output_objdir/$libname.ver~ + echo "local: *; };" >> $output_objdir/$libname.ver~ + $CC -qmkshrobj $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-version-script $wl$output_objdir/$libname.ver -o $lib' + fi + ;; + *) + case `$CC -V 2>&1 | $SED 5q` in + *Sun\ C*) + # Sun C++ 5.9 + _LT_TAGVAR(no_undefined_flag, $1)=' -zdefs' + _LT_TAGVAR(archive_cmds, $1)='$CC -G$allow_undefined_flag -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -G$allow_undefined_flag -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-retain-symbols-file $wl$export_symbols' + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir' + _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`new_convenience=; for conv in $convenience\"\"; do test -z \"$conv\" || new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' + _LT_TAGVAR(compiler_needs_object, $1)=yes + + # Not sure whether something based on + # $CC $CFLAGS -v conftest.$objext -o libconftest$shared_ext 2>&1 + # would be better. + output_verbose_link_cmd='func_echo_all' + + # Archives containing C++ object files must be created using + # "CC -xar", where "CC" is the Sun C++ compiler. This is + # necessary to make sure instantiated templates are included + # in the archive. + _LT_TAGVAR(old_archive_cmds, $1)='$CC -xar -o $oldlib $oldobjs' + ;; + esac + ;; + esac + ;; + + lynxos*) + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + + m88k*) + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + + mvs*) + case $cc_basename in + cxx*) + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + *) + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + esac + ;; + + netbsd*) + if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then + _LT_TAGVAR(archive_cmds, $1)='$LD -Bshareable -o $lib $predep_objects $libobjs $deplibs $postdep_objects $linker_flags' + wlarc= + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir' + _LT_TAGVAR(hardcode_direct, $1)=yes + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + fi + # Workaround some broken pre-1.5 toolchains + output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP conftest.$objext | $SED -e "s:-lgcc -lc -lgcc::"' + ;; + + *nto* | *qnx*) + _LT_TAGVAR(ld_shlibs, $1)=yes + ;; + + openbsd* | bitrig*) + if test -f /usr/libexec/ld.so; then + _LT_TAGVAR(hardcode_direct, $1)=yes + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + _LT_TAGVAR(hardcode_direct_absolute, $1)=yes + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $lib' + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir' + if test -z "`echo __ELF__ | $CC -E - | grep __ELF__`"; then + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-retain-symbols-file,$export_symbols -o $lib' + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' + _LT_TAGVAR(whole_archive_flag_spec, $1)=$wlarc'--whole-archive$convenience '$wlarc'--no-whole-archive' + fi + output_verbose_link_cmd=func_echo_all + else + _LT_TAGVAR(ld_shlibs, $1)=no + fi + ;; + + osf3* | osf4* | osf5*) + case $cc_basename in + KCC*) + # Kuck and Associates, Inc. (KAI) C++ Compiler + + # KCC will only create a shared library if the output file + # ends with ".so" (or ".sl" for HP-UX), so rename the library + # to its proper name (with version) after linking. + _LT_TAGVAR(archive_cmds, $1)='tempext=`echo $shared_ext | $SED -e '\''s/\([[^()0-9A-Za-z{}]]\)/\\\\\1/g'\''`; templib=`echo "$lib" | $SED -e "s/\$tempext\..*/.so/"`; $CC $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags --soname $soname -o \$templib; mv \$templib $lib' + + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir' + _LT_TAGVAR(hardcode_libdir_separator, $1)=: + + # Archives containing C++ object files must be created using + # the KAI C++ compiler. + case $host in + osf3*) _LT_TAGVAR(old_archive_cmds, $1)='$CC -Bstatic -o $oldlib $oldobjs' ;; + *) _LT_TAGVAR(old_archive_cmds, $1)='$CC -o $oldlib $oldobjs' ;; + esac + ;; + RCC*) + # Rational C++ 2.4.1 + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + cxx*) + case $host in + osf3*) + _LT_TAGVAR(allow_undefined_flag, $1)=' $wl-expect_unresolved $wl\*' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $soname `test -n "$verstring" && func_echo_all "$wl-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' + ;; + *) + _LT_TAGVAR(allow_undefined_flag, $1)=' -expect_unresolved \*' + _LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -msym -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='for i in `cat $export_symbols`; do printf "%s %s\\n" -exported_symbol "\$i" >> $lib.exp; done~ + echo "-hidden">> $lib.exp~ + $CC -shared$allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -msym -soname $soname $wl-input $wl$lib.exp `test -n "$verstring" && $ECHO "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib~ + $RM $lib.exp' + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-rpath $libdir' + ;; + esac + + _LT_TAGVAR(hardcode_libdir_separator, $1)=: + + # Commands to make compiler produce verbose output that lists + # what "hidden" libraries, object files and flags are used when + # linking a shared library. + # + # There doesn't appear to be a way to prevent this compiler from + # explicitly linking system object files so we need to strip them + # from the output so that they don't get included in the library + # dependencies. + output_verbose_link_cmd='templist=`$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "ld" | $GREP -v "ld:"`; templist=`func_echo_all "$templist" | $SED "s/\(^.*ld.*\)\( .*ld.*$\)/\1/"`; list= ; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "$list"' + ;; + *) + if test yes,no = "$GXX,$with_gnu_ld"; then + _LT_TAGVAR(allow_undefined_flag, $1)=' $wl-expect_unresolved $wl\*' + case $host in + osf3*) + _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' + ;; + *) + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -nostdlib $allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-msym $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' + ;; + esac + + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' + _LT_TAGVAR(hardcode_libdir_separator, $1)=: + + # Commands to make compiler produce verbose output that lists + # what "hidden" libraries, object files and flags are used when + # linking a shared library. + output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v "^Configured with:" | $GREP "\-L"' + + else + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + fi + ;; + esac + ;; + + psos*) + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + + sunos4*) + case $cc_basename in + CC*) + # Sun C++ 4.x + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + lcc*) + # Lucid + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + *) + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + esac + ;; + + solaris*) + case $cc_basename in + CC* | sunCC*) + # Sun C++ 4.2, 5.x and Centerline C++ + _LT_TAGVAR(archive_cmds_need_lc,$1)=yes + _LT_TAGVAR(no_undefined_flag, $1)=' -zdefs' + _LT_TAGVAR(archive_cmds, $1)='$CC -G$allow_undefined_flag -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' + _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ + $CC -G$allow_undefined_flag $wl-M $wl$lib.exp -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~$RM $lib.exp' + + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir' + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + case $host_os in + solaris2.[[0-5]] | solaris2.[[0-5]].*) ;; + *) + # The compiler driver will combine and reorder linker options, + # but understands '-z linker_flag'. + # Supported since Solaris 2.6 (maybe 2.5.1?) + _LT_TAGVAR(whole_archive_flag_spec, $1)='-z allextract$convenience -z defaultextract' + ;; + esac + _LT_TAGVAR(link_all_deplibs, $1)=yes + + output_verbose_link_cmd='func_echo_all' + + # Archives containing C++ object files must be created using + # "CC -xar", where "CC" is the Sun C++ compiler. This is + # necessary to make sure instantiated templates are included + # in the archive. + _LT_TAGVAR(old_archive_cmds, $1)='$CC -xar -o $oldlib $oldobjs' + ;; + gcx*) + # Green Hills C++ Compiler + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-h $wl$soname -o $lib' + + # The C++ compiler must be used to create the archive. + _LT_TAGVAR(old_archive_cmds, $1)='$CC $LDFLAGS -archive -o $oldlib $oldobjs' + ;; + *) + # GNU C++ compiler with Solaris linker + if test yes,no = "$GXX,$with_gnu_ld"; then + _LT_TAGVAR(no_undefined_flag, $1)=' $wl-z ${wl}defs' + if $CC --version | $GREP -v '^2\.7' > /dev/null; then + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-h $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ + $CC -shared $pic_flag -nostdlib $wl-M $wl$lib.exp $wl-h $wl$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~$RM $lib.exp' + + # Commands to make compiler produce verbose output that lists + # what "hidden" libraries, object files and flags are used when + # linking a shared library. + output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v "^Configured with:" | $GREP "\-L"' + else + # g++ 2.7 appears to require '-G' NOT '-shared' on this + # platform. + _LT_TAGVAR(archive_cmds, $1)='$CC -G -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-h $wl$soname -o $lib' + _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ + $CC -G -nostdlib $wl-M $wl$lib.exp $wl-h $wl$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~$RM $lib.exp' + + # Commands to make compiler produce verbose output that lists + # what "hidden" libraries, object files and flags are used when + # linking a shared library. + output_verbose_link_cmd='$CC -G $CFLAGS -v conftest.$objext 2>&1 | $GREP -v "^Configured with:" | $GREP "\-L"' + fi + + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-R $wl$libdir' + case $host_os in + solaris2.[[0-5]] | solaris2.[[0-5]].*) ;; + *) + _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl-z ${wl}allextract$convenience $wl-z ${wl}defaultextract' + ;; + esac + fi + ;; + esac + ;; + + sysv4*uw2* | sysv5OpenUNIX* | sysv5UnixWare7.[[01]].[[10]]* | unixware7* | sco3.2v5.0.[[024]]*) + _LT_TAGVAR(no_undefined_flag, $1)='$wl-z,text' + _LT_TAGVAR(archive_cmds_need_lc, $1)=no + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + runpath_var='LD_RUN_PATH' + + case $cc_basename in + CC*) + _LT_TAGVAR(archive_cmds, $1)='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + ;; + *) + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + ;; + esac + ;; + + sysv5* | sco3.2v5* | sco5v6*) + # Note: We CANNOT use -z defs as we might desire, because we do not + # link with -lc, and that would cause any symbols used from libc to + # always be unresolved, which means just about no library would + # ever link correctly. If we're not using GNU ld we use -z text + # though, which does catch some bad symbols but isn't as heavy-handed + # as -z defs. + _LT_TAGVAR(no_undefined_flag, $1)='$wl-z,text' + _LT_TAGVAR(allow_undefined_flag, $1)='$wl-z,nodefs' + _LT_TAGVAR(archive_cmds_need_lc, $1)=no + _LT_TAGVAR(hardcode_shlibpath_var, $1)=no + _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-R,$libdir' + _LT_TAGVAR(hardcode_libdir_separator, $1)=':' + _LT_TAGVAR(link_all_deplibs, $1)=yes + _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-Bexport' + runpath_var='LD_RUN_PATH' + + case $cc_basename in + CC*) + _LT_TAGVAR(archive_cmds, $1)='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(old_archive_cmds, $1)='$CC -Tprelink_objects $oldobjs~ + '"$_LT_TAGVAR(old_archive_cmds, $1)" + _LT_TAGVAR(reload_cmds, $1)='$CC -Tprelink_objects $reload_objs~ + '"$_LT_TAGVAR(reload_cmds, $1)" + ;; + *) + _LT_TAGVAR(archive_cmds, $1)='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + ;; + esac + ;; + + tandem*) + case $cc_basename in + NCC*) + # NonStop-UX NCC 3.20 + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + *) + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + esac + ;; + + vxworks*) + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + + *) + # FIXME: insert proper C++ library support + _LT_TAGVAR(ld_shlibs, $1)=no + ;; + esac + + AC_MSG_RESULT([$_LT_TAGVAR(ld_shlibs, $1)]) + test no = "$_LT_TAGVAR(ld_shlibs, $1)" && can_build_shared=no + + _LT_TAGVAR(GCC, $1)=$GXX + _LT_TAGVAR(LD, $1)=$LD + + ## CAVEAT EMPTOR: + ## There is no encapsulation within the following macros, do not change + ## the running order or otherwise move them around unless you know exactly + ## what you are doing... + _LT_SYS_HIDDEN_LIBDEPS($1) + _LT_COMPILER_PIC($1) + _LT_COMPILER_C_O($1) + _LT_COMPILER_FILE_LOCKS($1) + _LT_LINKER_SHLIBS($1) + _LT_SYS_DYNAMIC_LINKER($1) + _LT_LINKER_HARDCODE_LIBPATH($1) + + _LT_CONFIG($1) + fi # test -n "$compiler" + + CC=$lt_save_CC + CFLAGS=$lt_save_CFLAGS + LDCXX=$LD + LD=$lt_save_LD + GCC=$lt_save_GCC + with_gnu_ld=$lt_save_with_gnu_ld + lt_cv_path_LDCXX=$lt_cv_path_LD + lt_cv_path_LD=$lt_save_path_LD + lt_cv_prog_gnu_ldcxx=$lt_cv_prog_gnu_ld + lt_cv_prog_gnu_ld=$lt_save_with_gnu_ld +fi # test yes != "$_lt_caught_CXX_error" + +AC_LANG_POP +])# _LT_LANG_CXX_CONFIG + + +# _LT_FUNC_STRIPNAME_CNF +# ---------------------- +# func_stripname_cnf prefix suffix name +# strip PREFIX and SUFFIX off of NAME. +# PREFIX and SUFFIX must not contain globbing or regex special +# characters, hashes, percent signs, but SUFFIX may contain a leading +# dot (in which case that matches only a dot). +# +# This function is identical to the (non-XSI) version of func_stripname, +# except this one can be used by m4 code that may be executed by configure, +# rather than the libtool script. +m4_defun([_LT_FUNC_STRIPNAME_CNF],[dnl +AC_REQUIRE([_LT_DECL_SED]) +AC_REQUIRE([_LT_PROG_ECHO_BACKSLASH]) +func_stripname_cnf () +{ + case @S|@2 in + .*) func_stripname_result=`$ECHO "@S|@3" | $SED "s%^@S|@1%%; s%\\\\@S|@2\$%%"`;; + *) func_stripname_result=`$ECHO "@S|@3" | $SED "s%^@S|@1%%; s%@S|@2\$%%"`;; + esac +} # func_stripname_cnf +])# _LT_FUNC_STRIPNAME_CNF + + +# _LT_SYS_HIDDEN_LIBDEPS([TAGNAME]) +# --------------------------------- +# Figure out "hidden" library dependencies from verbose +# compiler output when linking a shared library. +# Parse the compiler output and extract the necessary +# objects, libraries and library flags. +m4_defun([_LT_SYS_HIDDEN_LIBDEPS], +[m4_require([_LT_FILEUTILS_DEFAULTS])dnl +AC_REQUIRE([_LT_FUNC_STRIPNAME_CNF])dnl +# Dependencies to place before and after the object being linked: +_LT_TAGVAR(predep_objects, $1)= +_LT_TAGVAR(postdep_objects, $1)= +_LT_TAGVAR(predeps, $1)= +_LT_TAGVAR(postdeps, $1)= +_LT_TAGVAR(compiler_lib_search_path, $1)= + +dnl we can't use the lt_simple_compile_test_code here, +dnl because it contains code intended for an executable, +dnl not a library. It's possible we should let each +dnl tag define a new lt_????_link_test_code variable, +dnl but it's only used here... +m4_if([$1], [], [cat > conftest.$ac_ext <<_LT_EOF +int a; +void foo (void) { a = 0; } +_LT_EOF +], [$1], [CXX], [cat > conftest.$ac_ext <<_LT_EOF +class Foo +{ +public: + Foo (void) { a = 0; } +private: + int a; +}; +_LT_EOF +], [$1], [F77], [cat > conftest.$ac_ext <<_LT_EOF + subroutine foo + implicit none + integer*4 a + a=0 + return + end +_LT_EOF +], [$1], [FC], [cat > conftest.$ac_ext <<_LT_EOF + subroutine foo + implicit none + integer a + a=0 + return + end +_LT_EOF +], [$1], [GCJ], [cat > conftest.$ac_ext <<_LT_EOF +public class foo { + private int a; + public void bar (void) { + a = 0; + } +}; +_LT_EOF +], [$1], [GO], [cat > conftest.$ac_ext <<_LT_EOF +package foo +func foo() { +} +_LT_EOF +]) + +_lt_libdeps_save_CFLAGS=$CFLAGS +case "$CC $CFLAGS " in #( +*\ -flto*\ *) CFLAGS="$CFLAGS -fno-lto" ;; +*\ -fwhopr*\ *) CFLAGS="$CFLAGS -fno-whopr" ;; +*\ -fuse-linker-plugin*\ *) CFLAGS="$CFLAGS -fno-use-linker-plugin" ;; +esac + +dnl Parse the compiler output and extract the necessary +dnl objects, libraries and library flags. +if AC_TRY_EVAL(ac_compile); then + # Parse the compiler output and extract the necessary + # objects, libraries and library flags. + + # Sentinel used to keep track of whether or not we are before + # the conftest object file. + pre_test_object_deps_done=no + + for p in `eval "$output_verbose_link_cmd"`; do + case $prev$p in + + -L* | -R* | -l*) + # Some compilers place space between "-{L,R}" and the path. + # Remove the space. + if test x-L = "$p" || + test x-R = "$p"; then + prev=$p + continue + fi + + # Expand the sysroot to ease extracting the directories later. + if test -z "$prev"; then + case $p in + -L*) func_stripname_cnf '-L' '' "$p"; prev=-L; p=$func_stripname_result ;; + -R*) func_stripname_cnf '-R' '' "$p"; prev=-R; p=$func_stripname_result ;; + -l*) func_stripname_cnf '-l' '' "$p"; prev=-l; p=$func_stripname_result ;; + esac + fi + case $p in + =*) func_stripname_cnf '=' '' "$p"; p=$lt_sysroot$func_stripname_result ;; + esac + if test no = "$pre_test_object_deps_done"; then + case $prev in + -L | -R) + # Internal compiler library paths should come after those + # provided the user. The postdeps already come after the + # user supplied libs so there is no need to process them. + if test -z "$_LT_TAGVAR(compiler_lib_search_path, $1)"; then + _LT_TAGVAR(compiler_lib_search_path, $1)=$prev$p + else + _LT_TAGVAR(compiler_lib_search_path, $1)="${_LT_TAGVAR(compiler_lib_search_path, $1)} $prev$p" + fi + ;; + # The "-l" case would never come before the object being + # linked, so don't bother handling this case. + esac + else + if test -z "$_LT_TAGVAR(postdeps, $1)"; then + _LT_TAGVAR(postdeps, $1)=$prev$p + else + _LT_TAGVAR(postdeps, $1)="${_LT_TAGVAR(postdeps, $1)} $prev$p" + fi + fi + prev= + ;; + + *.lto.$objext) ;; # Ignore GCC LTO objects + *.$objext) + # This assumes that the test object file only shows up + # once in the compiler output. + if test "$p" = "conftest.$objext"; then + pre_test_object_deps_done=yes + continue + fi + + if test no = "$pre_test_object_deps_done"; then + if test -z "$_LT_TAGVAR(predep_objects, $1)"; then + _LT_TAGVAR(predep_objects, $1)=$p + else + _LT_TAGVAR(predep_objects, $1)="$_LT_TAGVAR(predep_objects, $1) $p" + fi + else + if test -z "$_LT_TAGVAR(postdep_objects, $1)"; then + _LT_TAGVAR(postdep_objects, $1)=$p + else + _LT_TAGVAR(postdep_objects, $1)="$_LT_TAGVAR(postdep_objects, $1) $p" + fi + fi + ;; + + *) ;; # Ignore the rest. + + esac + done + + # Clean up. + rm -f a.out a.exe +else + echo "libtool.m4: error: problem compiling $1 test program" +fi + +$RM -f confest.$objext +CFLAGS=$_lt_libdeps_save_CFLAGS + +# PORTME: override above test on systems where it is broken +m4_if([$1], [CXX], +[case $host_os in +interix[[3-9]]*) + # Interix 3.5 installs completely hosed .la files for C++, so rather than + # hack all around it, let's just trust "g++" to DTRT. + _LT_TAGVAR(predep_objects,$1)= + _LT_TAGVAR(postdep_objects,$1)= + _LT_TAGVAR(postdeps,$1)= + ;; +esac +]) + +case " $_LT_TAGVAR(postdeps, $1) " in +*" -lc "*) _LT_TAGVAR(archive_cmds_need_lc, $1)=no ;; +esac + _LT_TAGVAR(compiler_lib_search_dirs, $1)= +if test -n "${_LT_TAGVAR(compiler_lib_search_path, $1)}"; then + _LT_TAGVAR(compiler_lib_search_dirs, $1)=`echo " ${_LT_TAGVAR(compiler_lib_search_path, $1)}" | $SED -e 's! -L! !g' -e 's!^ !!'` +fi +_LT_TAGDECL([], [compiler_lib_search_dirs], [1], + [The directories searched by this compiler when creating a shared library]) +_LT_TAGDECL([], [predep_objects], [1], + [Dependencies to place before and after the objects being linked to + create a shared library]) +_LT_TAGDECL([], [postdep_objects], [1]) +_LT_TAGDECL([], [predeps], [1]) +_LT_TAGDECL([], [postdeps], [1]) +_LT_TAGDECL([], [compiler_lib_search_path], [1], + [The library search path used internally by the compiler when linking + a shared library]) +])# _LT_SYS_HIDDEN_LIBDEPS + + +# _LT_LANG_F77_CONFIG([TAG]) +# -------------------------- +# Ensure that the configuration variables for a Fortran 77 compiler are +# suitably defined. These variables are subsequently used by _LT_CONFIG +# to write the compiler configuration to 'libtool'. +m4_defun([_LT_LANG_F77_CONFIG], +[AC_LANG_PUSH(Fortran 77) +if test -z "$F77" || test no = "$F77"; then + _lt_disable_F77=yes +fi + +_LT_TAGVAR(archive_cmds_need_lc, $1)=no +_LT_TAGVAR(allow_undefined_flag, $1)= +_LT_TAGVAR(always_export_symbols, $1)=no +_LT_TAGVAR(archive_expsym_cmds, $1)= +_LT_TAGVAR(export_dynamic_flag_spec, $1)= +_LT_TAGVAR(hardcode_direct, $1)=no +_LT_TAGVAR(hardcode_direct_absolute, $1)=no +_LT_TAGVAR(hardcode_libdir_flag_spec, $1)= +_LT_TAGVAR(hardcode_libdir_separator, $1)= +_LT_TAGVAR(hardcode_minus_L, $1)=no +_LT_TAGVAR(hardcode_automatic, $1)=no +_LT_TAGVAR(inherit_rpath, $1)=no +_LT_TAGVAR(module_cmds, $1)= +_LT_TAGVAR(module_expsym_cmds, $1)= +_LT_TAGVAR(link_all_deplibs, $1)=unknown +_LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds +_LT_TAGVAR(reload_flag, $1)=$reload_flag +_LT_TAGVAR(reload_cmds, $1)=$reload_cmds +_LT_TAGVAR(no_undefined_flag, $1)= +_LT_TAGVAR(whole_archive_flag_spec, $1)= +_LT_TAGVAR(enable_shared_with_static_runtimes, $1)=no + +# Source file extension for f77 test sources. +ac_ext=f + +# Object file extension for compiled f77 test sources. +objext=o +_LT_TAGVAR(objext, $1)=$objext + +# No sense in running all these tests if we already determined that +# the F77 compiler isn't working. Some variables (like enable_shared) +# are currently assumed to apply to all compilers on this platform, +# and will be corrupted by setting them based on a non-working compiler. +if test yes != "$_lt_disable_F77"; then + # Code to be used in simple compile tests + lt_simple_compile_test_code="\ + subroutine t + return + end +" + + # Code to be used in simple link tests + lt_simple_link_test_code="\ + program t + end +" + + # ltmain only uses $CC for tagged configurations so make sure $CC is set. + _LT_TAG_COMPILER + + # save warnings/boilerplate of simple test code + _LT_COMPILER_BOILERPLATE + _LT_LINKER_BOILERPLATE + + # Allow CC to be a program name with arguments. + lt_save_CC=$CC + lt_save_GCC=$GCC + lt_save_CFLAGS=$CFLAGS + CC=${F77-"f77"} + CFLAGS=$FFLAGS + compiler=$CC + _LT_TAGVAR(compiler, $1)=$CC + _LT_CC_BASENAME([$compiler]) + GCC=$G77 + if test -n "$compiler"; then + AC_MSG_CHECKING([if libtool supports shared libraries]) + AC_MSG_RESULT([$can_build_shared]) + + AC_MSG_CHECKING([whether to build shared libraries]) + test no = "$can_build_shared" && enable_shared=no + + # On AIX, shared libraries and static libraries use the same namespace, and + # are all built from PIC. + case $host_os in + aix3*) + test yes = "$enable_shared" && enable_static=no + if test -n "$RANLIB"; then + archive_cmds="$archive_cmds~\$RANLIB \$lib" + postinstall_cmds='$RANLIB $lib' + fi + ;; + aix[[4-9]]*) + if test ia64 != "$host_cpu"; then + case $enable_shared,$with_aix_soname,$aix_use_runtimelinking in + yes,aix,yes) ;; # shared object as lib.so file only + yes,svr4,*) ;; # shared object as lib.so archive member only + yes,*) enable_static=no ;; # shared object in lib.a archive as well + esac + fi + ;; + esac + AC_MSG_RESULT([$enable_shared]) + + AC_MSG_CHECKING([whether to build static libraries]) + # Make sure either enable_shared or enable_static is yes. + test yes = "$enable_shared" || enable_static=yes + AC_MSG_RESULT([$enable_static]) + + _LT_TAGVAR(GCC, $1)=$G77 + _LT_TAGVAR(LD, $1)=$LD + + ## CAVEAT EMPTOR: + ## There is no encapsulation within the following macros, do not change + ## the running order or otherwise move them around unless you know exactly + ## what you are doing... + _LT_COMPILER_PIC($1) + _LT_COMPILER_C_O($1) + _LT_COMPILER_FILE_LOCKS($1) + _LT_LINKER_SHLIBS($1) + _LT_SYS_DYNAMIC_LINKER($1) + _LT_LINKER_HARDCODE_LIBPATH($1) + + _LT_CONFIG($1) + fi # test -n "$compiler" + + GCC=$lt_save_GCC + CC=$lt_save_CC + CFLAGS=$lt_save_CFLAGS +fi # test yes != "$_lt_disable_F77" + +AC_LANG_POP +])# _LT_LANG_F77_CONFIG + + +# _LT_LANG_FC_CONFIG([TAG]) +# ------------------------- +# Ensure that the configuration variables for a Fortran compiler are +# suitably defined. These variables are subsequently used by _LT_CONFIG +# to write the compiler configuration to 'libtool'. +m4_defun([_LT_LANG_FC_CONFIG], +[AC_LANG_PUSH(Fortran) + +if test -z "$FC" || test no = "$FC"; then + _lt_disable_FC=yes +fi + +_LT_TAGVAR(archive_cmds_need_lc, $1)=no +_LT_TAGVAR(allow_undefined_flag, $1)= +_LT_TAGVAR(always_export_symbols, $1)=no +_LT_TAGVAR(archive_expsym_cmds, $1)= +_LT_TAGVAR(export_dynamic_flag_spec, $1)= +_LT_TAGVAR(hardcode_direct, $1)=no +_LT_TAGVAR(hardcode_direct_absolute, $1)=no +_LT_TAGVAR(hardcode_libdir_flag_spec, $1)= +_LT_TAGVAR(hardcode_libdir_separator, $1)= +_LT_TAGVAR(hardcode_minus_L, $1)=no +_LT_TAGVAR(hardcode_automatic, $1)=no +_LT_TAGVAR(inherit_rpath, $1)=no +_LT_TAGVAR(module_cmds, $1)= +_LT_TAGVAR(module_expsym_cmds, $1)= +_LT_TAGVAR(link_all_deplibs, $1)=unknown +_LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds +_LT_TAGVAR(reload_flag, $1)=$reload_flag +_LT_TAGVAR(reload_cmds, $1)=$reload_cmds +_LT_TAGVAR(no_undefined_flag, $1)= +_LT_TAGVAR(whole_archive_flag_spec, $1)= +_LT_TAGVAR(enable_shared_with_static_runtimes, $1)=no + +# Source file extension for fc test sources. +ac_ext=${ac_fc_srcext-f} + +# Object file extension for compiled fc test sources. +objext=o +_LT_TAGVAR(objext, $1)=$objext + +# No sense in running all these tests if we already determined that +# the FC compiler isn't working. Some variables (like enable_shared) +# are currently assumed to apply to all compilers on this platform, +# and will be corrupted by setting them based on a non-working compiler. +if test yes != "$_lt_disable_FC"; then + # Code to be used in simple compile tests + lt_simple_compile_test_code="\ + subroutine t + return + end +" + + # Code to be used in simple link tests + lt_simple_link_test_code="\ + program t + end +" + + # ltmain only uses $CC for tagged configurations so make sure $CC is set. + _LT_TAG_COMPILER + + # save warnings/boilerplate of simple test code + _LT_COMPILER_BOILERPLATE + _LT_LINKER_BOILERPLATE + + # Allow CC to be a program name with arguments. + lt_save_CC=$CC + lt_save_GCC=$GCC + lt_save_CFLAGS=$CFLAGS + CC=${FC-"f95"} + CFLAGS=$FCFLAGS + compiler=$CC + GCC=$ac_cv_fc_compiler_gnu + + _LT_TAGVAR(compiler, $1)=$CC + _LT_CC_BASENAME([$compiler]) + + if test -n "$compiler"; then + AC_MSG_CHECKING([if libtool supports shared libraries]) + AC_MSG_RESULT([$can_build_shared]) + + AC_MSG_CHECKING([whether to build shared libraries]) + test no = "$can_build_shared" && enable_shared=no + + # On AIX, shared libraries and static libraries use the same namespace, and + # are all built from PIC. + case $host_os in + aix3*) + test yes = "$enable_shared" && enable_static=no + if test -n "$RANLIB"; then + archive_cmds="$archive_cmds~\$RANLIB \$lib" + postinstall_cmds='$RANLIB $lib' + fi + ;; + aix[[4-9]]*) + if test ia64 != "$host_cpu"; then + case $enable_shared,$with_aix_soname,$aix_use_runtimelinking in + yes,aix,yes) ;; # shared object as lib.so file only + yes,svr4,*) ;; # shared object as lib.so archive member only + yes,*) enable_static=no ;; # shared object in lib.a archive as well + esac + fi + ;; + esac + AC_MSG_RESULT([$enable_shared]) + + AC_MSG_CHECKING([whether to build static libraries]) + # Make sure either enable_shared or enable_static is yes. + test yes = "$enable_shared" || enable_static=yes + AC_MSG_RESULT([$enable_static]) + + _LT_TAGVAR(GCC, $1)=$ac_cv_fc_compiler_gnu + _LT_TAGVAR(LD, $1)=$LD + + ## CAVEAT EMPTOR: + ## There is no encapsulation within the following macros, do not change + ## the running order or otherwise move them around unless you know exactly + ## what you are doing... + _LT_SYS_HIDDEN_LIBDEPS($1) + _LT_COMPILER_PIC($1) + _LT_COMPILER_C_O($1) + _LT_COMPILER_FILE_LOCKS($1) + _LT_LINKER_SHLIBS($1) + _LT_SYS_DYNAMIC_LINKER($1) + _LT_LINKER_HARDCODE_LIBPATH($1) + + _LT_CONFIG($1) + fi # test -n "$compiler" + + GCC=$lt_save_GCC + CC=$lt_save_CC + CFLAGS=$lt_save_CFLAGS +fi # test yes != "$_lt_disable_FC" + +AC_LANG_POP +])# _LT_LANG_FC_CONFIG + + +# _LT_LANG_GCJ_CONFIG([TAG]) +# -------------------------- +# Ensure that the configuration variables for the GNU Java Compiler compiler +# are suitably defined. These variables are subsequently used by _LT_CONFIG +# to write the compiler configuration to 'libtool'. +m4_defun([_LT_LANG_GCJ_CONFIG], +[AC_REQUIRE([LT_PROG_GCJ])dnl +AC_LANG_SAVE + +# Source file extension for Java test sources. +ac_ext=java + +# Object file extension for compiled Java test sources. +objext=o +_LT_TAGVAR(objext, $1)=$objext + +# Code to be used in simple compile tests +lt_simple_compile_test_code="class foo {}" + +# Code to be used in simple link tests +lt_simple_link_test_code='public class conftest { public static void main(String[[]] argv) {}; }' + +# ltmain only uses $CC for tagged configurations so make sure $CC is set. +_LT_TAG_COMPILER + +# save warnings/boilerplate of simple test code +_LT_COMPILER_BOILERPLATE +_LT_LINKER_BOILERPLATE + +# Allow CC to be a program name with arguments. +lt_save_CC=$CC +lt_save_CFLAGS=$CFLAGS +lt_save_GCC=$GCC +GCC=yes +CC=${GCJ-"gcj"} +CFLAGS=$GCJFLAGS +compiler=$CC +_LT_TAGVAR(compiler, $1)=$CC +_LT_TAGVAR(LD, $1)=$LD +_LT_CC_BASENAME([$compiler]) + +# GCJ did not exist at the time GCC didn't implicitly link libc in. +_LT_TAGVAR(archive_cmds_need_lc, $1)=no + +_LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds +_LT_TAGVAR(reload_flag, $1)=$reload_flag +_LT_TAGVAR(reload_cmds, $1)=$reload_cmds + +if test -n "$compiler"; then + _LT_COMPILER_NO_RTTI($1) + _LT_COMPILER_PIC($1) + _LT_COMPILER_C_O($1) + _LT_COMPILER_FILE_LOCKS($1) + _LT_LINKER_SHLIBS($1) + _LT_LINKER_HARDCODE_LIBPATH($1) + + _LT_CONFIG($1) +fi + +AC_LANG_RESTORE + +GCC=$lt_save_GCC +CC=$lt_save_CC +CFLAGS=$lt_save_CFLAGS +])# _LT_LANG_GCJ_CONFIG + + +# _LT_LANG_GO_CONFIG([TAG]) +# -------------------------- +# Ensure that the configuration variables for the GNU Go compiler +# are suitably defined. These variables are subsequently used by _LT_CONFIG +# to write the compiler configuration to 'libtool'. +m4_defun([_LT_LANG_GO_CONFIG], +[AC_REQUIRE([LT_PROG_GO])dnl +AC_LANG_SAVE + +# Source file extension for Go test sources. +ac_ext=go + +# Object file extension for compiled Go test sources. +objext=o +_LT_TAGVAR(objext, $1)=$objext + +# Code to be used in simple compile tests +lt_simple_compile_test_code="package main; func main() { }" + +# Code to be used in simple link tests +lt_simple_link_test_code='package main; func main() { }' + +# ltmain only uses $CC for tagged configurations so make sure $CC is set. +_LT_TAG_COMPILER + +# save warnings/boilerplate of simple test code +_LT_COMPILER_BOILERPLATE +_LT_LINKER_BOILERPLATE + +# Allow CC to be a program name with arguments. +lt_save_CC=$CC +lt_save_CFLAGS=$CFLAGS +lt_save_GCC=$GCC +GCC=yes +CC=${GOC-"gccgo"} +CFLAGS=$GOFLAGS +compiler=$CC +_LT_TAGVAR(compiler, $1)=$CC +_LT_TAGVAR(LD, $1)=$LD +_LT_CC_BASENAME([$compiler]) + +# Go did not exist at the time GCC didn't implicitly link libc in. +_LT_TAGVAR(archive_cmds_need_lc, $1)=no + +_LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds +_LT_TAGVAR(reload_flag, $1)=$reload_flag +_LT_TAGVAR(reload_cmds, $1)=$reload_cmds + +if test -n "$compiler"; then + _LT_COMPILER_NO_RTTI($1) + _LT_COMPILER_PIC($1) + _LT_COMPILER_C_O($1) + _LT_COMPILER_FILE_LOCKS($1) + _LT_LINKER_SHLIBS($1) + _LT_LINKER_HARDCODE_LIBPATH($1) + + _LT_CONFIG($1) +fi + +AC_LANG_RESTORE + +GCC=$lt_save_GCC +CC=$lt_save_CC +CFLAGS=$lt_save_CFLAGS +])# _LT_LANG_GO_CONFIG + + +# _LT_LANG_RC_CONFIG([TAG]) +# ------------------------- +# Ensure that the configuration variables for the Windows resource compiler +# are suitably defined. These variables are subsequently used by _LT_CONFIG +# to write the compiler configuration to 'libtool'. +m4_defun([_LT_LANG_RC_CONFIG], +[AC_REQUIRE([LT_PROG_RC])dnl +AC_LANG_SAVE + +# Source file extension for RC test sources. +ac_ext=rc + +# Object file extension for compiled RC test sources. +objext=o +_LT_TAGVAR(objext, $1)=$objext + +# Code to be used in simple compile tests +lt_simple_compile_test_code='sample MENU { MENUITEM "&Soup", 100, CHECKED }' + +# Code to be used in simple link tests +lt_simple_link_test_code=$lt_simple_compile_test_code + +# ltmain only uses $CC for tagged configurations so make sure $CC is set. +_LT_TAG_COMPILER + +# save warnings/boilerplate of simple test code +_LT_COMPILER_BOILERPLATE +_LT_LINKER_BOILERPLATE + +# Allow CC to be a program name with arguments. +lt_save_CC=$CC +lt_save_CFLAGS=$CFLAGS +lt_save_GCC=$GCC +GCC= +CC=${RC-"windres"} +CFLAGS= +compiler=$CC +_LT_TAGVAR(compiler, $1)=$CC +_LT_CC_BASENAME([$compiler]) +_LT_TAGVAR(lt_cv_prog_compiler_c_o, $1)=yes + +if test -n "$compiler"; then + : + _LT_CONFIG($1) +fi + +GCC=$lt_save_GCC +AC_LANG_RESTORE +CC=$lt_save_CC +CFLAGS=$lt_save_CFLAGS +])# _LT_LANG_RC_CONFIG + + +# LT_PROG_GCJ +# ----------- +AC_DEFUN([LT_PROG_GCJ], +[m4_ifdef([AC_PROG_GCJ], [AC_PROG_GCJ], + [m4_ifdef([A][M_PROG_GCJ], [A][M_PROG_GCJ], + [AC_CHECK_TOOL(GCJ, gcj,) + test set = "${GCJFLAGS+set}" || GCJFLAGS="-g -O2" + AC_SUBST(GCJFLAGS)])])[]dnl +]) + +# Old name: +AU_ALIAS([LT_AC_PROG_GCJ], [LT_PROG_GCJ]) +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([LT_AC_PROG_GCJ], []) + + +# LT_PROG_GO +# ---------- +AC_DEFUN([LT_PROG_GO], +[AC_CHECK_TOOL(GOC, gccgo,) +]) + + +# LT_PROG_RC +# ---------- +AC_DEFUN([LT_PROG_RC], +[AC_CHECK_TOOL(RC, windres,) +]) + +# Old name: +AU_ALIAS([LT_AC_PROG_RC], [LT_PROG_RC]) +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([LT_AC_PROG_RC], []) + + +# _LT_DECL_EGREP +# -------------- +# If we don't have a new enough Autoconf to choose the best grep +# available, choose the one first in the user's PATH. +m4_defun([_LT_DECL_EGREP], +[AC_REQUIRE([AC_PROG_EGREP])dnl +AC_REQUIRE([AC_PROG_FGREP])dnl +test -z "$GREP" && GREP=grep +_LT_DECL([], [GREP], [1], [A grep program that handles long lines]) +_LT_DECL([], [EGREP], [1], [An ERE matcher]) +_LT_DECL([], [FGREP], [1], [A literal string matcher]) +dnl Non-bleeding-edge autoconf doesn't subst GREP, so do it here too +AC_SUBST([GREP]) +]) + + +# _LT_DECL_OBJDUMP +# -------------- +# If we don't have a new enough Autoconf to choose the best objdump +# available, choose the one first in the user's PATH. +m4_defun([_LT_DECL_OBJDUMP], +[AC_CHECK_TOOL(OBJDUMP, objdump, false) +test -z "$OBJDUMP" && OBJDUMP=objdump +_LT_DECL([], [OBJDUMP], [1], [An object symbol dumper]) +AC_SUBST([OBJDUMP]) +]) + +# _LT_DECL_DLLTOOL +# ---------------- +# Ensure DLLTOOL variable is set. +m4_defun([_LT_DECL_DLLTOOL], +[AC_CHECK_TOOL(DLLTOOL, dlltool, false) +test -z "$DLLTOOL" && DLLTOOL=dlltool +_LT_DECL([], [DLLTOOL], [1], [DLL creation program]) +AC_SUBST([DLLTOOL]) +]) + +# _LT_DECL_FILECMD +# ---------------- +# Check for a file(cmd) program that can be used to detect file type and magic +m4_defun([_LT_DECL_FILECMD], +[AC_CHECK_TOOL([FILECMD], [file], [:]) +_LT_DECL([], [FILECMD], [1], [A file(cmd) program that detects file types]) +])# _LD_DECL_FILECMD + +# _LT_DECL_SED +# ------------ +# Check for a fully-functional sed program, that truncates +# as few characters as possible. Prefer GNU sed if found. +m4_defun([_LT_DECL_SED], +[AC_PROG_SED +test -z "$SED" && SED=sed +Xsed="$SED -e 1s/^X//" +_LT_DECL([], [SED], [1], [A sed program that does not truncate output]) +_LT_DECL([], [Xsed], ["\$SED -e 1s/^X//"], + [Sed that helps us avoid accidentally triggering echo(1) options like -n]) +])# _LT_DECL_SED + +m4_ifndef([AC_PROG_SED], [ +# NOTE: This macro has been submitted for inclusion into # +# GNU Autoconf as AC_PROG_SED. When it is available in # +# a released version of Autoconf we should remove this # +# macro and use it instead. # + +m4_defun([AC_PROG_SED], +[AC_MSG_CHECKING([for a sed that does not truncate output]) +AC_CACHE_VAL(lt_cv_path_SED, +[# Loop through the user's path and test for sed and gsed. +# Then use that list of sed's as ones to test for truncation. +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for lt_ac_prog in sed gsed; do + for ac_exec_ext in '' $ac_executable_extensions; do + if $as_executable_p "$as_dir/$lt_ac_prog$ac_exec_ext"; then + lt_ac_sed_list="$lt_ac_sed_list $as_dir/$lt_ac_prog$ac_exec_ext" + fi + done + done +done +IFS=$as_save_IFS +lt_ac_max=0 +lt_ac_count=0 +# Add /usr/xpg4/bin/sed as it is typically found on Solaris +# along with /bin/sed that truncates output. +for lt_ac_sed in $lt_ac_sed_list /usr/xpg4/bin/sed; do + test ! -f "$lt_ac_sed" && continue + cat /dev/null > conftest.in + lt_ac_count=0 + echo $ECHO_N "0123456789$ECHO_C" >conftest.in + # Check for GNU sed and select it if it is found. + if "$lt_ac_sed" --version 2>&1 < /dev/null | grep 'GNU' > /dev/null; then + lt_cv_path_SED=$lt_ac_sed + break + fi + while true; do + cat conftest.in conftest.in >conftest.tmp + mv conftest.tmp conftest.in + cp conftest.in conftest.nl + echo >>conftest.nl + $lt_ac_sed -e 's/a$//' < conftest.nl >conftest.out || break + cmp -s conftest.out conftest.nl || break + # 10000 chars as input seems more than enough + test 10 -lt "$lt_ac_count" && break + lt_ac_count=`expr $lt_ac_count + 1` + if test "$lt_ac_count" -gt "$lt_ac_max"; then + lt_ac_max=$lt_ac_count + lt_cv_path_SED=$lt_ac_sed + fi + done +done +]) +SED=$lt_cv_path_SED +AC_SUBST([SED]) +AC_MSG_RESULT([$SED]) +])#AC_PROG_SED +])#m4_ifndef + +# Old name: +AU_ALIAS([LT_AC_PROG_SED], [AC_PROG_SED]) +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([LT_AC_PROG_SED], []) + + +# _LT_CHECK_SHELL_FEATURES +# ------------------------ +# Find out whether the shell is Bourne or XSI compatible, +# or has some other useful features. +m4_defun([_LT_CHECK_SHELL_FEATURES], +[if ( (MAIL=60; unset MAIL) || exit) >/dev/null 2>&1; then + lt_unset=unset +else + lt_unset=false +fi +_LT_DECL([], [lt_unset], [0], [whether the shell understands "unset"])dnl + +# test EBCDIC or ASCII +case `echo X|tr X '\101'` in + A) # ASCII based system + # \n is not interpreted correctly by Solaris 8 /usr/ucb/tr + lt_SP2NL='tr \040 \012' + lt_NL2SP='tr \015\012 \040\040' + ;; + *) # EBCDIC based system + lt_SP2NL='tr \100 \n' + lt_NL2SP='tr \r\n \100\100' + ;; +esac +_LT_DECL([SP2NL], [lt_SP2NL], [1], [turn spaces into newlines])dnl +_LT_DECL([NL2SP], [lt_NL2SP], [1], [turn newlines into spaces])dnl +])# _LT_CHECK_SHELL_FEATURES + + +# _LT_PATH_CONVERSION_FUNCTIONS +# ----------------------------- +# Determine what file name conversion functions should be used by +# func_to_host_file (and, implicitly, by func_to_host_path). These are needed +# for certain cross-compile configurations and native mingw. +m4_defun([_LT_PATH_CONVERSION_FUNCTIONS], +[AC_REQUIRE([AC_CANONICAL_HOST])dnl +AC_REQUIRE([AC_CANONICAL_BUILD])dnl +AC_MSG_CHECKING([how to convert $build file names to $host format]) +AC_CACHE_VAL(lt_cv_to_host_file_cmd, +[case $host in + *-*-mingw* ) + case $build in + *-*-mingw* ) # actually msys + lt_cv_to_host_file_cmd=func_convert_file_msys_to_w32 + ;; + *-*-cygwin* ) + lt_cv_to_host_file_cmd=func_convert_file_cygwin_to_w32 + ;; + * ) # otherwise, assume *nix + lt_cv_to_host_file_cmd=func_convert_file_nix_to_w32 + ;; + esac + ;; + *-*-cygwin* ) + case $build in + *-*-mingw* ) # actually msys + lt_cv_to_host_file_cmd=func_convert_file_msys_to_cygwin + ;; + *-*-cygwin* ) + lt_cv_to_host_file_cmd=func_convert_file_noop + ;; + * ) # otherwise, assume *nix + lt_cv_to_host_file_cmd=func_convert_file_nix_to_cygwin + ;; + esac + ;; + * ) # unhandled hosts (and "normal" native builds) + lt_cv_to_host_file_cmd=func_convert_file_noop + ;; +esac +]) +to_host_file_cmd=$lt_cv_to_host_file_cmd +AC_MSG_RESULT([$lt_cv_to_host_file_cmd]) +_LT_DECL([to_host_file_cmd], [lt_cv_to_host_file_cmd], + [0], [convert $build file names to $host format])dnl + +AC_MSG_CHECKING([how to convert $build file names to toolchain format]) +AC_CACHE_VAL(lt_cv_to_tool_file_cmd, +[#assume ordinary cross tools, or native build. +lt_cv_to_tool_file_cmd=func_convert_file_noop +case $host in + *-*-mingw* ) + case $build in + *-*-mingw* ) # actually msys + lt_cv_to_tool_file_cmd=func_convert_file_msys_to_w32 + ;; + esac + ;; +esac +]) +to_tool_file_cmd=$lt_cv_to_tool_file_cmd +AC_MSG_RESULT([$lt_cv_to_tool_file_cmd]) +_LT_DECL([to_tool_file_cmd], [lt_cv_to_tool_file_cmd], + [0], [convert $build files to toolchain format])dnl +])# _LT_PATH_CONVERSION_FUNCTIONS + +# Helper functions for option handling. -*- Autoconf -*- +# +# Copyright (C) 2004-2005, 2007-2009, 2011-2019, 2021-2022 Free +# Software Foundation, Inc. +# Written by Gary V. Vaughan, 2004 +# +# This file is free software; the Free Software Foundation gives +# unlimited permission to copy and/or distribute it, with or without +# modifications, as long as this notice is preserved. + +# serial 8 ltoptions.m4 + +# This is to help aclocal find these macros, as it can't see m4_define. +AC_DEFUN([LTOPTIONS_VERSION], [m4_if([1])]) + + +# _LT_MANGLE_OPTION(MACRO-NAME, OPTION-NAME) +# ------------------------------------------ +m4_define([_LT_MANGLE_OPTION], +[[_LT_OPTION_]m4_bpatsubst($1__$2, [[^a-zA-Z0-9_]], [_])]) + + +# _LT_SET_OPTION(MACRO-NAME, OPTION-NAME) +# --------------------------------------- +# Set option OPTION-NAME for macro MACRO-NAME, and if there is a +# matching handler defined, dispatch to it. Other OPTION-NAMEs are +# saved as a flag. +m4_define([_LT_SET_OPTION], +[m4_define(_LT_MANGLE_OPTION([$1], [$2]))dnl +m4_ifdef(_LT_MANGLE_DEFUN([$1], [$2]), + _LT_MANGLE_DEFUN([$1], [$2]), + [m4_warning([Unknown $1 option '$2'])])[]dnl +]) + + +# _LT_IF_OPTION(MACRO-NAME, OPTION-NAME, IF-SET, [IF-NOT-SET]) +# ------------------------------------------------------------ +# Execute IF-SET if OPTION is set, IF-NOT-SET otherwise. +m4_define([_LT_IF_OPTION], +[m4_ifdef(_LT_MANGLE_OPTION([$1], [$2]), [$3], [$4])]) + + +# _LT_UNLESS_OPTIONS(MACRO-NAME, OPTION-LIST, IF-NOT-SET) +# ------------------------------------------------------- +# Execute IF-NOT-SET unless all options in OPTION-LIST for MACRO-NAME +# are set. +m4_define([_LT_UNLESS_OPTIONS], +[m4_foreach([_LT_Option], m4_split(m4_normalize([$2])), + [m4_ifdef(_LT_MANGLE_OPTION([$1], _LT_Option), + [m4_define([$0_found])])])[]dnl +m4_ifdef([$0_found], [m4_undefine([$0_found])], [$3 +])[]dnl +]) + + +# _LT_SET_OPTIONS(MACRO-NAME, OPTION-LIST) +# ---------------------------------------- +# OPTION-LIST is a space-separated list of Libtool options associated +# with MACRO-NAME. If any OPTION has a matching handler declared with +# LT_OPTION_DEFINE, dispatch to that macro; otherwise complain about +# the unknown option and exit. +m4_defun([_LT_SET_OPTIONS], +[# Set options +m4_foreach([_LT_Option], m4_split(m4_normalize([$2])), + [_LT_SET_OPTION([$1], _LT_Option)]) + +m4_if([$1],[LT_INIT],[ + dnl + dnl Simply set some default values (i.e off) if boolean options were not + dnl specified: + _LT_UNLESS_OPTIONS([LT_INIT], [dlopen], [enable_dlopen=no + ]) + _LT_UNLESS_OPTIONS([LT_INIT], [win32-dll], [enable_win32_dll=no + ]) + dnl + dnl If no reference was made to various pairs of opposing options, then + dnl we run the default mode handler for the pair. For example, if neither + dnl 'shared' nor 'disable-shared' was passed, we enable building of shared + dnl archives by default: + _LT_UNLESS_OPTIONS([LT_INIT], [shared disable-shared], [_LT_ENABLE_SHARED]) + _LT_UNLESS_OPTIONS([LT_INIT], [static disable-static], [_LT_ENABLE_STATIC]) + _LT_UNLESS_OPTIONS([LT_INIT], [pic-only no-pic], [_LT_WITH_PIC]) + _LT_UNLESS_OPTIONS([LT_INIT], [fast-install disable-fast-install], + [_LT_ENABLE_FAST_INSTALL]) + _LT_UNLESS_OPTIONS([LT_INIT], [aix-soname=aix aix-soname=both aix-soname=svr4], + [_LT_WITH_AIX_SONAME([aix])]) + ]) +])# _LT_SET_OPTIONS + + + +# _LT_MANGLE_DEFUN(MACRO-NAME, OPTION-NAME) +# ----------------------------------------- +m4_define([_LT_MANGLE_DEFUN], +[[_LT_OPTION_DEFUN_]m4_bpatsubst(m4_toupper([$1__$2]), [[^A-Z0-9_]], [_])]) + + +# LT_OPTION_DEFINE(MACRO-NAME, OPTION-NAME, CODE) +# ----------------------------------------------- +m4_define([LT_OPTION_DEFINE], +[m4_define(_LT_MANGLE_DEFUN([$1], [$2]), [$3])[]dnl +])# LT_OPTION_DEFINE + + +# dlopen +# ------ +LT_OPTION_DEFINE([LT_INIT], [dlopen], [enable_dlopen=yes +]) + +AU_DEFUN([AC_LIBTOOL_DLOPEN], +[_LT_SET_OPTION([LT_INIT], [dlopen]) +AC_DIAGNOSE([obsolete], +[$0: Remove this warning and the call to _LT_SET_OPTION when you +put the 'dlopen' option into LT_INIT's first parameter.]) +]) + +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([AC_LIBTOOL_DLOPEN], []) + + +# win32-dll +# --------- +# Declare package support for building win32 dll's. +LT_OPTION_DEFINE([LT_INIT], [win32-dll], +[enable_win32_dll=yes + +case $host in +*-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-cegcc*) + AC_CHECK_TOOL(AS, as, false) + AC_CHECK_TOOL(DLLTOOL, dlltool, false) + AC_CHECK_TOOL(OBJDUMP, objdump, false) + ;; +esac + +test -z "$AS" && AS=as +_LT_DECL([], [AS], [1], [Assembler program])dnl + +test -z "$DLLTOOL" && DLLTOOL=dlltool +_LT_DECL([], [DLLTOOL], [1], [DLL creation program])dnl + +test -z "$OBJDUMP" && OBJDUMP=objdump +_LT_DECL([], [OBJDUMP], [1], [Object dumper program])dnl +])# win32-dll + +AU_DEFUN([AC_LIBTOOL_WIN32_DLL], +[AC_REQUIRE([AC_CANONICAL_HOST])dnl +_LT_SET_OPTION([LT_INIT], [win32-dll]) +AC_DIAGNOSE([obsolete], +[$0: Remove this warning and the call to _LT_SET_OPTION when you +put the 'win32-dll' option into LT_INIT's first parameter.]) +]) + +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([AC_LIBTOOL_WIN32_DLL], []) + + +# _LT_ENABLE_SHARED([DEFAULT]) +# ---------------------------- +# implement the --enable-shared flag, and supports the 'shared' and +# 'disable-shared' LT_INIT options. +# DEFAULT is either 'yes' or 'no'. If omitted, it defaults to 'yes'. +m4_define([_LT_ENABLE_SHARED], +[m4_define([_LT_ENABLE_SHARED_DEFAULT], [m4_if($1, no, no, yes)])dnl +AC_ARG_ENABLE([shared], + [AS_HELP_STRING([--enable-shared@<:@=PKGS@:>@], + [build shared libraries @<:@default=]_LT_ENABLE_SHARED_DEFAULT[@:>@])], + [p=${PACKAGE-default} + case $enableval in + yes) enable_shared=yes ;; + no) enable_shared=no ;; + *) + enable_shared=no + # Look at the argument we got. We use all the common list separators. + lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR, + for pkg in $enableval; do + IFS=$lt_save_ifs + if test "X$pkg" = "X$p"; then + enable_shared=yes + fi + done + IFS=$lt_save_ifs + ;; + esac], + [enable_shared=]_LT_ENABLE_SHARED_DEFAULT) + + _LT_DECL([build_libtool_libs], [enable_shared], [0], + [Whether or not to build shared libraries]) +])# _LT_ENABLE_SHARED + +LT_OPTION_DEFINE([LT_INIT], [shared], [_LT_ENABLE_SHARED([yes])]) +LT_OPTION_DEFINE([LT_INIT], [disable-shared], [_LT_ENABLE_SHARED([no])]) + +# Old names: +AC_DEFUN([AC_ENABLE_SHARED], +[_LT_SET_OPTION([LT_INIT], m4_if([$1], [no], [disable-])[shared]) +]) + +AC_DEFUN([AC_DISABLE_SHARED], +[_LT_SET_OPTION([LT_INIT], [disable-shared]) +]) + +AU_DEFUN([AM_ENABLE_SHARED], [AC_ENABLE_SHARED($@)]) +AU_DEFUN([AM_DISABLE_SHARED], [AC_DISABLE_SHARED($@)]) + +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([AM_ENABLE_SHARED], []) +dnl AC_DEFUN([AM_DISABLE_SHARED], []) + + + +# _LT_ENABLE_STATIC([DEFAULT]) +# ---------------------------- +# implement the --enable-static flag, and support the 'static' and +# 'disable-static' LT_INIT options. +# DEFAULT is either 'yes' or 'no'. If omitted, it defaults to 'yes'. +m4_define([_LT_ENABLE_STATIC], +[m4_define([_LT_ENABLE_STATIC_DEFAULT], [m4_if($1, no, no, yes)])dnl +AC_ARG_ENABLE([static], + [AS_HELP_STRING([--enable-static@<:@=PKGS@:>@], + [build static libraries @<:@default=]_LT_ENABLE_STATIC_DEFAULT[@:>@])], + [p=${PACKAGE-default} + case $enableval in + yes) enable_static=yes ;; + no) enable_static=no ;; + *) + enable_static=no + # Look at the argument we got. We use all the common list separators. + lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR, + for pkg in $enableval; do + IFS=$lt_save_ifs + if test "X$pkg" = "X$p"; then + enable_static=yes + fi + done + IFS=$lt_save_ifs + ;; + esac], + [enable_static=]_LT_ENABLE_STATIC_DEFAULT) + + _LT_DECL([build_old_libs], [enable_static], [0], + [Whether or not to build static libraries]) +])# _LT_ENABLE_STATIC + +LT_OPTION_DEFINE([LT_INIT], [static], [_LT_ENABLE_STATIC([yes])]) +LT_OPTION_DEFINE([LT_INIT], [disable-static], [_LT_ENABLE_STATIC([no])]) + +# Old names: +AC_DEFUN([AC_ENABLE_STATIC], +[_LT_SET_OPTION([LT_INIT], m4_if([$1], [no], [disable-])[static]) +]) + +AC_DEFUN([AC_DISABLE_STATIC], +[_LT_SET_OPTION([LT_INIT], [disable-static]) +]) + +AU_DEFUN([AM_ENABLE_STATIC], [AC_ENABLE_STATIC($@)]) +AU_DEFUN([AM_DISABLE_STATIC], [AC_DISABLE_STATIC($@)]) + +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([AM_ENABLE_STATIC], []) +dnl AC_DEFUN([AM_DISABLE_STATIC], []) + + + +# _LT_ENABLE_FAST_INSTALL([DEFAULT]) +# ---------------------------------- +# implement the --enable-fast-install flag, and support the 'fast-install' +# and 'disable-fast-install' LT_INIT options. +# DEFAULT is either 'yes' or 'no'. If omitted, it defaults to 'yes'. +m4_define([_LT_ENABLE_FAST_INSTALL], +[m4_define([_LT_ENABLE_FAST_INSTALL_DEFAULT], [m4_if($1, no, no, yes)])dnl +AC_ARG_ENABLE([fast-install], + [AS_HELP_STRING([--enable-fast-install@<:@=PKGS@:>@], + [optimize for fast installation @<:@default=]_LT_ENABLE_FAST_INSTALL_DEFAULT[@:>@])], + [p=${PACKAGE-default} + case $enableval in + yes) enable_fast_install=yes ;; + no) enable_fast_install=no ;; + *) + enable_fast_install=no + # Look at the argument we got. We use all the common list separators. + lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR, + for pkg in $enableval; do + IFS=$lt_save_ifs + if test "X$pkg" = "X$p"; then + enable_fast_install=yes + fi + done + IFS=$lt_save_ifs + ;; + esac], + [enable_fast_install=]_LT_ENABLE_FAST_INSTALL_DEFAULT) + +_LT_DECL([fast_install], [enable_fast_install], [0], + [Whether or not to optimize for fast installation])dnl +])# _LT_ENABLE_FAST_INSTALL + +LT_OPTION_DEFINE([LT_INIT], [fast-install], [_LT_ENABLE_FAST_INSTALL([yes])]) +LT_OPTION_DEFINE([LT_INIT], [disable-fast-install], [_LT_ENABLE_FAST_INSTALL([no])]) + +# Old names: +AU_DEFUN([AC_ENABLE_FAST_INSTALL], +[_LT_SET_OPTION([LT_INIT], m4_if([$1], [no], [disable-])[fast-install]) +AC_DIAGNOSE([obsolete], +[$0: Remove this warning and the call to _LT_SET_OPTION when you put +the 'fast-install' option into LT_INIT's first parameter.]) +]) + +AU_DEFUN([AC_DISABLE_FAST_INSTALL], +[_LT_SET_OPTION([LT_INIT], [disable-fast-install]) +AC_DIAGNOSE([obsolete], +[$0: Remove this warning and the call to _LT_SET_OPTION when you put +the 'disable-fast-install' option into LT_INIT's first parameter.]) +]) + +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([AC_ENABLE_FAST_INSTALL], []) +dnl AC_DEFUN([AM_DISABLE_FAST_INSTALL], []) + + +# _LT_WITH_AIX_SONAME([DEFAULT]) +# ---------------------------------- +# implement the --with-aix-soname flag, and support the `aix-soname=aix' +# and `aix-soname=both' and `aix-soname=svr4' LT_INIT options. DEFAULT +# is either `aix', `both' or `svr4'. If omitted, it defaults to `aix'. +m4_define([_LT_WITH_AIX_SONAME], +[m4_define([_LT_WITH_AIX_SONAME_DEFAULT], [m4_if($1, svr4, svr4, m4_if($1, both, both, aix))])dnl +shared_archive_member_spec= +case $host,$enable_shared in +power*-*-aix[[5-9]]*,yes) + AC_MSG_CHECKING([which variant of shared library versioning to provide]) + AC_ARG_WITH([aix-soname], + [AS_HELP_STRING([--with-aix-soname=aix|svr4|both], + [shared library versioning (aka "SONAME") variant to provide on AIX, @<:@default=]_LT_WITH_AIX_SONAME_DEFAULT[@:>@.])], + [case $withval in + aix|svr4|both) + ;; + *) + AC_MSG_ERROR([Unknown argument to --with-aix-soname]) + ;; + esac + lt_cv_with_aix_soname=$with_aix_soname], + [AC_CACHE_VAL([lt_cv_with_aix_soname], + [lt_cv_with_aix_soname=]_LT_WITH_AIX_SONAME_DEFAULT) + with_aix_soname=$lt_cv_with_aix_soname]) + AC_MSG_RESULT([$with_aix_soname]) + if test aix != "$with_aix_soname"; then + # For the AIX way of multilib, we name the shared archive member + # based on the bitwidth used, traditionally 'shr.o' or 'shr_64.o', + # and 'shr.imp' or 'shr_64.imp', respectively, for the Import File. + # Even when GNU compilers ignore OBJECT_MODE but need '-maix64' flag, + # the AIX toolchain works better with OBJECT_MODE set (default 32). + if test 64 = "${OBJECT_MODE-32}"; then + shared_archive_member_spec=shr_64 + else + shared_archive_member_spec=shr + fi + fi + ;; +*) + with_aix_soname=aix + ;; +esac + +_LT_DECL([], [shared_archive_member_spec], [0], + [Shared archive member basename, for filename based shared library versioning on AIX])dnl +])# _LT_WITH_AIX_SONAME + +LT_OPTION_DEFINE([LT_INIT], [aix-soname=aix], [_LT_WITH_AIX_SONAME([aix])]) +LT_OPTION_DEFINE([LT_INIT], [aix-soname=both], [_LT_WITH_AIX_SONAME([both])]) +LT_OPTION_DEFINE([LT_INIT], [aix-soname=svr4], [_LT_WITH_AIX_SONAME([svr4])]) + + +# _LT_WITH_PIC([MODE]) +# -------------------- +# implement the --with-pic flag, and support the 'pic-only' and 'no-pic' +# LT_INIT options. +# MODE is either 'yes' or 'no'. If omitted, it defaults to 'both'. +m4_define([_LT_WITH_PIC], +[AC_ARG_WITH([pic], + [AS_HELP_STRING([--with-pic@<:@=PKGS@:>@], + [try to use only PIC/non-PIC objects @<:@default=use both@:>@])], + [lt_p=${PACKAGE-default} + case $withval in + yes|no) pic_mode=$withval ;; + *) + pic_mode=default + # Look at the argument we got. We use all the common list separators. + lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR, + for lt_pkg in $withval; do + IFS=$lt_save_ifs + if test "X$lt_pkg" = "X$lt_p"; then + pic_mode=yes + fi + done + IFS=$lt_save_ifs + ;; + esac], + [pic_mode=m4_default([$1], [default])]) + +_LT_DECL([], [pic_mode], [0], [What type of objects to build])dnl +])# _LT_WITH_PIC + +LT_OPTION_DEFINE([LT_INIT], [pic-only], [_LT_WITH_PIC([yes])]) +LT_OPTION_DEFINE([LT_INIT], [no-pic], [_LT_WITH_PIC([no])]) + +# Old name: +AU_DEFUN([AC_LIBTOOL_PICMODE], +[_LT_SET_OPTION([LT_INIT], [pic-only]) +AC_DIAGNOSE([obsolete], +[$0: Remove this warning and the call to _LT_SET_OPTION when you +put the 'pic-only' option into LT_INIT's first parameter.]) +]) + +dnl aclocal-1.4 backwards compatibility: +dnl AC_DEFUN([AC_LIBTOOL_PICMODE], []) + + +m4_define([_LTDL_MODE], []) +LT_OPTION_DEFINE([LTDL_INIT], [nonrecursive], + [m4_define([_LTDL_MODE], [nonrecursive])]) +LT_OPTION_DEFINE([LTDL_INIT], [recursive], + [m4_define([_LTDL_MODE], [recursive])]) +LT_OPTION_DEFINE([LTDL_INIT], [subproject], + [m4_define([_LTDL_MODE], [subproject])]) + +m4_define([_LTDL_TYPE], []) +LT_OPTION_DEFINE([LTDL_INIT], [installable], + [m4_define([_LTDL_TYPE], [installable])]) +LT_OPTION_DEFINE([LTDL_INIT], [convenience], + [m4_define([_LTDL_TYPE], [convenience])]) + +# ltsugar.m4 -- libtool m4 base layer. -*-Autoconf-*- +# +# Copyright (C) 2004-2005, 2007-2008, 2011-2019, 2021-2022 Free Software +# Foundation, Inc. +# Written by Gary V. Vaughan, 2004 +# +# This file is free software; the Free Software Foundation gives +# unlimited permission to copy and/or distribute it, with or without +# modifications, as long as this notice is preserved. + +# serial 6 ltsugar.m4 + +# This is to help aclocal find these macros, as it can't see m4_define. +AC_DEFUN([LTSUGAR_VERSION], [m4_if([0.1])]) + + +# lt_join(SEP, ARG1, [ARG2...]) +# ----------------------------- +# Produce ARG1SEPARG2...SEPARGn, omitting [] arguments and their +# associated separator. +# Needed until we can rely on m4_join from Autoconf 2.62, since all earlier +# versions in m4sugar had bugs. +m4_define([lt_join], +[m4_if([$#], [1], [], + [$#], [2], [[$2]], + [m4_if([$2], [], [], [[$2]_])$0([$1], m4_shift(m4_shift($@)))])]) +m4_define([_lt_join], +[m4_if([$#$2], [2], [], + [m4_if([$2], [], [], [[$1$2]])$0([$1], m4_shift(m4_shift($@)))])]) + + +# lt_car(LIST) +# lt_cdr(LIST) +# ------------ +# Manipulate m4 lists. +# These macros are necessary as long as will still need to support +# Autoconf-2.59, which quotes differently. +m4_define([lt_car], [[$1]]) +m4_define([lt_cdr], +[m4_if([$#], 0, [m4_fatal([$0: cannot be called without arguments])], + [$#], 1, [], + [m4_dquote(m4_shift($@))])]) +m4_define([lt_unquote], $1) + + +# lt_append(MACRO-NAME, STRING, [SEPARATOR]) +# ------------------------------------------ +# Redefine MACRO-NAME to hold its former content plus 'SEPARATOR''STRING'. +# Note that neither SEPARATOR nor STRING are expanded; they are appended +# to MACRO-NAME as is (leaving the expansion for when MACRO-NAME is invoked). +# No SEPARATOR is output if MACRO-NAME was previously undefined (different +# than defined and empty). +# +# This macro is needed until we can rely on Autoconf 2.62, since earlier +# versions of m4sugar mistakenly expanded SEPARATOR but not STRING. +m4_define([lt_append], +[m4_define([$1], + m4_ifdef([$1], [m4_defn([$1])[$3]])[$2])]) + + + +# lt_combine(SEP, PREFIX-LIST, INFIX, SUFFIX1, [SUFFIX2...]) +# ---------------------------------------------------------- +# Produce a SEP delimited list of all paired combinations of elements of +# PREFIX-LIST with SUFFIX1 through SUFFIXn. Each element of the list +# has the form PREFIXmINFIXSUFFIXn. +# Needed until we can rely on m4_combine added in Autoconf 2.62. +m4_define([lt_combine], +[m4_if(m4_eval([$# > 3]), [1], + [m4_pushdef([_Lt_sep], [m4_define([_Lt_sep], m4_defn([lt_car]))])]]dnl +[[m4_foreach([_Lt_prefix], [$2], + [m4_foreach([_Lt_suffix], + ]m4_dquote(m4_dquote(m4_shift(m4_shift(m4_shift($@)))))[, + [_Lt_sep([$1])[]m4_defn([_Lt_prefix])[$3]m4_defn([_Lt_suffix])])])])]) + + +# lt_if_append_uniq(MACRO-NAME, VARNAME, [SEPARATOR], [UNIQ], [NOT-UNIQ]) +# ----------------------------------------------------------------------- +# Iff MACRO-NAME does not yet contain VARNAME, then append it (delimited +# by SEPARATOR if supplied) and expand UNIQ, else NOT-UNIQ. +m4_define([lt_if_append_uniq], +[m4_ifdef([$1], + [m4_if(m4_index([$3]m4_defn([$1])[$3], [$3$2$3]), [-1], + [lt_append([$1], [$2], [$3])$4], + [$5])], + [lt_append([$1], [$2], [$3])$4])]) + + +# lt_dict_add(DICT, KEY, VALUE) +# ----------------------------- +m4_define([lt_dict_add], +[m4_define([$1($2)], [$3])]) + + +# lt_dict_add_subkey(DICT, KEY, SUBKEY, VALUE) +# -------------------------------------------- +m4_define([lt_dict_add_subkey], +[m4_define([$1($2:$3)], [$4])]) + + +# lt_dict_fetch(DICT, KEY, [SUBKEY]) +# ---------------------------------- +m4_define([lt_dict_fetch], +[m4_ifval([$3], + m4_ifdef([$1($2:$3)], [m4_defn([$1($2:$3)])]), + m4_ifdef([$1($2)], [m4_defn([$1($2)])]))]) + + +# lt_if_dict_fetch(DICT, KEY, [SUBKEY], VALUE, IF-TRUE, [IF-FALSE]) +# ----------------------------------------------------------------- +m4_define([lt_if_dict_fetch], +[m4_if(lt_dict_fetch([$1], [$2], [$3]), [$4], + [$5], + [$6])]) + + +# lt_dict_filter(DICT, [SUBKEY], VALUE, [SEPARATOR], KEY, [...]) +# -------------------------------------------------------------- +m4_define([lt_dict_filter], +[m4_if([$5], [], [], + [lt_join(m4_quote(m4_default([$4], [[, ]])), + lt_unquote(m4_split(m4_normalize(m4_foreach(_Lt_key, lt_car([m4_shiftn(4, $@)]), + [lt_if_dict_fetch([$1], _Lt_key, [$2], [$3], [_Lt_key ])])))))])[]dnl +]) + +# ltversion.m4 -- version numbers -*- Autoconf -*- +# +# Copyright (C) 2004, 2011-2019, 2021-2022 Free Software Foundation, +# Inc. +# Written by Scott James Remnant, 2004 +# +# This file is free software; the Free Software Foundation gives +# unlimited permission to copy and/or distribute it, with or without +# modifications, as long as this notice is preserved. + +# @configure_input@ + +# serial 4245 ltversion.m4 +# This file is part of GNU Libtool + +m4_define([LT_PACKAGE_VERSION], [2.4.7]) +m4_define([LT_PACKAGE_REVISION], [2.4.7]) + +AC_DEFUN([LTVERSION_VERSION], +[macro_version='2.4.7' +macro_revision='2.4.7' +_LT_DECL(, macro_version, 0, [Which release of libtool.m4 was used?]) +_LT_DECL(, macro_revision, 0) +]) + +# lt~obsolete.m4 -- aclocal satisfying obsolete definitions. -*-Autoconf-*- +# +# Copyright (C) 2004-2005, 2007, 2009, 2011-2019, 2021-2022 Free +# Software Foundation, Inc. +# Written by Scott James Remnant, 2004. +# +# This file is free software; the Free Software Foundation gives +# unlimited permission to copy and/or distribute it, with or without +# modifications, as long as this notice is preserved. + +# serial 5 lt~obsolete.m4 + +# These exist entirely to fool aclocal when bootstrapping libtool. +# +# In the past libtool.m4 has provided macros via AC_DEFUN (or AU_DEFUN), +# which have later been changed to m4_define as they aren't part of the +# exported API, or moved to Autoconf or Automake where they belong. +# +# The trouble is, aclocal is a bit thick. It'll see the old AC_DEFUN +# in /usr/share/aclocal/libtool.m4 and remember it, then when it sees us +# using a macro with the same name in our local m4/libtool.m4 it'll +# pull the old libtool.m4 in (it doesn't see our shiny new m4_define +# and doesn't know about Autoconf macros at all.) +# +# So we provide this file, which has a silly filename so it's always +# included after everything else. This provides aclocal with the +# AC_DEFUNs it wants, but when m4 processes it, it doesn't do anything +# because those macros already exist, or will be overwritten later. +# We use AC_DEFUN over AU_DEFUN for compatibility with aclocal-1.6. +# +# Anytime we withdraw an AC_DEFUN or AU_DEFUN, remember to add it here. +# Yes, that means every name once taken will need to remain here until +# we give up compatibility with versions before 1.7, at which point +# we need to keep only those names which we still refer to. + +# This is to help aclocal find these macros, as it can't see m4_define. +AC_DEFUN([LTOBSOLETE_VERSION], [m4_if([1])]) + +m4_ifndef([AC_LIBTOOL_LINKER_OPTION], [AC_DEFUN([AC_LIBTOOL_LINKER_OPTION])]) +m4_ifndef([AC_PROG_EGREP], [AC_DEFUN([AC_PROG_EGREP])]) +m4_ifndef([_LT_AC_PROG_ECHO_BACKSLASH], [AC_DEFUN([_LT_AC_PROG_ECHO_BACKSLASH])]) +m4_ifndef([_LT_AC_SHELL_INIT], [AC_DEFUN([_LT_AC_SHELL_INIT])]) +m4_ifndef([_LT_AC_SYS_LIBPATH_AIX], [AC_DEFUN([_LT_AC_SYS_LIBPATH_AIX])]) +m4_ifndef([_LT_PROG_LTMAIN], [AC_DEFUN([_LT_PROG_LTMAIN])]) +m4_ifndef([_LT_AC_TAGVAR], [AC_DEFUN([_LT_AC_TAGVAR])]) +m4_ifndef([AC_LTDL_ENABLE_INSTALL], [AC_DEFUN([AC_LTDL_ENABLE_INSTALL])]) +m4_ifndef([AC_LTDL_PREOPEN], [AC_DEFUN([AC_LTDL_PREOPEN])]) +m4_ifndef([_LT_AC_SYS_COMPILER], [AC_DEFUN([_LT_AC_SYS_COMPILER])]) +m4_ifndef([_LT_AC_LOCK], [AC_DEFUN([_LT_AC_LOCK])]) +m4_ifndef([AC_LIBTOOL_SYS_OLD_ARCHIVE], [AC_DEFUN([AC_LIBTOOL_SYS_OLD_ARCHIVE])]) +m4_ifndef([_LT_AC_TRY_DLOPEN_SELF], [AC_DEFUN([_LT_AC_TRY_DLOPEN_SELF])]) +m4_ifndef([AC_LIBTOOL_PROG_CC_C_O], [AC_DEFUN([AC_LIBTOOL_PROG_CC_C_O])]) +m4_ifndef([AC_LIBTOOL_SYS_HARD_LINK_LOCKS], [AC_DEFUN([AC_LIBTOOL_SYS_HARD_LINK_LOCKS])]) +m4_ifndef([AC_LIBTOOL_OBJDIR], [AC_DEFUN([AC_LIBTOOL_OBJDIR])]) +m4_ifndef([AC_LTDL_OBJDIR], [AC_DEFUN([AC_LTDL_OBJDIR])]) +m4_ifndef([AC_LIBTOOL_PROG_LD_HARDCODE_LIBPATH], [AC_DEFUN([AC_LIBTOOL_PROG_LD_HARDCODE_LIBPATH])]) +m4_ifndef([AC_LIBTOOL_SYS_LIB_STRIP], [AC_DEFUN([AC_LIBTOOL_SYS_LIB_STRIP])]) +m4_ifndef([AC_PATH_MAGIC], [AC_DEFUN([AC_PATH_MAGIC])]) +m4_ifndef([AC_PROG_LD_GNU], [AC_DEFUN([AC_PROG_LD_GNU])]) +m4_ifndef([AC_PROG_LD_RELOAD_FLAG], [AC_DEFUN([AC_PROG_LD_RELOAD_FLAG])]) +m4_ifndef([AC_DEPLIBS_CHECK_METHOD], [AC_DEFUN([AC_DEPLIBS_CHECK_METHOD])]) +m4_ifndef([AC_LIBTOOL_PROG_COMPILER_NO_RTTI], [AC_DEFUN([AC_LIBTOOL_PROG_COMPILER_NO_RTTI])]) +m4_ifndef([AC_LIBTOOL_SYS_GLOBAL_SYMBOL_PIPE], [AC_DEFUN([AC_LIBTOOL_SYS_GLOBAL_SYMBOL_PIPE])]) +m4_ifndef([AC_LIBTOOL_PROG_COMPILER_PIC], [AC_DEFUN([AC_LIBTOOL_PROG_COMPILER_PIC])]) +m4_ifndef([AC_LIBTOOL_PROG_LD_SHLIBS], [AC_DEFUN([AC_LIBTOOL_PROG_LD_SHLIBS])]) +m4_ifndef([AC_LIBTOOL_POSTDEP_PREDEP], [AC_DEFUN([AC_LIBTOOL_POSTDEP_PREDEP])]) +m4_ifndef([LT_AC_PROG_EGREP], [AC_DEFUN([LT_AC_PROG_EGREP])]) +m4_ifndef([LT_AC_PROG_SED], [AC_DEFUN([LT_AC_PROG_SED])]) +m4_ifndef([_LT_CC_BASENAME], [AC_DEFUN([_LT_CC_BASENAME])]) +m4_ifndef([_LT_COMPILER_BOILERPLATE], [AC_DEFUN([_LT_COMPILER_BOILERPLATE])]) +m4_ifndef([_LT_LINKER_BOILERPLATE], [AC_DEFUN([_LT_LINKER_BOILERPLATE])]) +m4_ifndef([_AC_PROG_LIBTOOL], [AC_DEFUN([_AC_PROG_LIBTOOL])]) +m4_ifndef([AC_LIBTOOL_SETUP], [AC_DEFUN([AC_LIBTOOL_SETUP])]) +m4_ifndef([_LT_AC_CHECK_DLFCN], [AC_DEFUN([_LT_AC_CHECK_DLFCN])]) +m4_ifndef([AC_LIBTOOL_SYS_DYNAMIC_LINKER], [AC_DEFUN([AC_LIBTOOL_SYS_DYNAMIC_LINKER])]) +m4_ifndef([_LT_AC_TAGCONFIG], [AC_DEFUN([_LT_AC_TAGCONFIG])]) +m4_ifndef([AC_DISABLE_FAST_INSTALL], [AC_DEFUN([AC_DISABLE_FAST_INSTALL])]) +m4_ifndef([_LT_AC_LANG_CXX], [AC_DEFUN([_LT_AC_LANG_CXX])]) +m4_ifndef([_LT_AC_LANG_F77], [AC_DEFUN([_LT_AC_LANG_F77])]) +m4_ifndef([_LT_AC_LANG_GCJ], [AC_DEFUN([_LT_AC_LANG_GCJ])]) +m4_ifndef([AC_LIBTOOL_LANG_C_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_C_CONFIG])]) +m4_ifndef([_LT_AC_LANG_C_CONFIG], [AC_DEFUN([_LT_AC_LANG_C_CONFIG])]) +m4_ifndef([AC_LIBTOOL_LANG_CXX_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_CXX_CONFIG])]) +m4_ifndef([_LT_AC_LANG_CXX_CONFIG], [AC_DEFUN([_LT_AC_LANG_CXX_CONFIG])]) +m4_ifndef([AC_LIBTOOL_LANG_F77_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_F77_CONFIG])]) +m4_ifndef([_LT_AC_LANG_F77_CONFIG], [AC_DEFUN([_LT_AC_LANG_F77_CONFIG])]) +m4_ifndef([AC_LIBTOOL_LANG_GCJ_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_GCJ_CONFIG])]) +m4_ifndef([_LT_AC_LANG_GCJ_CONFIG], [AC_DEFUN([_LT_AC_LANG_GCJ_CONFIG])]) +m4_ifndef([AC_LIBTOOL_LANG_RC_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_RC_CONFIG])]) +m4_ifndef([_LT_AC_LANG_RC_CONFIG], [AC_DEFUN([_LT_AC_LANG_RC_CONFIG])]) +m4_ifndef([AC_LIBTOOL_CONFIG], [AC_DEFUN([AC_LIBTOOL_CONFIG])]) +m4_ifndef([_LT_AC_FILE_LTDLL_C], [AC_DEFUN([_LT_AC_FILE_LTDLL_C])]) +m4_ifndef([_LT_REQUIRED_DARWIN_CHECKS], [AC_DEFUN([_LT_REQUIRED_DARWIN_CHECKS])]) +m4_ifndef([_LT_AC_PROG_CXXCPP], [AC_DEFUN([_LT_AC_PROG_CXXCPP])]) +m4_ifndef([_LT_PREPARE_SED_QUOTE_VARS], [AC_DEFUN([_LT_PREPARE_SED_QUOTE_VARS])]) +m4_ifndef([_LT_PROG_ECHO_BACKSLASH], [AC_DEFUN([_LT_PROG_ECHO_BACKSLASH])]) +m4_ifndef([_LT_PROG_F77], [AC_DEFUN([_LT_PROG_F77])]) +m4_ifndef([_LT_PROG_FC], [AC_DEFUN([_LT_PROG_FC])]) +m4_ifndef([_LT_PROG_CXX], [AC_DEFUN([_LT_PROG_CXX])]) + +m4_include([ax_compare_version.m4]) +m4_include([ax_prog_python_version.m4]) +m4_include([ax_pthread.m4]) +m4_include([ft-munmap.m4]) +m4_include([pkg.m4]) diff --git a/3rdparty/freetype-2.13.2/builds/unix/ax_compare_version.m4 b/3rdparty/freetype-2.13.2/builds/unix/ax_compare_version.m4 new file mode 100644 index 000000000..ffb4997e8 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/ax_compare_version.m4 @@ -0,0 +1,177 @@ +# =========================================================================== +# https://www.gnu.org/software/autoconf-archive/ax_compare_version.html +# =========================================================================== +# +# SYNOPSIS +# +# AX_COMPARE_VERSION(VERSION_A, OP, VERSION_B, [ACTION-IF-TRUE], [ACTION-IF-FALSE]) +# +# DESCRIPTION +# +# This macro compares two version strings. Due to the various number of +# minor-version numbers that can exist, and the fact that string +# comparisons are not compatible with numeric comparisons, this is not +# necessarily trivial to do in a autoconf script. This macro makes doing +# these comparisons easy. +# +# The six basic comparisons are available, as well as checking equality +# limited to a certain number of minor-version levels. +# +# The operator OP determines what type of comparison to do, and can be one +# of: +# +# eq - equal (test A == B) +# ne - not equal (test A != B) +# le - less than or equal (test A <= B) +# ge - greater than or equal (test A >= B) +# lt - less than (test A < B) +# gt - greater than (test A > B) +# +# Additionally, the eq and ne operator can have a number after it to limit +# the test to that number of minor versions. +# +# eq0 - equal up to the length of the shorter version +# ne0 - not equal up to the length of the shorter version +# eqN - equal up to N sub-version levels +# neN - not equal up to N sub-version levels +# +# When the condition is true, shell commands ACTION-IF-TRUE are run, +# otherwise shell commands ACTION-IF-FALSE are run. The environment +# variable 'ax_compare_version' is always set to either 'true' or 'false' +# as well. +# +# Examples: +# +# AX_COMPARE_VERSION([3.15.7],[lt],[3.15.8]) +# AX_COMPARE_VERSION([3.15],[lt],[3.15.8]) +# +# would both be true. +# +# AX_COMPARE_VERSION([3.15.7],[eq],[3.15.8]) +# AX_COMPARE_VERSION([3.15],[gt],[3.15.8]) +# +# would both be false. +# +# AX_COMPARE_VERSION([3.15.7],[eq2],[3.15.8]) +# +# would be true because it is only comparing two minor versions. +# +# AX_COMPARE_VERSION([3.15.7],[eq0],[3.15]) +# +# would be true because it is only comparing the lesser number of minor +# versions of the two values. +# +# Note: The characters that separate the version numbers do not matter. An +# empty string is the same as version 0. OP is evaluated by autoconf, not +# configure, so must be a string, not a variable. +# +# The author would like to acknowledge Guido Draheim whose advice about +# the m4_case and m4_ifvaln functions make this macro only include the +# portions necessary to perform the specific comparison specified by the +# OP argument in the final configure script. +# +# LICENSE +# +# Copyright (c) 2008 Tim Toolan +# +# Copying and distribution of this file, with or without modification, are +# permitted in any medium without royalty provided the copyright notice +# and this notice are preserved. This file is offered as-is, without any +# warranty. + +#serial 13 + +dnl ######################################################################### +AC_DEFUN([AX_COMPARE_VERSION], [ + AC_REQUIRE([AC_PROG_AWK]) + + # Used to indicate true or false condition + ax_compare_version=false + + # Convert the two version strings to be compared into a format that + # allows a simple string comparison. The end result is that a version + # string of the form 1.12.5-r617 will be converted to the form + # 0001001200050617. In other words, each number is zero padded to four + # digits, and non digits are removed. + AS_VAR_PUSHDEF([A],[ax_compare_version_A]) + A=`echo "$1" | sed -e 's/\([[0-9]]*\)/Z\1Z/g' \ + -e 's/Z\([[0-9]]\)Z/Z0\1Z/g' \ + -e 's/Z\([[0-9]][[0-9]]\)Z/Z0\1Z/g' \ + -e 's/Z\([[0-9]][[0-9]][[0-9]]\)Z/Z0\1Z/g' \ + -e 's/[[^0-9]]//g'` + + AS_VAR_PUSHDEF([B],[ax_compare_version_B]) + B=`echo "$3" | sed -e 's/\([[0-9]]*\)/Z\1Z/g' \ + -e 's/Z\([[0-9]]\)Z/Z0\1Z/g' \ + -e 's/Z\([[0-9]][[0-9]]\)Z/Z0\1Z/g' \ + -e 's/Z\([[0-9]][[0-9]][[0-9]]\)Z/Z0\1Z/g' \ + -e 's/[[^0-9]]//g'` + + dnl # In the case of le, ge, lt, and gt, the strings are sorted as necessary + dnl # then the first line is used to determine if the condition is true. + dnl # The sed right after the echo is to remove any indented white space. + m4_case(m4_tolower($2), + [lt],[ + ax_compare_version=`echo "x$A +x$B" | sed 's/^ *//' | sort -r | sed "s/x${A}/false/;s/x${B}/true/;1q"` + ], + [gt],[ + ax_compare_version=`echo "x$A +x$B" | sed 's/^ *//' | sort | sed "s/x${A}/false/;s/x${B}/true/;1q"` + ], + [le],[ + ax_compare_version=`echo "x$A +x$B" | sed 's/^ *//' | sort | sed "s/x${A}/true/;s/x${B}/false/;1q"` + ], + [ge],[ + ax_compare_version=`echo "x$A +x$B" | sed 's/^ *//' | sort -r | sed "s/x${A}/true/;s/x${B}/false/;1q"` + ],[ + dnl Split the operator from the subversion count if present. + m4_bmatch(m4_substr($2,2), + [0],[ + # A count of zero means use the length of the shorter version. + # Determine the number of characters in A and B. + ax_compare_version_len_A=`echo "$A" | $AWK '{print(length)}'` + ax_compare_version_len_B=`echo "$B" | $AWK '{print(length)}'` + + # Set A to no more than B's length and B to no more than A's length. + A=`echo "$A" | sed "s/\(.\{$ax_compare_version_len_B\}\).*/\1/"` + B=`echo "$B" | sed "s/\(.\{$ax_compare_version_len_A\}\).*/\1/"` + ], + [[0-9]+],[ + # A count greater than zero means use only that many subversions + A=`echo "$A" | sed "s/\(\([[0-9]]\{4\}\)\{m4_substr($2,2)\}\).*/\1/"` + B=`echo "$B" | sed "s/\(\([[0-9]]\{4\}\)\{m4_substr($2,2)\}\).*/\1/"` + ], + [.+],[ + AC_WARNING( + [invalid OP numeric parameter: $2]) + ],[]) + + # Pad zeros at end of numbers to make same length. + ax_compare_version_tmp_A="$A`echo $B | sed 's/./0/g'`" + B="$B`echo $A | sed 's/./0/g'`" + A="$ax_compare_version_tmp_A" + + # Check for equality or inequality as necessary. + m4_case(m4_tolower(m4_substr($2,0,2)), + [eq],[ + test "x$A" = "x$B" && ax_compare_version=true + ], + [ne],[ + test "x$A" != "x$B" && ax_compare_version=true + ],[ + AC_WARNING([invalid OP parameter: $2]) + ]) + ]) + + AS_VAR_POPDEF([A])dnl + AS_VAR_POPDEF([B])dnl + + dnl # Execute ACTION-IF-TRUE / ACTION-IF-FALSE. + if test "$ax_compare_version" = "true" ; then + m4_ifvaln([$4],[$4],[:])dnl + m4_ifvaln([$5],[else $5])dnl + fi +]) dnl AX_COMPARE_VERSION diff --git a/3rdparty/freetype-2.13.2/builds/unix/ax_prog_python_version.m4 b/3rdparty/freetype-2.13.2/builds/unix/ax_prog_python_version.m4 new file mode 100644 index 000000000..dbc3dbf1d --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/ax_prog_python_version.m4 @@ -0,0 +1,66 @@ +# =========================================================================== +# https://www.gnu.org/software/autoconf-archive/ax_prog_python_version.html +# =========================================================================== +# +# SYNOPSIS +# +# AX_PROG_PYTHON_VERSION([VERSION],[ACTION-IF-TRUE],[ACTION-IF-FALSE]) +# +# DESCRIPTION +# +# Makes sure that python supports the version indicated. If true the shell +# commands in ACTION-IF-TRUE are executed. If not the shell commands in +# ACTION-IF-FALSE are run. Note if $PYTHON is not set (for example by +# running AC_CHECK_PROG or AC_PATH_PROG) the macro will fail. +# +# Example: +# +# AC_PATH_PROG([PYTHON],[python]) +# AX_PROG_PYTHON_VERSION([2.4.4],[ ... ],[ ... ]) +# +# This will check to make sure that the python you have supports at least +# version 2.4.4. +# +# NOTE: This macro uses the $PYTHON variable to perform the check. +# AX_WITH_PYTHON can be used to set that variable prior to running this +# macro. The $PYTHON_VERSION variable will be valorized with the detected +# version. +# +# LICENSE +# +# Copyright (c) 2009 Francesco Salvestrini +# +# Copying and distribution of this file, with or without modification, are +# permitted in any medium without royalty provided the copyright notice +# and this notice are preserved. This file is offered as-is, without any +# warranty. + +#serial 12 + +AC_DEFUN([AX_PROG_PYTHON_VERSION],[ + AC_REQUIRE([AC_PROG_SED]) + AC_REQUIRE([AC_PROG_GREP]) + + AS_IF([test -n "$PYTHON"],[ + ax_python_version="$1" + + AC_MSG_CHECKING([for python version]) + changequote(<<,>>) + python_version=`$PYTHON -V 2>&1 | $GREP "^Python " | $SED -e 's/^.* \([0-9]*\.[0-9]*\.[0-9]*\)/\1/'` + changequote([,]) + AC_MSG_RESULT($python_version) + + AC_SUBST([PYTHON_VERSION],[$python_version]) + + AX_COMPARE_VERSION([$ax_python_version],[le],[$python_version],[ + : + $2 + ],[ + : + $3 + ]) + ],[ + AC_MSG_WARN([could not find the python interpreter]) + $3 + ]) +]) diff --git a/3rdparty/freetype-2.13.2/builds/unix/ax_pthread.m4 b/3rdparty/freetype-2.13.2/builds/unix/ax_pthread.m4 new file mode 100644 index 000000000..e5858e50c --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/ax_pthread.m4 @@ -0,0 +1,522 @@ +# =========================================================================== +# https://www.gnu.org/software/autoconf-archive/ax_pthread.html +# =========================================================================== +# +# SYNOPSIS +# +# AX_PTHREAD([ACTION-IF-FOUND[, ACTION-IF-NOT-FOUND]]) +# +# DESCRIPTION +# +# This macro figures out how to build C programs using POSIX threads. It +# sets the PTHREAD_LIBS output variable to the threads library and linker +# flags, and the PTHREAD_CFLAGS output variable to any special C compiler +# flags that are needed. (The user can also force certain compiler +# flags/libs to be tested by setting these environment variables.) +# +# Also sets PTHREAD_CC and PTHREAD_CXX to any special C compiler that is +# needed for multi-threaded programs (defaults to the value of CC +# respectively CXX otherwise). (This is necessary on e.g. AIX to use the +# special cc_r/CC_r compiler alias.) +# +# NOTE: You are assumed to not only compile your program with these flags, +# but also to link with them as well. For example, you might link with +# $PTHREAD_CC $CFLAGS $PTHREAD_CFLAGS $LDFLAGS ... $PTHREAD_LIBS $LIBS +# $PTHREAD_CXX $CXXFLAGS $PTHREAD_CFLAGS $LDFLAGS ... $PTHREAD_LIBS $LIBS +# +# If you are only building threaded programs, you may wish to use these +# variables in your default LIBS, CFLAGS, and CC: +# +# LIBS="$PTHREAD_LIBS $LIBS" +# CFLAGS="$CFLAGS $PTHREAD_CFLAGS" +# CXXFLAGS="$CXXFLAGS $PTHREAD_CFLAGS" +# CC="$PTHREAD_CC" +# CXX="$PTHREAD_CXX" +# +# In addition, if the PTHREAD_CREATE_JOINABLE thread-attribute constant +# has a nonstandard name, this macro defines PTHREAD_CREATE_JOINABLE to +# that name (e.g. PTHREAD_CREATE_UNDETACHED on AIX). +# +# Also HAVE_PTHREAD_PRIO_INHERIT is defined if pthread is found and the +# PTHREAD_PRIO_INHERIT symbol is defined when compiling with +# PTHREAD_CFLAGS. +# +# ACTION-IF-FOUND is a list of shell commands to run if a threads library +# is found, and ACTION-IF-NOT-FOUND is a list of commands to run it if it +# is not found. If ACTION-IF-FOUND is not specified, the default action +# will define HAVE_PTHREAD. +# +# Please let the authors know if this macro fails on any platform, or if +# you have any other suggestions or comments. This macro was based on work +# by SGJ on autoconf scripts for FFTW (http://www.fftw.org/) (with help +# from M. Frigo), as well as ac_pthread and hb_pthread macros posted by +# Alejandro Forero Cuervo to the autoconf macro repository. We are also +# grateful for the helpful feedback of numerous users. +# +# Updated for Autoconf 2.68 by Daniel Richard G. +# +# LICENSE +# +# Copyright (c) 2008 Steven G. Johnson +# Copyright (c) 2011 Daniel Richard G. +# Copyright (c) 2019 Marc Stevens +# +# This program is free software: you can redistribute it and/or modify it +# under the terms of the GNU General Public License as published by the +# Free Software Foundation, either version 3 of the License, or (at your +# option) any later version. +# +# This program is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General +# Public License for more details. +# +# You should have received a copy of the GNU General Public License along +# with this program. If not, see . +# +# As a special exception, the respective Autoconf Macro's copyright owner +# gives unlimited permission to copy, distribute and modify the configure +# scripts that are the output of Autoconf when processing the Macro. You +# need not follow the terms of the GNU General Public License when using +# or distributing such scripts, even though portions of the text of the +# Macro appear in them. The GNU General Public License (GPL) does govern +# all other use of the material that constitutes the Autoconf Macro. +# +# This special exception to the GPL applies to versions of the Autoconf +# Macro released by the Autoconf Archive. When you make and distribute a +# modified version of the Autoconf Macro, you may extend this special +# exception to the GPL to apply to your modified version as well. + +#serial 30 + +AU_ALIAS([ACX_PTHREAD], [AX_PTHREAD]) +AC_DEFUN([AX_PTHREAD], [ +AC_REQUIRE([AC_CANONICAL_TARGET]) +AC_REQUIRE([AC_PROG_CC]) +AC_REQUIRE([AC_PROG_SED]) +AC_LANG_PUSH([C]) +ax_pthread_ok=no + +# We used to check for pthread.h first, but this fails if pthread.h +# requires special compiler flags (e.g. on Tru64 or Sequent). +# It gets checked for in the link test anyway. + +# First of all, check if the user has set any of the PTHREAD_LIBS, +# etcetera environment variables, and if threads linking works using +# them: +if test "x$PTHREAD_CFLAGS$PTHREAD_LIBS" != "x"; then + ax_pthread_save_CC="$CC" + ax_pthread_save_CFLAGS="$CFLAGS" + ax_pthread_save_LIBS="$LIBS" + AS_IF([test "x$PTHREAD_CC" != "x"], [CC="$PTHREAD_CC"]) + AS_IF([test "x$PTHREAD_CXX" != "x"], [CXX="$PTHREAD_CXX"]) + CFLAGS="$CFLAGS $PTHREAD_CFLAGS" + LIBS="$PTHREAD_LIBS $LIBS" + AC_MSG_CHECKING([for pthread_join using $CC $PTHREAD_CFLAGS $PTHREAD_LIBS]) + AC_LINK_IFELSE([AC_LANG_CALL([], [pthread_join])], [ax_pthread_ok=yes]) + AC_MSG_RESULT([$ax_pthread_ok]) + if test "x$ax_pthread_ok" = "xno"; then + PTHREAD_LIBS="" + PTHREAD_CFLAGS="" + fi + CC="$ax_pthread_save_CC" + CFLAGS="$ax_pthread_save_CFLAGS" + LIBS="$ax_pthread_save_LIBS" +fi + +# We must check for the threads library under a number of different +# names; the ordering is very important because some systems +# (e.g. DEC) have both -lpthread and -lpthreads, where one of the +# libraries is broken (non-POSIX). + +# Create a list of thread flags to try. Items with a "," contain both +# C compiler flags (before ",") and linker flags (after ","). Other items +# starting with a "-" are C compiler flags, and remaining items are +# library names, except for "none" which indicates that we try without +# any flags at all, and "pthread-config" which is a program returning +# the flags for the Pth emulation library. + +ax_pthread_flags="pthreads none -Kthread -pthread -pthreads -mthreads pthread --thread-safe -mt pthread-config" + +# The ordering *is* (sometimes) important. Some notes on the +# individual items follow: + +# pthreads: AIX (must check this before -lpthread) +# none: in case threads are in libc; should be tried before -Kthread and +# other compiler flags to prevent continual compiler warnings +# -Kthread: Sequent (threads in libc, but -Kthread needed for pthread.h) +# -pthread: Linux/gcc (kernel threads), BSD/gcc (userland threads), Tru64 +# (Note: HP C rejects this with "bad form for `-t' option") +# -pthreads: Solaris/gcc (Note: HP C also rejects) +# -mt: Sun Workshop C (may only link SunOS threads [-lthread], but it +# doesn't hurt to check since this sometimes defines pthreads and +# -D_REENTRANT too), HP C (must be checked before -lpthread, which +# is present but should not be used directly; and before -mthreads, +# because the compiler interprets this as "-mt" + "-hreads") +# -mthreads: Mingw32/gcc, Lynx/gcc +# pthread: Linux, etcetera +# --thread-safe: KAI C++ +# pthread-config: use pthread-config program (for GNU Pth library) + +case $target_os in + + freebsd*) + + # -kthread: FreeBSD kernel threads (preferred to -pthread since SMP-able) + # lthread: LinuxThreads port on FreeBSD (also preferred to -pthread) + + ax_pthread_flags="-kthread lthread $ax_pthread_flags" + ;; + + hpux*) + + # From the cc(1) man page: "[-mt] Sets various -D flags to enable + # multi-threading and also sets -lpthread." + + ax_pthread_flags="-mt -pthread pthread $ax_pthread_flags" + ;; + + openedition*) + + # IBM z/OS requires a feature-test macro to be defined in order to + # enable POSIX threads at all, so give the user a hint if this is + # not set. (We don't define these ourselves, as they can affect + # other portions of the system API in unpredictable ways.) + + AC_EGREP_CPP([AX_PTHREAD_ZOS_MISSING], + [ +# if !defined(_OPEN_THREADS) && !defined(_UNIX03_THREADS) + AX_PTHREAD_ZOS_MISSING +# endif + ], + [AC_MSG_WARN([IBM z/OS requires -D_OPEN_THREADS or -D_UNIX03_THREADS to enable pthreads support.])]) + ;; + + solaris*) + + # On Solaris (at least, for some versions), libc contains stubbed + # (non-functional) versions of the pthreads routines, so link-based + # tests will erroneously succeed. (N.B.: The stubs are missing + # pthread_cleanup_push, or rather a function called by this macro, + # so we could check for that, but who knows whether they'll stub + # that too in a future libc.) So we'll check first for the + # standard Solaris way of linking pthreads (-mt -lpthread). + + ax_pthread_flags="-mt,-lpthread pthread $ax_pthread_flags" + ;; +esac + +# Are we compiling with Clang? + +AC_CACHE_CHECK([whether $CC is Clang], + [ax_cv_PTHREAD_CLANG], + [ax_cv_PTHREAD_CLANG=no + # Note that Autoconf sets GCC=yes for Clang as well as GCC + if test "x$GCC" = "xyes"; then + AC_EGREP_CPP([AX_PTHREAD_CC_IS_CLANG], + [/* Note: Clang 2.7 lacks __clang_[a-z]+__ */ +# if defined(__clang__) && defined(__llvm__) + AX_PTHREAD_CC_IS_CLANG +# endif + ], + [ax_cv_PTHREAD_CLANG=yes]) + fi + ]) +ax_pthread_clang="$ax_cv_PTHREAD_CLANG" + + +# GCC generally uses -pthread, or -pthreads on some platforms (e.g. SPARC) + +# Note that for GCC and Clang -pthread generally implies -lpthread, +# except when -nostdlib is passed. +# This is problematic using libtool to build C++ shared libraries with pthread: +# [1] https://gcc.gnu.org/bugzilla/show_bug.cgi?id=25460 +# [2] https://bugzilla.redhat.com/show_bug.cgi?id=661333 +# [3] https://bugs.debian.org/cgi-bin/bugreport.cgi?bug=468555 +# To solve this, first try -pthread together with -lpthread for GCC + +AS_IF([test "x$GCC" = "xyes"], + [ax_pthread_flags="-pthread,-lpthread -pthread -pthreads $ax_pthread_flags"]) + +# Clang takes -pthread (never supported any other flag), but we'll try with -lpthread first + +AS_IF([test "x$ax_pthread_clang" = "xyes"], + [ax_pthread_flags="-pthread,-lpthread -pthread"]) + + +# The presence of a feature test macro requesting re-entrant function +# definitions is, on some systems, a strong hint that pthreads support is +# correctly enabled + +case $target_os in + darwin* | hpux* | linux* | osf* | solaris*) + ax_pthread_check_macro="_REENTRANT" + ;; + + aix*) + ax_pthread_check_macro="_THREAD_SAFE" + ;; + + *) + ax_pthread_check_macro="--" + ;; +esac +AS_IF([test "x$ax_pthread_check_macro" = "x--"], + [ax_pthread_check_cond=0], + [ax_pthread_check_cond="!defined($ax_pthread_check_macro)"]) + + +if test "x$ax_pthread_ok" = "xno"; then +for ax_pthread_try_flag in $ax_pthread_flags; do + + case $ax_pthread_try_flag in + none) + AC_MSG_CHECKING([whether pthreads work without any flags]) + ;; + + *,*) + PTHREAD_CFLAGS=`echo $ax_pthread_try_flag | sed "s/^\(.*\),\(.*\)$/\1/"` + PTHREAD_LIBS=`echo $ax_pthread_try_flag | sed "s/^\(.*\),\(.*\)$/\2/"` + AC_MSG_CHECKING([whether pthreads work with "$PTHREAD_CFLAGS" and "$PTHREAD_LIBS"]) + ;; + + -*) + AC_MSG_CHECKING([whether pthreads work with $ax_pthread_try_flag]) + PTHREAD_CFLAGS="$ax_pthread_try_flag" + ;; + + pthread-config) + AC_CHECK_PROG([ax_pthread_config], [pthread-config], [yes], [no]) + AS_IF([test "x$ax_pthread_config" = "xno"], [continue]) + PTHREAD_CFLAGS="`pthread-config --cflags`" + PTHREAD_LIBS="`pthread-config --ldflags` `pthread-config --libs`" + ;; + + *) + AC_MSG_CHECKING([for the pthreads library -l$ax_pthread_try_flag]) + PTHREAD_LIBS="-l$ax_pthread_try_flag" + ;; + esac + + ax_pthread_save_CFLAGS="$CFLAGS" + ax_pthread_save_LIBS="$LIBS" + CFLAGS="$CFLAGS $PTHREAD_CFLAGS" + LIBS="$PTHREAD_LIBS $LIBS" + + # Check for various functions. We must include pthread.h, + # since some functions may be macros. (On the Sequent, we + # need a special flag -Kthread to make this header compile.) + # We check for pthread_join because it is in -lpthread on IRIX + # while pthread_create is in libc. We check for pthread_attr_init + # due to DEC craziness with -lpthreads. We check for + # pthread_cleanup_push because it is one of the few pthread + # functions on Solaris that doesn't have a non-functional libc stub. + # We try pthread_create on general principles. + + AC_LINK_IFELSE([AC_LANG_PROGRAM([#include +# if $ax_pthread_check_cond +# error "$ax_pthread_check_macro must be defined" +# endif + static void *some_global = NULL; + static void routine(void *a) + { + /* To avoid any unused-parameter or + unused-but-set-parameter warning. */ + some_global = a; + } + static void *start_routine(void *a) { return a; }], + [pthread_t th; pthread_attr_t attr; + pthread_create(&th, 0, start_routine, 0); + pthread_join(th, 0); + pthread_attr_init(&attr); + pthread_cleanup_push(routine, 0); + pthread_cleanup_pop(0) /* ; */])], + [ax_pthread_ok=yes], + []) + + CFLAGS="$ax_pthread_save_CFLAGS" + LIBS="$ax_pthread_save_LIBS" + + AC_MSG_RESULT([$ax_pthread_ok]) + AS_IF([test "x$ax_pthread_ok" = "xyes"], [break]) + + PTHREAD_LIBS="" + PTHREAD_CFLAGS="" +done +fi + + +# Clang needs special handling, because older versions handle the -pthread +# option in a rather... idiosyncratic way + +if test "x$ax_pthread_clang" = "xyes"; then + + # Clang takes -pthread; it has never supported any other flag + + # (Note 1: This will need to be revisited if a system that Clang + # supports has POSIX threads in a separate library. This tends not + # to be the way of modern systems, but it's conceivable.) + + # (Note 2: On some systems, notably Darwin, -pthread is not needed + # to get POSIX threads support; the API is always present and + # active. We could reasonably leave PTHREAD_CFLAGS empty. But + # -pthread does define _REENTRANT, and while the Darwin headers + # ignore this macro, third-party headers might not.) + + # However, older versions of Clang make a point of warning the user + # that, in an invocation where only linking and no compilation is + # taking place, the -pthread option has no effect ("argument unused + # during compilation"). They expect -pthread to be passed in only + # when source code is being compiled. + # + # Problem is, this is at odds with the way Automake and most other + # C build frameworks function, which is that the same flags used in + # compilation (CFLAGS) are also used in linking. Many systems + # supported by AX_PTHREAD require exactly this for POSIX threads + # support, and in fact it is often not straightforward to specify a + # flag that is used only in the compilation phase and not in + # linking. Such a scenario is extremely rare in practice. + # + # Even though use of the -pthread flag in linking would only print + # a warning, this can be a nuisance for well-run software projects + # that build with -Werror. So if the active version of Clang has + # this misfeature, we search for an option to squash it. + + AC_CACHE_CHECK([whether Clang needs flag to prevent "argument unused" warning when linking with -pthread], + [ax_cv_PTHREAD_CLANG_NO_WARN_FLAG], + [ax_cv_PTHREAD_CLANG_NO_WARN_FLAG=unknown + # Create an alternate version of $ac_link that compiles and + # links in two steps (.c -> .o, .o -> exe) instead of one + # (.c -> exe), because the warning occurs only in the second + # step + ax_pthread_save_ac_link="$ac_link" + ax_pthread_sed='s/conftest\.\$ac_ext/conftest.$ac_objext/g' + ax_pthread_link_step=`AS_ECHO(["$ac_link"]) | sed "$ax_pthread_sed"` + ax_pthread_2step_ac_link="($ac_compile) && (echo ==== >&5) && ($ax_pthread_link_step)" + ax_pthread_save_CFLAGS="$CFLAGS" + for ax_pthread_try in '' -Qunused-arguments -Wno-unused-command-line-argument unknown; do + AS_IF([test "x$ax_pthread_try" = "xunknown"], [break]) + CFLAGS="-Werror -Wunknown-warning-option $ax_pthread_try -pthread $ax_pthread_save_CFLAGS" + ac_link="$ax_pthread_save_ac_link" + AC_LINK_IFELSE([AC_LANG_SOURCE([[int main(void){return 0;}]])], + [ac_link="$ax_pthread_2step_ac_link" + AC_LINK_IFELSE([AC_LANG_SOURCE([[int main(void){return 0;}]])], + [break]) + ]) + done + ac_link="$ax_pthread_save_ac_link" + CFLAGS="$ax_pthread_save_CFLAGS" + AS_IF([test "x$ax_pthread_try" = "x"], [ax_pthread_try=no]) + ax_cv_PTHREAD_CLANG_NO_WARN_FLAG="$ax_pthread_try" + ]) + + case "$ax_cv_PTHREAD_CLANG_NO_WARN_FLAG" in + no | unknown) ;; + *) PTHREAD_CFLAGS="$ax_cv_PTHREAD_CLANG_NO_WARN_FLAG $PTHREAD_CFLAGS" ;; + esac + +fi # $ax_pthread_clang = yes + + + +# Various other checks: +if test "x$ax_pthread_ok" = "xyes"; then + ax_pthread_save_CFLAGS="$CFLAGS" + ax_pthread_save_LIBS="$LIBS" + CFLAGS="$CFLAGS $PTHREAD_CFLAGS" + LIBS="$PTHREAD_LIBS $LIBS" + + # Detect AIX lossage: JOINABLE attribute is called UNDETACHED. + AC_CACHE_CHECK([for joinable pthread attribute], + [ax_cv_PTHREAD_JOINABLE_ATTR], + [ax_cv_PTHREAD_JOINABLE_ATTR=unknown + for ax_pthread_attr in PTHREAD_CREATE_JOINABLE PTHREAD_CREATE_UNDETACHED; do + AC_LINK_IFELSE([AC_LANG_PROGRAM([#include ], + [int attr = $ax_pthread_attr; return attr /* ; */])], + [ax_cv_PTHREAD_JOINABLE_ATTR=$ax_pthread_attr; break], + []) + done + ]) + AS_IF([test "x$ax_cv_PTHREAD_JOINABLE_ATTR" != "xunknown" && \ + test "x$ax_cv_PTHREAD_JOINABLE_ATTR" != "xPTHREAD_CREATE_JOINABLE" && \ + test "x$ax_pthread_joinable_attr_defined" != "xyes"], + [AC_DEFINE_UNQUOTED([PTHREAD_CREATE_JOINABLE], + [$ax_cv_PTHREAD_JOINABLE_ATTR], + [Define to necessary symbol if this constant + uses a non-standard name on your system.]) + ax_pthread_joinable_attr_defined=yes + ]) + + AC_CACHE_CHECK([whether more special flags are required for pthreads], + [ax_cv_PTHREAD_SPECIAL_FLAGS], + [ax_cv_PTHREAD_SPECIAL_FLAGS=no + case $target_os in + solaris*) + ax_cv_PTHREAD_SPECIAL_FLAGS="-D_POSIX_PTHREAD_SEMANTICS" + ;; + esac + ]) + AS_IF([test "x$ax_cv_PTHREAD_SPECIAL_FLAGS" != "xno" && \ + test "x$ax_pthread_special_flags_added" != "xyes"], + [PTHREAD_CFLAGS="$ax_cv_PTHREAD_SPECIAL_FLAGS $PTHREAD_CFLAGS" + ax_pthread_special_flags_added=yes]) + + AC_CACHE_CHECK([for PTHREAD_PRIO_INHERIT], + [ax_cv_PTHREAD_PRIO_INHERIT], + [AC_LINK_IFELSE([AC_LANG_PROGRAM([[#include ]], + [[int i = PTHREAD_PRIO_INHERIT; + return i;]])], + [ax_cv_PTHREAD_PRIO_INHERIT=yes], + [ax_cv_PTHREAD_PRIO_INHERIT=no]) + ]) + AS_IF([test "x$ax_cv_PTHREAD_PRIO_INHERIT" = "xyes" && \ + test "x$ax_pthread_prio_inherit_defined" != "xyes"], + [AC_DEFINE([HAVE_PTHREAD_PRIO_INHERIT], [1], [Have PTHREAD_PRIO_INHERIT.]) + ax_pthread_prio_inherit_defined=yes + ]) + + CFLAGS="$ax_pthread_save_CFLAGS" + LIBS="$ax_pthread_save_LIBS" + + # More AIX lossage: compile with *_r variant + if test "x$GCC" != "xyes"; then + case $target_os in + aix*) + AS_CASE(["x/$CC"], + [x*/c89|x*/c89_128|x*/c99|x*/c99_128|x*/cc|x*/cc128|x*/xlc|x*/xlc_v6|x*/xlc128|x*/xlc128_v6], + [#handle absolute path differently from PATH based program lookup + AS_CASE(["x$CC"], + [x/*], + [ + AS_IF([AS_EXECUTABLE_P([${CC}_r])],[PTHREAD_CC="${CC}_r"]) + AS_IF([test "x${CXX}" != "x"], [AS_IF([AS_EXECUTABLE_P([${CXX}_r])],[PTHREAD_CXX="${CXX}_r"])]) + ], + [ + AC_CHECK_PROGS([PTHREAD_CC],[${CC}_r],[$CC]) + AS_IF([test "x${CXX}" != "x"], [AC_CHECK_PROGS([PTHREAD_CXX],[${CXX}_r],[$CXX])]) + ] + ) + ]) + ;; + esac + fi +fi + +test -n "$PTHREAD_CC" || PTHREAD_CC="$CC" +test -n "$PTHREAD_CXX" || PTHREAD_CXX="$CXX" + +AC_SUBST([PTHREAD_LIBS]) +AC_SUBST([PTHREAD_CFLAGS]) +AC_SUBST([PTHREAD_CC]) +AC_SUBST([PTHREAD_CXX]) + +# Finally, execute ACTION-IF-FOUND/ACTION-IF-NOT-FOUND: +if test "x$ax_pthread_ok" = "xyes"; then + ifelse([$1],,[AC_DEFINE([HAVE_PTHREAD],[1],[Define if you have POSIX threads libraries and header files.])],[$1]) + : +else + ax_pthread_ok=no + $2 +fi +AC_LANG_POP +])dnl AX_PTHREAD diff --git a/3rdparty/freetype-2.13.2/builds/unix/config.guess b/3rdparty/freetype-2.13.2/builds/unix/config.guess new file mode 100644 index 000000000..b18721393 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/config.guess @@ -0,0 +1,1803 @@ +#! /bin/sh +# Attempt to guess a canonical system name. +# Copyright 1992-2023 Free Software Foundation, Inc. + +# shellcheck disable=SC2006,SC2268 # see below for rationale + +timestamp='2023-07-20' + +# This file is free software; you can redistribute it and/or modify it +# under the terms of the GNU General Public License as published by +# the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, see . +# +# As a special exception to the GNU General Public License, if you +# distribute this file as part of a program that contains a +# configuration script generated by Autoconf, you may include it under +# the same distribution terms that you use for the rest of that +# program. This Exception is an additional permission under section 7 +# of the GNU General Public License, version 3 ("GPLv3"). +# +# Originally written by Per Bothner; maintained since 2000 by Ben Elliston. +# +# You can get the latest version of this script from: +# https://git.savannah.gnu.org/cgit/config.git/plain/config.guess +# +# Please send patches to . + + +# The "shellcheck disable" line above the timestamp inhibits complaints +# about features and limitations of the classic Bourne shell that were +# superseded or lifted in POSIX. However, this script identifies a wide +# variety of pre-POSIX systems that do not have POSIX shells at all, and +# even some reasonably current systems (Solaris 10 as case-in-point) still +# have a pre-POSIX /bin/sh. + + +me=`echo "$0" | sed -e 's,.*/,,'` + +usage="\ +Usage: $0 [OPTION] + +Output the configuration name of the system '$me' is run on. + +Options: + -h, --help print this help, then exit + -t, --time-stamp print date of last modification, then exit + -v, --version print version number, then exit + +Report bugs and patches to ." + +version="\ +GNU config.guess ($timestamp) + +Originally written by Per Bothner. +Copyright 1992-2023 Free Software Foundation, Inc. + +This is free software; see the source for copying conditions. There is NO +warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." + +help=" +Try '$me --help' for more information." + +# Parse command line +while test $# -gt 0 ; do + case $1 in + --time-stamp | --time* | -t ) + echo "$timestamp" ; exit ;; + --version | -v ) + echo "$version" ; exit ;; + --help | --h* | -h ) + echo "$usage"; exit ;; + -- ) # Stop option processing + shift; break ;; + - ) # Use stdin as input. + break ;; + -* ) + echo "$me: invalid option $1$help" >&2 + exit 1 ;; + * ) + break ;; + esac +done + +if test $# != 0; then + echo "$me: too many arguments$help" >&2 + exit 1 +fi + +# Just in case it came from the environment. +GUESS= + +# CC_FOR_BUILD -- compiler used by this script. Note that the use of a +# compiler to aid in system detection is discouraged as it requires +# temporary files to be created and, as you can see below, it is a +# headache to deal with in a portable fashion. + +# Historically, 'CC_FOR_BUILD' used to be named 'HOST_CC'. We still +# use 'HOST_CC' if defined, but it is deprecated. + +# Portable tmp directory creation inspired by the Autoconf team. + +tmp= +# shellcheck disable=SC2172 +trap 'test -z "$tmp" || rm -fr "$tmp"' 0 1 2 13 15 + +set_cc_for_build() { + # prevent multiple calls if $tmp is already set + test "$tmp" && return 0 + : "${TMPDIR=/tmp}" + # shellcheck disable=SC2039,SC3028 + { tmp=`(umask 077 && mktemp -d "$TMPDIR/cgXXXXXX") 2>/dev/null` && test -n "$tmp" && test -d "$tmp" ; } || + { test -n "$RANDOM" && tmp=$TMPDIR/cg$$-$RANDOM && (umask 077 && mkdir "$tmp" 2>/dev/null) ; } || + { tmp=$TMPDIR/cg-$$ && (umask 077 && mkdir "$tmp" 2>/dev/null) && echo "Warning: creating insecure temp directory" >&2 ; } || + { echo "$me: cannot create a temporary directory in $TMPDIR" >&2 ; exit 1 ; } + dummy=$tmp/dummy + case ${CC_FOR_BUILD-},${HOST_CC-},${CC-} in + ,,) echo "int x;" > "$dummy.c" + for driver in cc gcc c89 c99 ; do + if ($driver -c -o "$dummy.o" "$dummy.c") >/dev/null 2>&1 ; then + CC_FOR_BUILD=$driver + break + fi + done + if test x"$CC_FOR_BUILD" = x ; then + CC_FOR_BUILD=no_compiler_found + fi + ;; + ,,*) CC_FOR_BUILD=$CC ;; + ,*,*) CC_FOR_BUILD=$HOST_CC ;; + esac +} + +# This is needed to find uname on a Pyramid OSx when run in the BSD universe. +# (ghazi@noc.rutgers.edu 1994-08-24) +if test -f /.attbin/uname ; then + PATH=$PATH:/.attbin ; export PATH +fi + +UNAME_MACHINE=`(uname -m) 2>/dev/null` || UNAME_MACHINE=unknown +UNAME_RELEASE=`(uname -r) 2>/dev/null` || UNAME_RELEASE=unknown +UNAME_SYSTEM=`(uname -s) 2>/dev/null` || UNAME_SYSTEM=unknown +UNAME_VERSION=`(uname -v) 2>/dev/null` || UNAME_VERSION=unknown + +case $UNAME_SYSTEM in +Linux|GNU|GNU/*) + LIBC=unknown + + set_cc_for_build + cat <<-EOF > "$dummy.c" + #include + #if defined(__UCLIBC__) + LIBC=uclibc + #elif defined(__dietlibc__) + LIBC=dietlibc + #elif defined(__GLIBC__) + LIBC=gnu + #else + #include + /* First heuristic to detect musl libc. */ + #ifdef __DEFINED_va_list + LIBC=musl + #endif + #endif + EOF + cc_set_libc=`$CC_FOR_BUILD -E "$dummy.c" 2>/dev/null | grep '^LIBC' | sed 's, ,,g'` + eval "$cc_set_libc" + + # Second heuristic to detect musl libc. + if [ "$LIBC" = unknown ] && + command -v ldd >/dev/null && + ldd --version 2>&1 | grep -q ^musl; then + LIBC=musl + fi + + # If the system lacks a compiler, then just pick glibc. + # We could probably try harder. + if [ "$LIBC" = unknown ]; then + LIBC=gnu + fi + ;; +esac + +# Note: order is significant - the case branches are not exclusive. + +case $UNAME_MACHINE:$UNAME_SYSTEM:$UNAME_RELEASE:$UNAME_VERSION in + *:NetBSD:*:*) + # NetBSD (nbsd) targets should (where applicable) match one or + # more of the tuples: *-*-netbsdelf*, *-*-netbsdaout*, + # *-*-netbsdecoff* and *-*-netbsd*. For targets that recently + # switched to ELF, *-*-netbsd* would select the old + # object file format. This provides both forward + # compatibility and a consistent mechanism for selecting the + # object file format. + # + # Note: NetBSD doesn't particularly care about the vendor + # portion of the name. We always set it to "unknown". + UNAME_MACHINE_ARCH=`(uname -p 2>/dev/null || \ + /sbin/sysctl -n hw.machine_arch 2>/dev/null || \ + /usr/sbin/sysctl -n hw.machine_arch 2>/dev/null || \ + echo unknown)` + case $UNAME_MACHINE_ARCH in + aarch64eb) machine=aarch64_be-unknown ;; + armeb) machine=armeb-unknown ;; + arm*) machine=arm-unknown ;; + sh3el) machine=shl-unknown ;; + sh3eb) machine=sh-unknown ;; + sh5el) machine=sh5le-unknown ;; + earmv*) + arch=`echo "$UNAME_MACHINE_ARCH" | sed -e 's,^e\(armv[0-9]\).*$,\1,'` + endian=`echo "$UNAME_MACHINE_ARCH" | sed -ne 's,^.*\(eb\)$,\1,p'` + machine=${arch}${endian}-unknown + ;; + *) machine=$UNAME_MACHINE_ARCH-unknown ;; + esac + # The Operating System including object format, if it has switched + # to ELF recently (or will in the future) and ABI. + case $UNAME_MACHINE_ARCH in + earm*) + os=netbsdelf + ;; + arm*|i386|m68k|ns32k|sh3*|sparc|vax) + set_cc_for_build + if echo __ELF__ | $CC_FOR_BUILD -E - 2>/dev/null \ + | grep -q __ELF__ + then + # Once all utilities can be ECOFF (netbsdecoff) or a.out (netbsdaout). + # Return netbsd for either. FIX? + os=netbsd + else + os=netbsdelf + fi + ;; + *) + os=netbsd + ;; + esac + # Determine ABI tags. + case $UNAME_MACHINE_ARCH in + earm*) + expr='s/^earmv[0-9]/-eabi/;s/eb$//' + abi=`echo "$UNAME_MACHINE_ARCH" | sed -e "$expr"` + ;; + esac + # The OS release + # Debian GNU/NetBSD machines have a different userland, and + # thus, need a distinct triplet. However, they do not need + # kernel version information, so it can be replaced with a + # suitable tag, in the style of linux-gnu. + case $UNAME_VERSION in + Debian*) + release='-gnu' + ;; + *) + release=`echo "$UNAME_RELEASE" | sed -e 's/[-_].*//' | cut -d. -f1,2` + ;; + esac + # Since CPU_TYPE-MANUFACTURER-KERNEL-OPERATING_SYSTEM: + # contains redundant information, the shorter form: + # CPU_TYPE-MANUFACTURER-OPERATING_SYSTEM is used. + GUESS=$machine-${os}${release}${abi-} + ;; + *:Bitrig:*:*) + UNAME_MACHINE_ARCH=`arch | sed 's/Bitrig.//'` + GUESS=$UNAME_MACHINE_ARCH-unknown-bitrig$UNAME_RELEASE + ;; + *:OpenBSD:*:*) + UNAME_MACHINE_ARCH=`arch | sed 's/OpenBSD.//'` + GUESS=$UNAME_MACHINE_ARCH-unknown-openbsd$UNAME_RELEASE + ;; + *:SecBSD:*:*) + UNAME_MACHINE_ARCH=`arch | sed 's/SecBSD.//'` + GUESS=$UNAME_MACHINE_ARCH-unknown-secbsd$UNAME_RELEASE + ;; + *:LibertyBSD:*:*) + UNAME_MACHINE_ARCH=`arch | sed 's/^.*BSD\.//'` + GUESS=$UNAME_MACHINE_ARCH-unknown-libertybsd$UNAME_RELEASE + ;; + *:MidnightBSD:*:*) + GUESS=$UNAME_MACHINE-unknown-midnightbsd$UNAME_RELEASE + ;; + *:ekkoBSD:*:*) + GUESS=$UNAME_MACHINE-unknown-ekkobsd$UNAME_RELEASE + ;; + *:SolidBSD:*:*) + GUESS=$UNAME_MACHINE-unknown-solidbsd$UNAME_RELEASE + ;; + *:OS108:*:*) + GUESS=$UNAME_MACHINE-unknown-os108_$UNAME_RELEASE + ;; + macppc:MirBSD:*:*) + GUESS=powerpc-unknown-mirbsd$UNAME_RELEASE + ;; + *:MirBSD:*:*) + GUESS=$UNAME_MACHINE-unknown-mirbsd$UNAME_RELEASE + ;; + *:Sortix:*:*) + GUESS=$UNAME_MACHINE-unknown-sortix + ;; + *:Twizzler:*:*) + GUESS=$UNAME_MACHINE-unknown-twizzler + ;; + *:Redox:*:*) + GUESS=$UNAME_MACHINE-unknown-redox + ;; + mips:OSF1:*.*) + GUESS=mips-dec-osf1 + ;; + alpha:OSF1:*:*) + # Reset EXIT trap before exiting to avoid spurious non-zero exit code. + trap '' 0 + case $UNAME_RELEASE in + *4.0) + UNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $3}'` + ;; + *5.*) + UNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $4}'` + ;; + esac + # According to Compaq, /usr/sbin/psrinfo has been available on + # OSF/1 and Tru64 systems produced since 1995. I hope that + # covers most systems running today. This code pipes the CPU + # types through head -n 1, so we only detect the type of CPU 0. + ALPHA_CPU_TYPE=`/usr/sbin/psrinfo -v | sed -n -e 's/^ The alpha \(.*\) processor.*$/\1/p' | head -n 1` + case $ALPHA_CPU_TYPE in + "EV4 (21064)") + UNAME_MACHINE=alpha ;; + "EV4.5 (21064)") + UNAME_MACHINE=alpha ;; + "LCA4 (21066/21068)") + UNAME_MACHINE=alpha ;; + "EV5 (21164)") + UNAME_MACHINE=alphaev5 ;; + "EV5.6 (21164A)") + UNAME_MACHINE=alphaev56 ;; + "EV5.6 (21164PC)") + UNAME_MACHINE=alphapca56 ;; + "EV5.7 (21164PC)") + UNAME_MACHINE=alphapca57 ;; + "EV6 (21264)") + UNAME_MACHINE=alphaev6 ;; + "EV6.7 (21264A)") + UNAME_MACHINE=alphaev67 ;; + "EV6.8CB (21264C)") + UNAME_MACHINE=alphaev68 ;; + "EV6.8AL (21264B)") + UNAME_MACHINE=alphaev68 ;; + "EV6.8CX (21264D)") + UNAME_MACHINE=alphaev68 ;; + "EV6.9A (21264/EV69A)") + UNAME_MACHINE=alphaev69 ;; + "EV7 (21364)") + UNAME_MACHINE=alphaev7 ;; + "EV7.9 (21364A)") + UNAME_MACHINE=alphaev79 ;; + esac + # A Pn.n version is a patched version. + # A Vn.n version is a released version. + # A Tn.n version is a released field test version. + # A Xn.n version is an unreleased experimental baselevel. + # 1.2 uses "1.2" for uname -r. + OSF_REL=`echo "$UNAME_RELEASE" | sed -e 's/^[PVTX]//' | tr ABCDEFGHIJKLMNOPQRSTUVWXYZ abcdefghijklmnopqrstuvwxyz` + GUESS=$UNAME_MACHINE-dec-osf$OSF_REL + ;; + Amiga*:UNIX_System_V:4.0:*) + GUESS=m68k-unknown-sysv4 + ;; + *:[Aa]miga[Oo][Ss]:*:*) + GUESS=$UNAME_MACHINE-unknown-amigaos + ;; + *:[Mm]orph[Oo][Ss]:*:*) + GUESS=$UNAME_MACHINE-unknown-morphos + ;; + *:OS/390:*:*) + GUESS=i370-ibm-openedition + ;; + *:z/VM:*:*) + GUESS=s390-ibm-zvmoe + ;; + *:OS400:*:*) + GUESS=powerpc-ibm-os400 + ;; + arm:RISC*:1.[012]*:*|arm:riscix:1.[012]*:*) + GUESS=arm-acorn-riscix$UNAME_RELEASE + ;; + arm*:riscos:*:*|arm*:RISCOS:*:*) + GUESS=arm-unknown-riscos + ;; + SR2?01:HI-UX/MPP:*:* | SR8000:HI-UX/MPP:*:*) + GUESS=hppa1.1-hitachi-hiuxmpp + ;; + Pyramid*:OSx*:*:* | MIS*:OSx*:*:* | MIS*:SMP_DC-OSx*:*:*) + # akee@wpdis03.wpafb.af.mil (Earle F. Ake) contributed MIS and NILE. + case `(/bin/universe) 2>/dev/null` in + att) GUESS=pyramid-pyramid-sysv3 ;; + *) GUESS=pyramid-pyramid-bsd ;; + esac + ;; + NILE*:*:*:dcosx) + GUESS=pyramid-pyramid-svr4 + ;; + DRS?6000:unix:4.0:6*) + GUESS=sparc-icl-nx6 + ;; + DRS?6000:UNIX_SV:4.2*:7* | DRS?6000:isis:4.2*:7*) + case `/usr/bin/uname -p` in + sparc) GUESS=sparc-icl-nx7 ;; + esac + ;; + s390x:SunOS:*:*) + SUN_REL=`echo "$UNAME_RELEASE" | sed -e 's/[^.]*//'` + GUESS=$UNAME_MACHINE-ibm-solaris2$SUN_REL + ;; + sun4H:SunOS:5.*:*) + SUN_REL=`echo "$UNAME_RELEASE" | sed -e 's/[^.]*//'` + GUESS=sparc-hal-solaris2$SUN_REL + ;; + sun4*:SunOS:5.*:* | tadpole*:SunOS:5.*:*) + SUN_REL=`echo "$UNAME_RELEASE" | sed -e 's/[^.]*//'` + GUESS=sparc-sun-solaris2$SUN_REL + ;; + i86pc:AuroraUX:5.*:* | i86xen:AuroraUX:5.*:*) + GUESS=i386-pc-auroraux$UNAME_RELEASE + ;; + i86pc:SunOS:5.*:* | i86xen:SunOS:5.*:*) + set_cc_for_build + SUN_ARCH=i386 + # If there is a compiler, see if it is configured for 64-bit objects. + # Note that the Sun cc does not turn __LP64__ into 1 like gcc does. + # This test works for both compilers. + if test "$CC_FOR_BUILD" != no_compiler_found; then + if (echo '#ifdef __amd64'; echo IS_64BIT_ARCH; echo '#endif') | \ + (CCOPTS="" $CC_FOR_BUILD -m64 -E - 2>/dev/null) | \ + grep IS_64BIT_ARCH >/dev/null + then + SUN_ARCH=x86_64 + fi + fi + SUN_REL=`echo "$UNAME_RELEASE" | sed -e 's/[^.]*//'` + GUESS=$SUN_ARCH-pc-solaris2$SUN_REL + ;; + sun4*:SunOS:6*:*) + # According to config.sub, this is the proper way to canonicalize + # SunOS6. Hard to guess exactly what SunOS6 will be like, but + # it's likely to be more like Solaris than SunOS4. + SUN_REL=`echo "$UNAME_RELEASE" | sed -e 's/[^.]*//'` + GUESS=sparc-sun-solaris3$SUN_REL + ;; + sun4*:SunOS:*:*) + case `/usr/bin/arch -k` in + Series*|S4*) + UNAME_RELEASE=`uname -v` + ;; + esac + # Japanese Language versions have a version number like '4.1.3-JL'. + SUN_REL=`echo "$UNAME_RELEASE" | sed -e 's/-/_/'` + GUESS=sparc-sun-sunos$SUN_REL + ;; + sun3*:SunOS:*:*) + GUESS=m68k-sun-sunos$UNAME_RELEASE + ;; + sun*:*:4.2BSD:*) + UNAME_RELEASE=`(sed 1q /etc/motd | awk '{print substr($5,1,3)}') 2>/dev/null` + test "x$UNAME_RELEASE" = x && UNAME_RELEASE=3 + case `/bin/arch` in + sun3) + GUESS=m68k-sun-sunos$UNAME_RELEASE + ;; + sun4) + GUESS=sparc-sun-sunos$UNAME_RELEASE + ;; + esac + ;; + aushp:SunOS:*:*) + GUESS=sparc-auspex-sunos$UNAME_RELEASE + ;; + # The situation for MiNT is a little confusing. The machine name + # can be virtually everything (everything which is not + # "atarist" or "atariste" at least should have a processor + # > m68000). The system name ranges from "MiNT" over "FreeMiNT" + # to the lowercase version "mint" (or "freemint"). Finally + # the system name "TOS" denotes a system which is actually not + # MiNT. But MiNT is downward compatible to TOS, so this should + # be no problem. + atarist[e]:*MiNT:*:* | atarist[e]:*mint:*:* | atarist[e]:*TOS:*:*) + GUESS=m68k-atari-mint$UNAME_RELEASE + ;; + atari*:*MiNT:*:* | atari*:*mint:*:* | atarist[e]:*TOS:*:*) + GUESS=m68k-atari-mint$UNAME_RELEASE + ;; + *falcon*:*MiNT:*:* | *falcon*:*mint:*:* | *falcon*:*TOS:*:*) + GUESS=m68k-atari-mint$UNAME_RELEASE + ;; + milan*:*MiNT:*:* | milan*:*mint:*:* | *milan*:*TOS:*:*) + GUESS=m68k-milan-mint$UNAME_RELEASE + ;; + hades*:*MiNT:*:* | hades*:*mint:*:* | *hades*:*TOS:*:*) + GUESS=m68k-hades-mint$UNAME_RELEASE + ;; + *:*MiNT:*:* | *:*mint:*:* | *:*TOS:*:*) + GUESS=m68k-unknown-mint$UNAME_RELEASE + ;; + m68k:machten:*:*) + GUESS=m68k-apple-machten$UNAME_RELEASE + ;; + powerpc:machten:*:*) + GUESS=powerpc-apple-machten$UNAME_RELEASE + ;; + RISC*:Mach:*:*) + GUESS=mips-dec-mach_bsd4.3 + ;; + RISC*:ULTRIX:*:*) + GUESS=mips-dec-ultrix$UNAME_RELEASE + ;; + VAX*:ULTRIX*:*:*) + GUESS=vax-dec-ultrix$UNAME_RELEASE + ;; + 2020:CLIX:*:* | 2430:CLIX:*:*) + GUESS=clipper-intergraph-clix$UNAME_RELEASE + ;; + mips:*:*:UMIPS | mips:*:*:RISCos) + set_cc_for_build + sed 's/^ //' << EOF > "$dummy.c" +#ifdef __cplusplus +#include /* for printf() prototype */ + int main (int argc, char *argv[]) { +#else + int main (argc, argv) int argc; char *argv[]; { +#endif + #if defined (host_mips) && defined (MIPSEB) + #if defined (SYSTYPE_SYSV) + printf ("mips-mips-riscos%ssysv\\n", argv[1]); exit (0); + #endif + #if defined (SYSTYPE_SVR4) + printf ("mips-mips-riscos%ssvr4\\n", argv[1]); exit (0); + #endif + #if defined (SYSTYPE_BSD43) || defined(SYSTYPE_BSD) + printf ("mips-mips-riscos%sbsd\\n", argv[1]); exit (0); + #endif + #endif + exit (-1); + } +EOF + $CC_FOR_BUILD -o "$dummy" "$dummy.c" && + dummyarg=`echo "$UNAME_RELEASE" | sed -n 's/\([0-9]*\).*/\1/p'` && + SYSTEM_NAME=`"$dummy" "$dummyarg"` && + { echo "$SYSTEM_NAME"; exit; } + GUESS=mips-mips-riscos$UNAME_RELEASE + ;; + Motorola:PowerMAX_OS:*:*) + GUESS=powerpc-motorola-powermax + ;; + Motorola:*:4.3:PL8-*) + GUESS=powerpc-harris-powermax + ;; + Night_Hawk:*:*:PowerMAX_OS | Synergy:PowerMAX_OS:*:*) + GUESS=powerpc-harris-powermax + ;; + Night_Hawk:Power_UNIX:*:*) + GUESS=powerpc-harris-powerunix + ;; + m88k:CX/UX:7*:*) + GUESS=m88k-harris-cxux7 + ;; + m88k:*:4*:R4*) + GUESS=m88k-motorola-sysv4 + ;; + m88k:*:3*:R3*) + GUESS=m88k-motorola-sysv3 + ;; + AViiON:dgux:*:*) + # DG/UX returns AViiON for all architectures + UNAME_PROCESSOR=`/usr/bin/uname -p` + if test "$UNAME_PROCESSOR" = mc88100 || test "$UNAME_PROCESSOR" = mc88110 + then + if test "$TARGET_BINARY_INTERFACE"x = m88kdguxelfx || \ + test "$TARGET_BINARY_INTERFACE"x = x + then + GUESS=m88k-dg-dgux$UNAME_RELEASE + else + GUESS=m88k-dg-dguxbcs$UNAME_RELEASE + fi + else + GUESS=i586-dg-dgux$UNAME_RELEASE + fi + ;; + M88*:DolphinOS:*:*) # DolphinOS (SVR3) + GUESS=m88k-dolphin-sysv3 + ;; + M88*:*:R3*:*) + # Delta 88k system running SVR3 + GUESS=m88k-motorola-sysv3 + ;; + XD88*:*:*:*) # Tektronix XD88 system running UTekV (SVR3) + GUESS=m88k-tektronix-sysv3 + ;; + Tek43[0-9][0-9]:UTek:*:*) # Tektronix 4300 system running UTek (BSD) + GUESS=m68k-tektronix-bsd + ;; + *:IRIX*:*:*) + IRIX_REL=`echo "$UNAME_RELEASE" | sed -e 's/-/_/g'` + GUESS=mips-sgi-irix$IRIX_REL + ;; + ????????:AIX?:[12].1:2) # AIX 2.2.1 or AIX 2.1.1 is RT/PC AIX. + GUESS=romp-ibm-aix # uname -m gives an 8 hex-code CPU id + ;; # Note that: echo "'`uname -s`'" gives 'AIX ' + i*86:AIX:*:*) + GUESS=i386-ibm-aix + ;; + ia64:AIX:*:*) + if test -x /usr/bin/oslevel ; then + IBM_REV=`/usr/bin/oslevel` + else + IBM_REV=$UNAME_VERSION.$UNAME_RELEASE + fi + GUESS=$UNAME_MACHINE-ibm-aix$IBM_REV + ;; + *:AIX:2:3) + if grep bos325 /usr/include/stdio.h >/dev/null 2>&1; then + set_cc_for_build + sed 's/^ //' << EOF > "$dummy.c" + #include + + main() + { + if (!__power_pc()) + exit(1); + puts("powerpc-ibm-aix3.2.5"); + exit(0); + } +EOF + if $CC_FOR_BUILD -o "$dummy" "$dummy.c" && SYSTEM_NAME=`"$dummy"` + then + GUESS=$SYSTEM_NAME + else + GUESS=rs6000-ibm-aix3.2.5 + fi + elif grep bos324 /usr/include/stdio.h >/dev/null 2>&1; then + GUESS=rs6000-ibm-aix3.2.4 + else + GUESS=rs6000-ibm-aix3.2 + fi + ;; + *:AIX:*:[4567]) + IBM_CPU_ID=`/usr/sbin/lsdev -C -c processor -S available | sed 1q | awk '{ print $1 }'` + if /usr/sbin/lsattr -El "$IBM_CPU_ID" | grep ' POWER' >/dev/null 2>&1; then + IBM_ARCH=rs6000 + else + IBM_ARCH=powerpc + fi + if test -x /usr/bin/lslpp ; then + IBM_REV=`/usr/bin/lslpp -Lqc bos.rte.libc | \ + awk -F: '{ print $3 }' | sed s/[0-9]*$/0/` + else + IBM_REV=$UNAME_VERSION.$UNAME_RELEASE + fi + GUESS=$IBM_ARCH-ibm-aix$IBM_REV + ;; + *:AIX:*:*) + GUESS=rs6000-ibm-aix + ;; + ibmrt:4.4BSD:*|romp-ibm:4.4BSD:*) + GUESS=romp-ibm-bsd4.4 + ;; + ibmrt:*BSD:*|romp-ibm:BSD:*) # covers RT/PC BSD and + GUESS=romp-ibm-bsd$UNAME_RELEASE # 4.3 with uname added to + ;; # report: romp-ibm BSD 4.3 + *:BOSX:*:*) + GUESS=rs6000-bull-bosx + ;; + DPX/2?00:B.O.S.:*:*) + GUESS=m68k-bull-sysv3 + ;; + 9000/[34]??:4.3bsd:1.*:*) + GUESS=m68k-hp-bsd + ;; + hp300:4.4BSD:*:* | 9000/[34]??:4.3bsd:2.*:*) + GUESS=m68k-hp-bsd4.4 + ;; + 9000/[34678]??:HP-UX:*:*) + HPUX_REV=`echo "$UNAME_RELEASE" | sed -e 's/[^.]*.[0B]*//'` + case $UNAME_MACHINE in + 9000/31?) HP_ARCH=m68000 ;; + 9000/[34]??) HP_ARCH=m68k ;; + 9000/[678][0-9][0-9]) + if test -x /usr/bin/getconf; then + sc_cpu_version=`/usr/bin/getconf SC_CPU_VERSION 2>/dev/null` + sc_kernel_bits=`/usr/bin/getconf SC_KERNEL_BITS 2>/dev/null` + case $sc_cpu_version in + 523) HP_ARCH=hppa1.0 ;; # CPU_PA_RISC1_0 + 528) HP_ARCH=hppa1.1 ;; # CPU_PA_RISC1_1 + 532) # CPU_PA_RISC2_0 + case $sc_kernel_bits in + 32) HP_ARCH=hppa2.0n ;; + 64) HP_ARCH=hppa2.0w ;; + '') HP_ARCH=hppa2.0 ;; # HP-UX 10.20 + esac ;; + esac + fi + if test "$HP_ARCH" = ""; then + set_cc_for_build + sed 's/^ //' << EOF > "$dummy.c" + + #define _HPUX_SOURCE + #include + #include + + int main () + { + #if defined(_SC_KERNEL_BITS) + long bits = sysconf(_SC_KERNEL_BITS); + #endif + long cpu = sysconf (_SC_CPU_VERSION); + + switch (cpu) + { + case CPU_PA_RISC1_0: puts ("hppa1.0"); break; + case CPU_PA_RISC1_1: puts ("hppa1.1"); break; + case CPU_PA_RISC2_0: + #if defined(_SC_KERNEL_BITS) + switch (bits) + { + case 64: puts ("hppa2.0w"); break; + case 32: puts ("hppa2.0n"); break; + default: puts ("hppa2.0"); break; + } break; + #else /* !defined(_SC_KERNEL_BITS) */ + puts ("hppa2.0"); break; + #endif + default: puts ("hppa1.0"); break; + } + exit (0); + } +EOF + (CCOPTS="" $CC_FOR_BUILD -o "$dummy" "$dummy.c" 2>/dev/null) && HP_ARCH=`"$dummy"` + test -z "$HP_ARCH" && HP_ARCH=hppa + fi ;; + esac + if test "$HP_ARCH" = hppa2.0w + then + set_cc_for_build + + # hppa2.0w-hp-hpux* has a 64-bit kernel and a compiler generating + # 32-bit code. hppa64-hp-hpux* has the same kernel and a compiler + # generating 64-bit code. GNU and HP use different nomenclature: + # + # $ CC_FOR_BUILD=cc ./config.guess + # => hppa2.0w-hp-hpux11.23 + # $ CC_FOR_BUILD="cc +DA2.0w" ./config.guess + # => hppa64-hp-hpux11.23 + + if echo __LP64__ | (CCOPTS="" $CC_FOR_BUILD -E - 2>/dev/null) | + grep -q __LP64__ + then + HP_ARCH=hppa2.0w + else + HP_ARCH=hppa64 + fi + fi + GUESS=$HP_ARCH-hp-hpux$HPUX_REV + ;; + ia64:HP-UX:*:*) + HPUX_REV=`echo "$UNAME_RELEASE" | sed -e 's/[^.]*.[0B]*//'` + GUESS=ia64-hp-hpux$HPUX_REV + ;; + 3050*:HI-UX:*:*) + set_cc_for_build + sed 's/^ //' << EOF > "$dummy.c" + #include + int + main () + { + long cpu = sysconf (_SC_CPU_VERSION); + /* The order matters, because CPU_IS_HP_MC68K erroneously returns + true for CPU_PA_RISC1_0. CPU_IS_PA_RISC returns correct + results, however. */ + if (CPU_IS_PA_RISC (cpu)) + { + switch (cpu) + { + case CPU_PA_RISC1_0: puts ("hppa1.0-hitachi-hiuxwe2"); break; + case CPU_PA_RISC1_1: puts ("hppa1.1-hitachi-hiuxwe2"); break; + case CPU_PA_RISC2_0: puts ("hppa2.0-hitachi-hiuxwe2"); break; + default: puts ("hppa-hitachi-hiuxwe2"); break; + } + } + else if (CPU_IS_HP_MC68K (cpu)) + puts ("m68k-hitachi-hiuxwe2"); + else puts ("unknown-hitachi-hiuxwe2"); + exit (0); + } +EOF + $CC_FOR_BUILD -o "$dummy" "$dummy.c" && SYSTEM_NAME=`"$dummy"` && + { echo "$SYSTEM_NAME"; exit; } + GUESS=unknown-hitachi-hiuxwe2 + ;; + 9000/7??:4.3bsd:*:* | 9000/8?[79]:4.3bsd:*:*) + GUESS=hppa1.1-hp-bsd + ;; + 9000/8??:4.3bsd:*:*) + GUESS=hppa1.0-hp-bsd + ;; + *9??*:MPE/iX:*:* | *3000*:MPE/iX:*:*) + GUESS=hppa1.0-hp-mpeix + ;; + hp7??:OSF1:*:* | hp8?[79]:OSF1:*:*) + GUESS=hppa1.1-hp-osf + ;; + hp8??:OSF1:*:*) + GUESS=hppa1.0-hp-osf + ;; + i*86:OSF1:*:*) + if test -x /usr/sbin/sysversion ; then + GUESS=$UNAME_MACHINE-unknown-osf1mk + else + GUESS=$UNAME_MACHINE-unknown-osf1 + fi + ;; + parisc*:Lites*:*:*) + GUESS=hppa1.1-hp-lites + ;; + C1*:ConvexOS:*:* | convex:ConvexOS:C1*:*) + GUESS=c1-convex-bsd + ;; + C2*:ConvexOS:*:* | convex:ConvexOS:C2*:*) + if getsysinfo -f scalar_acc + then echo c32-convex-bsd + else echo c2-convex-bsd + fi + exit ;; + C34*:ConvexOS:*:* | convex:ConvexOS:C34*:*) + GUESS=c34-convex-bsd + ;; + C38*:ConvexOS:*:* | convex:ConvexOS:C38*:*) + GUESS=c38-convex-bsd + ;; + C4*:ConvexOS:*:* | convex:ConvexOS:C4*:*) + GUESS=c4-convex-bsd + ;; + CRAY*Y-MP:*:*:*) + CRAY_REL=`echo "$UNAME_RELEASE" | sed -e 's/\.[^.]*$/.X/'` + GUESS=ymp-cray-unicos$CRAY_REL + ;; + CRAY*[A-Z]90:*:*:*) + echo "$UNAME_MACHINE"-cray-unicos"$UNAME_RELEASE" \ + | sed -e 's/CRAY.*\([A-Z]90\)/\1/' \ + -e y/ABCDEFGHIJKLMNOPQRSTUVWXYZ/abcdefghijklmnopqrstuvwxyz/ \ + -e 's/\.[^.]*$/.X/' + exit ;; + CRAY*TS:*:*:*) + CRAY_REL=`echo "$UNAME_RELEASE" | sed -e 's/\.[^.]*$/.X/'` + GUESS=t90-cray-unicos$CRAY_REL + ;; + CRAY*T3E:*:*:*) + CRAY_REL=`echo "$UNAME_RELEASE" | sed -e 's/\.[^.]*$/.X/'` + GUESS=alphaev5-cray-unicosmk$CRAY_REL + ;; + CRAY*SV1:*:*:*) + CRAY_REL=`echo "$UNAME_RELEASE" | sed -e 's/\.[^.]*$/.X/'` + GUESS=sv1-cray-unicos$CRAY_REL + ;; + *:UNICOS/mp:*:*) + CRAY_REL=`echo "$UNAME_RELEASE" | sed -e 's/\.[^.]*$/.X/'` + GUESS=craynv-cray-unicosmp$CRAY_REL + ;; + F30[01]:UNIX_System_V:*:* | F700:UNIX_System_V:*:*) + FUJITSU_PROC=`uname -m | tr ABCDEFGHIJKLMNOPQRSTUVWXYZ abcdefghijklmnopqrstuvwxyz` + FUJITSU_SYS=`uname -p | tr ABCDEFGHIJKLMNOPQRSTUVWXYZ abcdefghijklmnopqrstuvwxyz | sed -e 's/\///'` + FUJITSU_REL=`echo "$UNAME_RELEASE" | sed -e 's/ /_/'` + GUESS=${FUJITSU_PROC}-fujitsu-${FUJITSU_SYS}${FUJITSU_REL} + ;; + 5000:UNIX_System_V:4.*:*) + FUJITSU_SYS=`uname -p | tr ABCDEFGHIJKLMNOPQRSTUVWXYZ abcdefghijklmnopqrstuvwxyz | sed -e 's/\///'` + FUJITSU_REL=`echo "$UNAME_RELEASE" | tr ABCDEFGHIJKLMNOPQRSTUVWXYZ abcdefghijklmnopqrstuvwxyz | sed -e 's/ /_/'` + GUESS=sparc-fujitsu-${FUJITSU_SYS}${FUJITSU_REL} + ;; + i*86:BSD/386:*:* | i*86:BSD/OS:*:* | *:Ascend\ Embedded/OS:*:*) + GUESS=$UNAME_MACHINE-pc-bsdi$UNAME_RELEASE + ;; + sparc*:BSD/OS:*:*) + GUESS=sparc-unknown-bsdi$UNAME_RELEASE + ;; + *:BSD/OS:*:*) + GUESS=$UNAME_MACHINE-unknown-bsdi$UNAME_RELEASE + ;; + arm:FreeBSD:*:*) + UNAME_PROCESSOR=`uname -p` + set_cc_for_build + if echo __ARM_PCS_VFP | $CC_FOR_BUILD -E - 2>/dev/null \ + | grep -q __ARM_PCS_VFP + then + FREEBSD_REL=`echo "$UNAME_RELEASE" | sed -e 's/[-(].*//'` + GUESS=$UNAME_PROCESSOR-unknown-freebsd$FREEBSD_REL-gnueabi + else + FREEBSD_REL=`echo "$UNAME_RELEASE" | sed -e 's/[-(].*//'` + GUESS=$UNAME_PROCESSOR-unknown-freebsd$FREEBSD_REL-gnueabihf + fi + ;; + *:FreeBSD:*:*) + UNAME_PROCESSOR=`/usr/bin/uname -p` + case $UNAME_PROCESSOR in + amd64) + UNAME_PROCESSOR=x86_64 ;; + i386) + UNAME_PROCESSOR=i586 ;; + esac + FREEBSD_REL=`echo "$UNAME_RELEASE" | sed -e 's/[-(].*//'` + GUESS=$UNAME_PROCESSOR-unknown-freebsd$FREEBSD_REL + ;; + i*:CYGWIN*:*) + GUESS=$UNAME_MACHINE-pc-cygwin + ;; + *:MINGW64*:*) + GUESS=$UNAME_MACHINE-pc-mingw64 + ;; + *:MINGW*:*) + GUESS=$UNAME_MACHINE-pc-mingw32 + ;; + *:MSYS*:*) + GUESS=$UNAME_MACHINE-pc-msys + ;; + i*:PW*:*) + GUESS=$UNAME_MACHINE-pc-pw32 + ;; + *:SerenityOS:*:*) + GUESS=$UNAME_MACHINE-pc-serenity + ;; + *:Interix*:*) + case $UNAME_MACHINE in + x86) + GUESS=i586-pc-interix$UNAME_RELEASE + ;; + authenticamd | genuineintel | EM64T) + GUESS=x86_64-unknown-interix$UNAME_RELEASE + ;; + IA64) + GUESS=ia64-unknown-interix$UNAME_RELEASE + ;; + esac ;; + i*:UWIN*:*) + GUESS=$UNAME_MACHINE-pc-uwin + ;; + amd64:CYGWIN*:*:* | x86_64:CYGWIN*:*:*) + GUESS=x86_64-pc-cygwin + ;; + prep*:SunOS:5.*:*) + SUN_REL=`echo "$UNAME_RELEASE" | sed -e 's/[^.]*//'` + GUESS=powerpcle-unknown-solaris2$SUN_REL + ;; + *:GNU:*:*) + # the GNU system + GNU_ARCH=`echo "$UNAME_MACHINE" | sed -e 's,[-/].*$,,'` + GNU_REL=`echo "$UNAME_RELEASE" | sed -e 's,/.*$,,'` + GUESS=$GNU_ARCH-unknown-$LIBC$GNU_REL + ;; + *:GNU/*:*:*) + # other systems with GNU libc and userland + GNU_SYS=`echo "$UNAME_SYSTEM" | sed 's,^[^/]*/,,' | tr "[:upper:]" "[:lower:]"` + GNU_REL=`echo "$UNAME_RELEASE" | sed -e 's/[-(].*//'` + GUESS=$UNAME_MACHINE-unknown-$GNU_SYS$GNU_REL-$LIBC + ;; + x86_64:[Mm]anagarm:*:*|i?86:[Mm]anagarm:*:*) + GUESS="$UNAME_MACHINE-pc-managarm-mlibc" + ;; + *:[Mm]anagarm:*:*) + GUESS="$UNAME_MACHINE-unknown-managarm-mlibc" + ;; + *:Minix:*:*) + GUESS=$UNAME_MACHINE-unknown-minix + ;; + aarch64:Linux:*:*) + set_cc_for_build + CPU=$UNAME_MACHINE + LIBCABI=$LIBC + if test "$CC_FOR_BUILD" != no_compiler_found; then + ABI=64 + sed 's/^ //' << EOF > "$dummy.c" + #ifdef __ARM_EABI__ + #ifdef __ARM_PCS_VFP + ABI=eabihf + #else + ABI=eabi + #endif + #endif +EOF + cc_set_abi=`$CC_FOR_BUILD -E "$dummy.c" 2>/dev/null | grep '^ABI' | sed 's, ,,g'` + eval "$cc_set_abi" + case $ABI in + eabi | eabihf) CPU=armv8l; LIBCABI=$LIBC$ABI ;; + esac + fi + GUESS=$CPU-unknown-linux-$LIBCABI + ;; + aarch64_be:Linux:*:*) + UNAME_MACHINE=aarch64_be + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + alpha:Linux:*:*) + case `sed -n '/^cpu model/s/^.*: \(.*\)/\1/p' /proc/cpuinfo 2>/dev/null` in + EV5) UNAME_MACHINE=alphaev5 ;; + EV56) UNAME_MACHINE=alphaev56 ;; + PCA56) UNAME_MACHINE=alphapca56 ;; + PCA57) UNAME_MACHINE=alphapca56 ;; + EV6) UNAME_MACHINE=alphaev6 ;; + EV67) UNAME_MACHINE=alphaev67 ;; + EV68*) UNAME_MACHINE=alphaev68 ;; + esac + objdump --private-headers /bin/sh | grep -q ld.so.1 + if test "$?" = 0 ; then LIBC=gnulibc1 ; fi + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + arc:Linux:*:* | arceb:Linux:*:* | arc32:Linux:*:* | arc64:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + arm*:Linux:*:*) + set_cc_for_build + if echo __ARM_EABI__ | $CC_FOR_BUILD -E - 2>/dev/null \ + | grep -q __ARM_EABI__ + then + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + else + if echo __ARM_PCS_VFP | $CC_FOR_BUILD -E - 2>/dev/null \ + | grep -q __ARM_PCS_VFP + then + GUESS=$UNAME_MACHINE-unknown-linux-${LIBC}eabi + else + GUESS=$UNAME_MACHINE-unknown-linux-${LIBC}eabihf + fi + fi + ;; + avr32*:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + cris:Linux:*:*) + GUESS=$UNAME_MACHINE-axis-linux-$LIBC + ;; + crisv32:Linux:*:*) + GUESS=$UNAME_MACHINE-axis-linux-$LIBC + ;; + e2k:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + frv:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + hexagon:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + i*86:Linux:*:*) + GUESS=$UNAME_MACHINE-pc-linux-$LIBC + ;; + ia64:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + k1om:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + kvx:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + kvx:cos:*:*) + GUESS=$UNAME_MACHINE-unknown-cos + ;; + kvx:mbr:*:*) + GUESS=$UNAME_MACHINE-unknown-mbr + ;; + loongarch32:Linux:*:* | loongarch64:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + m32r*:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + m68*:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + mips:Linux:*:* | mips64:Linux:*:*) + set_cc_for_build + IS_GLIBC=0 + test x"${LIBC}" = xgnu && IS_GLIBC=1 + sed 's/^ //' << EOF > "$dummy.c" + #undef CPU + #undef mips + #undef mipsel + #undef mips64 + #undef mips64el + #if ${IS_GLIBC} && defined(_ABI64) + LIBCABI=gnuabi64 + #else + #if ${IS_GLIBC} && defined(_ABIN32) + LIBCABI=gnuabin32 + #else + LIBCABI=${LIBC} + #endif + #endif + + #if ${IS_GLIBC} && defined(__mips64) && defined(__mips_isa_rev) && __mips_isa_rev>=6 + CPU=mipsisa64r6 + #else + #if ${IS_GLIBC} && !defined(__mips64) && defined(__mips_isa_rev) && __mips_isa_rev>=6 + CPU=mipsisa32r6 + #else + #if defined(__mips64) + CPU=mips64 + #else + CPU=mips + #endif + #endif + #endif + + #if defined(__MIPSEL__) || defined(__MIPSEL) || defined(_MIPSEL) || defined(MIPSEL) + MIPS_ENDIAN=el + #else + #if defined(__MIPSEB__) || defined(__MIPSEB) || defined(_MIPSEB) || defined(MIPSEB) + MIPS_ENDIAN= + #else + MIPS_ENDIAN= + #endif + #endif +EOF + cc_set_vars=`$CC_FOR_BUILD -E "$dummy.c" 2>/dev/null | grep '^CPU\|^MIPS_ENDIAN\|^LIBCABI'` + eval "$cc_set_vars" + test "x$CPU" != x && { echo "$CPU${MIPS_ENDIAN}-unknown-linux-$LIBCABI"; exit; } + ;; + mips64el:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + openrisc*:Linux:*:*) + GUESS=or1k-unknown-linux-$LIBC + ;; + or32:Linux:*:* | or1k*:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + padre:Linux:*:*) + GUESS=sparc-unknown-linux-$LIBC + ;; + parisc64:Linux:*:* | hppa64:Linux:*:*) + GUESS=hppa64-unknown-linux-$LIBC + ;; + parisc:Linux:*:* | hppa:Linux:*:*) + # Look for CPU level + case `grep '^cpu[^a-z]*:' /proc/cpuinfo 2>/dev/null | cut -d' ' -f2` in + PA7*) GUESS=hppa1.1-unknown-linux-$LIBC ;; + PA8*) GUESS=hppa2.0-unknown-linux-$LIBC ;; + *) GUESS=hppa-unknown-linux-$LIBC ;; + esac + ;; + ppc64:Linux:*:*) + GUESS=powerpc64-unknown-linux-$LIBC + ;; + ppc:Linux:*:*) + GUESS=powerpc-unknown-linux-$LIBC + ;; + ppc64le:Linux:*:*) + GUESS=powerpc64le-unknown-linux-$LIBC + ;; + ppcle:Linux:*:*) + GUESS=powerpcle-unknown-linux-$LIBC + ;; + riscv32:Linux:*:* | riscv32be:Linux:*:* | riscv64:Linux:*:* | riscv64be:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + s390:Linux:*:* | s390x:Linux:*:*) + GUESS=$UNAME_MACHINE-ibm-linux-$LIBC + ;; + sh64*:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + sh*:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + sparc:Linux:*:* | sparc64:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + tile*:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + vax:Linux:*:*) + GUESS=$UNAME_MACHINE-dec-linux-$LIBC + ;; + x86_64:Linux:*:*) + set_cc_for_build + CPU=$UNAME_MACHINE + LIBCABI=$LIBC + if test "$CC_FOR_BUILD" != no_compiler_found; then + ABI=64 + sed 's/^ //' << EOF > "$dummy.c" + #ifdef __i386__ + ABI=x86 + #else + #ifdef __ILP32__ + ABI=x32 + #endif + #endif +EOF + cc_set_abi=`$CC_FOR_BUILD -E "$dummy.c" 2>/dev/null | grep '^ABI' | sed 's, ,,g'` + eval "$cc_set_abi" + case $ABI in + x86) CPU=i686 ;; + x32) LIBCABI=${LIBC}x32 ;; + esac + fi + GUESS=$CPU-pc-linux-$LIBCABI + ;; + xtensa*:Linux:*:*) + GUESS=$UNAME_MACHINE-unknown-linux-$LIBC + ;; + i*86:DYNIX/ptx:4*:*) + # ptx 4.0 does uname -s correctly, with DYNIX/ptx in there. + # earlier versions are messed up and put the nodename in both + # sysname and nodename. + GUESS=i386-sequent-sysv4 + ;; + i*86:UNIX_SV:4.2MP:2.*) + # Unixware is an offshoot of SVR4, but it has its own version + # number series starting with 2... + # I am not positive that other SVR4 systems won't match this, + # I just have to hope. -- rms. + # Use sysv4.2uw... so that sysv4* matches it. + GUESS=$UNAME_MACHINE-pc-sysv4.2uw$UNAME_VERSION + ;; + i*86:OS/2:*:*) + # If we were able to find 'uname', then EMX Unix compatibility + # is probably installed. + GUESS=$UNAME_MACHINE-pc-os2-emx + ;; + i*86:XTS-300:*:STOP) + GUESS=$UNAME_MACHINE-unknown-stop + ;; + i*86:atheos:*:*) + GUESS=$UNAME_MACHINE-unknown-atheos + ;; + i*86:syllable:*:*) + GUESS=$UNAME_MACHINE-pc-syllable + ;; + i*86:LynxOS:2.*:* | i*86:LynxOS:3.[01]*:* | i*86:LynxOS:4.[02]*:*) + GUESS=i386-unknown-lynxos$UNAME_RELEASE + ;; + i*86:*DOS:*:*) + GUESS=$UNAME_MACHINE-pc-msdosdjgpp + ;; + i*86:*:4.*:*) + UNAME_REL=`echo "$UNAME_RELEASE" | sed 's/\/MP$//'` + if grep Novell /usr/include/link.h >/dev/null 2>/dev/null; then + GUESS=$UNAME_MACHINE-univel-sysv$UNAME_REL + else + GUESS=$UNAME_MACHINE-pc-sysv$UNAME_REL + fi + ;; + i*86:*:5:[678]*) + # UnixWare 7.x, OpenUNIX and OpenServer 6. + case `/bin/uname -X | grep "^Machine"` in + *486*) UNAME_MACHINE=i486 ;; + *Pentium) UNAME_MACHINE=i586 ;; + *Pent*|*Celeron) UNAME_MACHINE=i686 ;; + esac + GUESS=$UNAME_MACHINE-unknown-sysv${UNAME_RELEASE}${UNAME_SYSTEM}${UNAME_VERSION} + ;; + i*86:*:3.2:*) + if test -f /usr/options/cb.name; then + UNAME_REL=`sed -n 's/.*Version //p' /dev/null >/dev/null ; then + UNAME_REL=`(/bin/uname -X|grep Release|sed -e 's/.*= //')` + (/bin/uname -X|grep i80486 >/dev/null) && UNAME_MACHINE=i486 + (/bin/uname -X|grep '^Machine.*Pentium' >/dev/null) \ + && UNAME_MACHINE=i586 + (/bin/uname -X|grep '^Machine.*Pent *II' >/dev/null) \ + && UNAME_MACHINE=i686 + (/bin/uname -X|grep '^Machine.*Pentium Pro' >/dev/null) \ + && UNAME_MACHINE=i686 + GUESS=$UNAME_MACHINE-pc-sco$UNAME_REL + else + GUESS=$UNAME_MACHINE-pc-sysv32 + fi + ;; + pc:*:*:*) + # Left here for compatibility: + # uname -m prints for DJGPP always 'pc', but it prints nothing about + # the processor, so we play safe by assuming i586. + # Note: whatever this is, it MUST be the same as what config.sub + # prints for the "djgpp" host, or else GDB configure will decide that + # this is a cross-build. + GUESS=i586-pc-msdosdjgpp + ;; + Intel:Mach:3*:*) + GUESS=i386-pc-mach3 + ;; + paragon:*:*:*) + GUESS=i860-intel-osf1 + ;; + i860:*:4.*:*) # i860-SVR4 + if grep Stardent /usr/include/sys/uadmin.h >/dev/null 2>&1 ; then + GUESS=i860-stardent-sysv$UNAME_RELEASE # Stardent Vistra i860-SVR4 + else # Add other i860-SVR4 vendors below as they are discovered. + GUESS=i860-unknown-sysv$UNAME_RELEASE # Unknown i860-SVR4 + fi + ;; + mini*:CTIX:SYS*5:*) + # "miniframe" + GUESS=m68010-convergent-sysv + ;; + mc68k:UNIX:SYSTEM5:3.51m) + GUESS=m68k-convergent-sysv + ;; + M680?0:D-NIX:5.3:*) + GUESS=m68k-diab-dnix + ;; + M68*:*:R3V[5678]*:*) + test -r /sysV68 && { echo 'm68k-motorola-sysv'; exit; } ;; + 3[345]??:*:4.0:3.0 | 3[34]??A:*:4.0:3.0 | 3[34]??,*:*:4.0:3.0 | 3[34]??/*:*:4.0:3.0 | 4400:*:4.0:3.0 | 4850:*:4.0:3.0 | SKA40:*:4.0:3.0 | SDS2:*:4.0:3.0 | SHG2:*:4.0:3.0 | S7501*:*:4.0:3.0) + OS_REL='' + test -r /etc/.relid \ + && OS_REL=.`sed -n 's/[^ ]* [^ ]* \([0-9][0-9]\).*/\1/p' < /etc/.relid` + /bin/uname -p 2>/dev/null | grep 86 >/dev/null \ + && { echo i486-ncr-sysv4.3"$OS_REL"; exit; } + /bin/uname -p 2>/dev/null | /bin/grep entium >/dev/null \ + && { echo i586-ncr-sysv4.3"$OS_REL"; exit; } ;; + 3[34]??:*:4.0:* | 3[34]??,*:*:4.0:*) + /bin/uname -p 2>/dev/null | grep 86 >/dev/null \ + && { echo i486-ncr-sysv4; exit; } ;; + NCR*:*:4.2:* | MPRAS*:*:4.2:*) + OS_REL='.3' + test -r /etc/.relid \ + && OS_REL=.`sed -n 's/[^ ]* [^ ]* \([0-9][0-9]\).*/\1/p' < /etc/.relid` + /bin/uname -p 2>/dev/null | grep 86 >/dev/null \ + && { echo i486-ncr-sysv4.3"$OS_REL"; exit; } + /bin/uname -p 2>/dev/null | /bin/grep entium >/dev/null \ + && { echo i586-ncr-sysv4.3"$OS_REL"; exit; } + /bin/uname -p 2>/dev/null | /bin/grep pteron >/dev/null \ + && { echo i586-ncr-sysv4.3"$OS_REL"; exit; } ;; + m68*:LynxOS:2.*:* | m68*:LynxOS:3.0*:*) + GUESS=m68k-unknown-lynxos$UNAME_RELEASE + ;; + mc68030:UNIX_System_V:4.*:*) + GUESS=m68k-atari-sysv4 + ;; + TSUNAMI:LynxOS:2.*:*) + GUESS=sparc-unknown-lynxos$UNAME_RELEASE + ;; + rs6000:LynxOS:2.*:*) + GUESS=rs6000-unknown-lynxos$UNAME_RELEASE + ;; + PowerPC:LynxOS:2.*:* | PowerPC:LynxOS:3.[01]*:* | PowerPC:LynxOS:4.[02]*:*) + GUESS=powerpc-unknown-lynxos$UNAME_RELEASE + ;; + SM[BE]S:UNIX_SV:*:*) + GUESS=mips-dde-sysv$UNAME_RELEASE + ;; + RM*:ReliantUNIX-*:*:*) + GUESS=mips-sni-sysv4 + ;; + RM*:SINIX-*:*:*) + GUESS=mips-sni-sysv4 + ;; + *:SINIX-*:*:*) + if uname -p 2>/dev/null >/dev/null ; then + UNAME_MACHINE=`(uname -p) 2>/dev/null` + GUESS=$UNAME_MACHINE-sni-sysv4 + else + GUESS=ns32k-sni-sysv + fi + ;; + PENTIUM:*:4.0*:*) # Unisys 'ClearPath HMP IX 4000' SVR4/MP effort + # says + GUESS=i586-unisys-sysv4 + ;; + *:UNIX_System_V:4*:FTX*) + # From Gerald Hewes . + # How about differentiating between stratus architectures? -djm + GUESS=hppa1.1-stratus-sysv4 + ;; + *:*:*:FTX*) + # From seanf@swdc.stratus.com. + GUESS=i860-stratus-sysv4 + ;; + i*86:VOS:*:*) + # From Paul.Green@stratus.com. + GUESS=$UNAME_MACHINE-stratus-vos + ;; + *:VOS:*:*) + # From Paul.Green@stratus.com. + GUESS=hppa1.1-stratus-vos + ;; + mc68*:A/UX:*:*) + GUESS=m68k-apple-aux$UNAME_RELEASE + ;; + news*:NEWS-OS:6*:*) + GUESS=mips-sony-newsos6 + ;; + R[34]000:*System_V*:*:* | R4000:UNIX_SYSV:*:* | R*000:UNIX_SV:*:*) + if test -d /usr/nec; then + GUESS=mips-nec-sysv$UNAME_RELEASE + else + GUESS=mips-unknown-sysv$UNAME_RELEASE + fi + ;; + BeBox:BeOS:*:*) # BeOS running on hardware made by Be, PPC only. + GUESS=powerpc-be-beos + ;; + BeMac:BeOS:*:*) # BeOS running on Mac or Mac clone, PPC only. + GUESS=powerpc-apple-beos + ;; + BePC:BeOS:*:*) # BeOS running on Intel PC compatible. + GUESS=i586-pc-beos + ;; + BePC:Haiku:*:*) # Haiku running on Intel PC compatible. + GUESS=i586-pc-haiku + ;; + ppc:Haiku:*:*) # Haiku running on Apple PowerPC + GUESS=powerpc-apple-haiku + ;; + *:Haiku:*:*) # Haiku modern gcc (not bound by BeOS compat) + GUESS=$UNAME_MACHINE-unknown-haiku + ;; + SX-4:SUPER-UX:*:*) + GUESS=sx4-nec-superux$UNAME_RELEASE + ;; + SX-5:SUPER-UX:*:*) + GUESS=sx5-nec-superux$UNAME_RELEASE + ;; + SX-6:SUPER-UX:*:*) + GUESS=sx6-nec-superux$UNAME_RELEASE + ;; + SX-7:SUPER-UX:*:*) + GUESS=sx7-nec-superux$UNAME_RELEASE + ;; + SX-8:SUPER-UX:*:*) + GUESS=sx8-nec-superux$UNAME_RELEASE + ;; + SX-8R:SUPER-UX:*:*) + GUESS=sx8r-nec-superux$UNAME_RELEASE + ;; + SX-ACE:SUPER-UX:*:*) + GUESS=sxace-nec-superux$UNAME_RELEASE + ;; + Power*:Rhapsody:*:*) + GUESS=powerpc-apple-rhapsody$UNAME_RELEASE + ;; + *:Rhapsody:*:*) + GUESS=$UNAME_MACHINE-apple-rhapsody$UNAME_RELEASE + ;; + arm64:Darwin:*:*) + GUESS=aarch64-apple-darwin$UNAME_RELEASE + ;; + *:Darwin:*:*) + UNAME_PROCESSOR=`uname -p` + case $UNAME_PROCESSOR in + unknown) UNAME_PROCESSOR=powerpc ;; + esac + if command -v xcode-select > /dev/null 2> /dev/null && \ + ! xcode-select --print-path > /dev/null 2> /dev/null ; then + # Avoid executing cc if there is no toolchain installed as + # cc will be a stub that puts up a graphical alert + # prompting the user to install developer tools. + CC_FOR_BUILD=no_compiler_found + else + set_cc_for_build + fi + if test "$CC_FOR_BUILD" != no_compiler_found; then + if (echo '#ifdef __LP64__'; echo IS_64BIT_ARCH; echo '#endif') | \ + (CCOPTS="" $CC_FOR_BUILD -E - 2>/dev/null) | \ + grep IS_64BIT_ARCH >/dev/null + then + case $UNAME_PROCESSOR in + i386) UNAME_PROCESSOR=x86_64 ;; + powerpc) UNAME_PROCESSOR=powerpc64 ;; + esac + fi + # On 10.4-10.6 one might compile for PowerPC via gcc -arch ppc + if (echo '#ifdef __POWERPC__'; echo IS_PPC; echo '#endif') | \ + (CCOPTS="" $CC_FOR_BUILD -E - 2>/dev/null) | \ + grep IS_PPC >/dev/null + then + UNAME_PROCESSOR=powerpc + fi + elif test "$UNAME_PROCESSOR" = i386 ; then + # uname -m returns i386 or x86_64 + UNAME_PROCESSOR=$UNAME_MACHINE + fi + GUESS=$UNAME_PROCESSOR-apple-darwin$UNAME_RELEASE + ;; + *:procnto*:*:* | *:QNX:[0123456789]*:*) + UNAME_PROCESSOR=`uname -p` + if test "$UNAME_PROCESSOR" = x86; then + UNAME_PROCESSOR=i386 + UNAME_MACHINE=pc + fi + GUESS=$UNAME_PROCESSOR-$UNAME_MACHINE-nto-qnx$UNAME_RELEASE + ;; + *:QNX:*:4*) + GUESS=i386-pc-qnx + ;; + NEO-*:NONSTOP_KERNEL:*:*) + GUESS=neo-tandem-nsk$UNAME_RELEASE + ;; + NSE-*:NONSTOP_KERNEL:*:*) + GUESS=nse-tandem-nsk$UNAME_RELEASE + ;; + NSR-*:NONSTOP_KERNEL:*:*) + GUESS=nsr-tandem-nsk$UNAME_RELEASE + ;; + NSV-*:NONSTOP_KERNEL:*:*) + GUESS=nsv-tandem-nsk$UNAME_RELEASE + ;; + NSX-*:NONSTOP_KERNEL:*:*) + GUESS=nsx-tandem-nsk$UNAME_RELEASE + ;; + *:NonStop-UX:*:*) + GUESS=mips-compaq-nonstopux + ;; + BS2000:POSIX*:*:*) + GUESS=bs2000-siemens-sysv + ;; + DS/*:UNIX_System_V:*:*) + GUESS=$UNAME_MACHINE-$UNAME_SYSTEM-$UNAME_RELEASE + ;; + *:Plan9:*:*) + # "uname -m" is not consistent, so use $cputype instead. 386 + # is converted to i386 for consistency with other x86 + # operating systems. + if test "${cputype-}" = 386; then + UNAME_MACHINE=i386 + elif test "x${cputype-}" != x; then + UNAME_MACHINE=$cputype + fi + GUESS=$UNAME_MACHINE-unknown-plan9 + ;; + *:TOPS-10:*:*) + GUESS=pdp10-unknown-tops10 + ;; + *:TENEX:*:*) + GUESS=pdp10-unknown-tenex + ;; + KS10:TOPS-20:*:* | KL10:TOPS-20:*:* | TYPE4:TOPS-20:*:*) + GUESS=pdp10-dec-tops20 + ;; + XKL-1:TOPS-20:*:* | TYPE5:TOPS-20:*:*) + GUESS=pdp10-xkl-tops20 + ;; + *:TOPS-20:*:*) + GUESS=pdp10-unknown-tops20 + ;; + *:ITS:*:*) + GUESS=pdp10-unknown-its + ;; + SEI:*:*:SEIUX) + GUESS=mips-sei-seiux$UNAME_RELEASE + ;; + *:DragonFly:*:*) + DRAGONFLY_REL=`echo "$UNAME_RELEASE" | sed -e 's/[-(].*//'` + GUESS=$UNAME_MACHINE-unknown-dragonfly$DRAGONFLY_REL + ;; + *:*VMS:*:*) + UNAME_MACHINE=`(uname -p) 2>/dev/null` + case $UNAME_MACHINE in + A*) GUESS=alpha-dec-vms ;; + I*) GUESS=ia64-dec-vms ;; + V*) GUESS=vax-dec-vms ;; + esac ;; + *:XENIX:*:SysV) + GUESS=i386-pc-xenix + ;; + i*86:skyos:*:*) + SKYOS_REL=`echo "$UNAME_RELEASE" | sed -e 's/ .*$//'` + GUESS=$UNAME_MACHINE-pc-skyos$SKYOS_REL + ;; + i*86:rdos:*:*) + GUESS=$UNAME_MACHINE-pc-rdos + ;; + i*86:Fiwix:*:*) + GUESS=$UNAME_MACHINE-pc-fiwix + ;; + *:AROS:*:*) + GUESS=$UNAME_MACHINE-unknown-aros + ;; + x86_64:VMkernel:*:*) + GUESS=$UNAME_MACHINE-unknown-esx + ;; + amd64:Isilon\ OneFS:*:*) + GUESS=x86_64-unknown-onefs + ;; + *:Unleashed:*:*) + GUESS=$UNAME_MACHINE-unknown-unleashed$UNAME_RELEASE + ;; +esac + +# Do we have a guess based on uname results? +if test "x$GUESS" != x; then + echo "$GUESS" + exit +fi + +# No uname command or uname output not recognized. +set_cc_for_build +cat > "$dummy.c" < +#include +#endif +#if defined(ultrix) || defined(_ultrix) || defined(__ultrix) || defined(__ultrix__) +#if defined (vax) || defined (__vax) || defined (__vax__) || defined(mips) || defined(__mips) || defined(__mips__) || defined(MIPS) || defined(__MIPS__) +#include +#if defined(_SIZE_T_) || defined(SIGLOST) +#include +#endif +#endif +#endif +main () +{ +#if defined (sony) +#if defined (MIPSEB) + /* BFD wants "bsd" instead of "newsos". Perhaps BFD should be changed, + I don't know.... */ + printf ("mips-sony-bsd\n"); exit (0); +#else +#include + printf ("m68k-sony-newsos%s\n", +#ifdef NEWSOS4 + "4" +#else + "" +#endif + ); exit (0); +#endif +#endif + +#if defined (NeXT) +#if !defined (__ARCHITECTURE__) +#define __ARCHITECTURE__ "m68k" +#endif + int version; + version=`(hostinfo | sed -n 's/.*NeXT Mach \([0-9]*\).*/\1/p') 2>/dev/null`; + if (version < 4) + printf ("%s-next-nextstep%d\n", __ARCHITECTURE__, version); + else + printf ("%s-next-openstep%d\n", __ARCHITECTURE__, version); + exit (0); +#endif + +#if defined (MULTIMAX) || defined (n16) +#if defined (UMAXV) + printf ("ns32k-encore-sysv\n"); exit (0); +#else +#if defined (CMU) + printf ("ns32k-encore-mach\n"); exit (0); +#else + printf ("ns32k-encore-bsd\n"); exit (0); +#endif +#endif +#endif + +#if defined (__386BSD__) + printf ("i386-pc-bsd\n"); exit (0); +#endif + +#if defined (sequent) +#if defined (i386) + printf ("i386-sequent-dynix\n"); exit (0); +#endif +#if defined (ns32000) + printf ("ns32k-sequent-dynix\n"); exit (0); +#endif +#endif + +#if defined (_SEQUENT_) + struct utsname un; + + uname(&un); + if (strncmp(un.version, "V2", 2) == 0) { + printf ("i386-sequent-ptx2\n"); exit (0); + } + if (strncmp(un.version, "V1", 2) == 0) { /* XXX is V1 correct? */ + printf ("i386-sequent-ptx1\n"); exit (0); + } + printf ("i386-sequent-ptx\n"); exit (0); +#endif + +#if defined (vax) +#if !defined (ultrix) +#include +#if defined (BSD) +#if BSD == 43 + printf ("vax-dec-bsd4.3\n"); exit (0); +#else +#if BSD == 199006 + printf ("vax-dec-bsd4.3reno\n"); exit (0); +#else + printf ("vax-dec-bsd\n"); exit (0); +#endif +#endif +#else + printf ("vax-dec-bsd\n"); exit (0); +#endif +#else +#if defined(_SIZE_T_) || defined(SIGLOST) + struct utsname un; + uname (&un); + printf ("vax-dec-ultrix%s\n", un.release); exit (0); +#else + printf ("vax-dec-ultrix\n"); exit (0); +#endif +#endif +#endif +#if defined(ultrix) || defined(_ultrix) || defined(__ultrix) || defined(__ultrix__) +#if defined(mips) || defined(__mips) || defined(__mips__) || defined(MIPS) || defined(__MIPS__) +#if defined(_SIZE_T_) || defined(SIGLOST) + struct utsname *un; + uname (&un); + printf ("mips-dec-ultrix%s\n", un.release); exit (0); +#else + printf ("mips-dec-ultrix\n"); exit (0); +#endif +#endif +#endif + +#if defined (alliant) && defined (i860) + printf ("i860-alliant-bsd\n"); exit (0); +#endif + + exit (1); +} +EOF + +$CC_FOR_BUILD -o "$dummy" "$dummy.c" 2>/dev/null && SYSTEM_NAME=`"$dummy"` && + { echo "$SYSTEM_NAME"; exit; } + +# Apollos put the system type in the environment. +test -d /usr/apollo && { echo "$ISP-apollo-$SYSTYPE"; exit; } + +echo "$0: unable to guess system type" >&2 + +case $UNAME_MACHINE:$UNAME_SYSTEM in + mips:Linux | mips64:Linux) + # If we got here on MIPS GNU/Linux, output extra information. + cat >&2 <&2 <&2 </dev/null || echo unknown` +uname -r = `(uname -r) 2>/dev/null || echo unknown` +uname -s = `(uname -s) 2>/dev/null || echo unknown` +uname -v = `(uname -v) 2>/dev/null || echo unknown` + +/usr/bin/uname -p = `(/usr/bin/uname -p) 2>/dev/null` +/bin/uname -X = `(/bin/uname -X) 2>/dev/null` + +hostinfo = `(hostinfo) 2>/dev/null` +/bin/universe = `(/bin/universe) 2>/dev/null` +/usr/bin/arch -k = `(/usr/bin/arch -k) 2>/dev/null` +/bin/arch = `(/bin/arch) 2>/dev/null` +/usr/bin/oslevel = `(/usr/bin/oslevel) 2>/dev/null` +/usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null` + +UNAME_MACHINE = "$UNAME_MACHINE" +UNAME_RELEASE = "$UNAME_RELEASE" +UNAME_SYSTEM = "$UNAME_SYSTEM" +UNAME_VERSION = "$UNAME_VERSION" +EOF +fi + +exit 1 + +# Local variables: +# eval: (add-hook 'before-save-hook 'time-stamp) +# time-stamp-start: "timestamp='" +# time-stamp-format: "%:y-%02m-%02d" +# time-stamp-end: "'" +# End: diff --git a/3rdparty/freetype-2.13.2/builds/unix/config.sub b/3rdparty/freetype-2.13.2/builds/unix/config.sub new file mode 100644 index 000000000..6ae250275 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/config.sub @@ -0,0 +1,1895 @@ +#! /bin/sh +# Configuration validation subroutine script. +# Copyright 1992-2023 Free Software Foundation, Inc. + +# shellcheck disable=SC2006,SC2268 # see below for rationale + +timestamp='2023-07-31' + +# This file is free software; you can redistribute it and/or modify it +# under the terms of the GNU General Public License as published by +# the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, see . +# +# As a special exception to the GNU General Public License, if you +# distribute this file as part of a program that contains a +# configuration script generated by Autoconf, you may include it under +# the same distribution terms that you use for the rest of that +# program. This Exception is an additional permission under section 7 +# of the GNU General Public License, version 3 ("GPLv3"). + + +# Please send patches to . +# +# Configuration subroutine to validate and canonicalize a configuration type. +# Supply the specified configuration type as an argument. +# If it is invalid, we print an error message on stderr and exit with code 1. +# Otherwise, we print the canonical config type on stdout and succeed. + +# You can get the latest version of this script from: +# https://git.savannah.gnu.org/cgit/config.git/plain/config.sub + +# This file is supposed to be the same for all GNU packages +# and recognize all the CPU types, system types and aliases +# that are meaningful with *any* GNU software. +# Each package is responsible for reporting which valid configurations +# it does not support. The user should be able to distinguish +# a failure to support a valid configuration from a meaningless +# configuration. + +# The goal of this file is to map all the various variations of a given +# machine specification into a single specification in the form: +# CPU_TYPE-MANUFACTURER-OPERATING_SYSTEM +# or in some cases, the newer four-part form: +# CPU_TYPE-MANUFACTURER-KERNEL-OPERATING_SYSTEM +# It is wrong to echo any other type of specification. + +# The "shellcheck disable" line above the timestamp inhibits complaints +# about features and limitations of the classic Bourne shell that were +# superseded or lifted in POSIX. However, this script identifies a wide +# variety of pre-POSIX systems that do not have POSIX shells at all, and +# even some reasonably current systems (Solaris 10 as case-in-point) still +# have a pre-POSIX /bin/sh. + +me=`echo "$0" | sed -e 's,.*/,,'` + +usage="\ +Usage: $0 [OPTION] CPU-MFR-OPSYS or ALIAS + +Canonicalize a configuration name. + +Options: + -h, --help print this help, then exit + -t, --time-stamp print date of last modification, then exit + -v, --version print version number, then exit + +Report bugs and patches to ." + +version="\ +GNU config.sub ($timestamp) + +Copyright 1992-2023 Free Software Foundation, Inc. + +This is free software; see the source for copying conditions. There is NO +warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." + +help=" +Try '$me --help' for more information." + +# Parse command line +while test $# -gt 0 ; do + case $1 in + --time-stamp | --time* | -t ) + echo "$timestamp" ; exit ;; + --version | -v ) + echo "$version" ; exit ;; + --help | --h* | -h ) + echo "$usage"; exit ;; + -- ) # Stop option processing + shift; break ;; + - ) # Use stdin as input. + break ;; + -* ) + echo "$me: invalid option $1$help" >&2 + exit 1 ;; + + *local*) + # First pass through any local machine types. + echo "$1" + exit ;; + + * ) + break ;; + esac +done + +case $# in + 0) echo "$me: missing argument$help" >&2 + exit 1;; + 1) ;; + *) echo "$me: too many arguments$help" >&2 + exit 1;; +esac + +# Split fields of configuration type +# shellcheck disable=SC2162 +saved_IFS=$IFS +IFS="-" read field1 field2 field3 field4 <&2 + exit 1 + ;; + *-*-*-*) + basic_machine=$field1-$field2 + basic_os=$field3-$field4 + ;; + *-*-*) + # Ambiguous whether COMPANY is present, or skipped and KERNEL-OS is two + # parts + maybe_os=$field2-$field3 + case $maybe_os in + nto-qnx* | linux-* | uclinux-uclibc* \ + | uclinux-gnu* | kfreebsd*-gnu* | knetbsd*-gnu* | netbsd*-gnu* \ + | netbsd*-eabi* | kopensolaris*-gnu* | cloudabi*-eabi* \ + | storm-chaos* | os2-emx* | rtmk-nova* | managarm-* \ + | windows-* ) + basic_machine=$field1 + basic_os=$maybe_os + ;; + android-linux) + basic_machine=$field1-unknown + basic_os=linux-android + ;; + *) + basic_machine=$field1-$field2 + basic_os=$field3 + ;; + esac + ;; + *-*) + # A lone config we happen to match not fitting any pattern + case $field1-$field2 in + decstation-3100) + basic_machine=mips-dec + basic_os= + ;; + *-*) + # Second component is usually, but not always the OS + case $field2 in + # Prevent following clause from handling this valid os + sun*os*) + basic_machine=$field1 + basic_os=$field2 + ;; + zephyr*) + basic_machine=$field1-unknown + basic_os=$field2 + ;; + # Manufacturers + dec* | mips* | sequent* | encore* | pc533* | sgi* | sony* \ + | att* | 7300* | 3300* | delta* | motorola* | sun[234]* \ + | unicom* | ibm* | next | hp | isi* | apollo | altos* \ + | convergent* | ncr* | news | 32* | 3600* | 3100* \ + | hitachi* | c[123]* | convex* | sun | crds | omron* | dg \ + | ultra | tti* | harris | dolphin | highlevel | gould \ + | cbm | ns | masscomp | apple | axis | knuth | cray \ + | microblaze* | sim | cisco \ + | oki | wec | wrs | winbond) + basic_machine=$field1-$field2 + basic_os= + ;; + *) + basic_machine=$field1 + basic_os=$field2 + ;; + esac + ;; + esac + ;; + *) + # Convert single-component short-hands not valid as part of + # multi-component configurations. + case $field1 in + 386bsd) + basic_machine=i386-pc + basic_os=bsd + ;; + a29khif) + basic_machine=a29k-amd + basic_os=udi + ;; + adobe68k) + basic_machine=m68010-adobe + basic_os=scout + ;; + alliant) + basic_machine=fx80-alliant + basic_os= + ;; + altos | altos3068) + basic_machine=m68k-altos + basic_os= + ;; + am29k) + basic_machine=a29k-none + basic_os=bsd + ;; + amdahl) + basic_machine=580-amdahl + basic_os=sysv + ;; + amiga) + basic_machine=m68k-unknown + basic_os= + ;; + amigaos | amigados) + basic_machine=m68k-unknown + basic_os=amigaos + ;; + amigaunix | amix) + basic_machine=m68k-unknown + basic_os=sysv4 + ;; + apollo68) + basic_machine=m68k-apollo + basic_os=sysv + ;; + apollo68bsd) + basic_machine=m68k-apollo + basic_os=bsd + ;; + aros) + basic_machine=i386-pc + basic_os=aros + ;; + aux) + basic_machine=m68k-apple + basic_os=aux + ;; + balance) + basic_machine=ns32k-sequent + basic_os=dynix + ;; + blackfin) + basic_machine=bfin-unknown + basic_os=linux + ;; + cegcc) + basic_machine=arm-unknown + basic_os=cegcc + ;; + convex-c1) + basic_machine=c1-convex + basic_os=bsd + ;; + convex-c2) + basic_machine=c2-convex + basic_os=bsd + ;; + convex-c32) + basic_machine=c32-convex + basic_os=bsd + ;; + convex-c34) + basic_machine=c34-convex + basic_os=bsd + ;; + convex-c38) + basic_machine=c38-convex + basic_os=bsd + ;; + cray) + basic_machine=j90-cray + basic_os=unicos + ;; + crds | unos) + basic_machine=m68k-crds + basic_os= + ;; + da30) + basic_machine=m68k-da30 + basic_os= + ;; + decstation | pmax | pmin | dec3100 | decstatn) + basic_machine=mips-dec + basic_os= + ;; + delta88) + basic_machine=m88k-motorola + basic_os=sysv3 + ;; + dicos) + basic_machine=i686-pc + basic_os=dicos + ;; + djgpp) + basic_machine=i586-pc + basic_os=msdosdjgpp + ;; + ebmon29k) + basic_machine=a29k-amd + basic_os=ebmon + ;; + es1800 | OSE68k | ose68k | ose | OSE) + basic_machine=m68k-ericsson + basic_os=ose + ;; + gmicro) + basic_machine=tron-gmicro + basic_os=sysv + ;; + go32) + basic_machine=i386-pc + basic_os=go32 + ;; + h8300hms) + basic_machine=h8300-hitachi + basic_os=hms + ;; + h8300xray) + basic_machine=h8300-hitachi + basic_os=xray + ;; + h8500hms) + basic_machine=h8500-hitachi + basic_os=hms + ;; + harris) + basic_machine=m88k-harris + basic_os=sysv3 + ;; + hp300 | hp300hpux) + basic_machine=m68k-hp + basic_os=hpux + ;; + hp300bsd) + basic_machine=m68k-hp + basic_os=bsd + ;; + hppaosf) + basic_machine=hppa1.1-hp + basic_os=osf + ;; + hppro) + basic_machine=hppa1.1-hp + basic_os=proelf + ;; + i386mach) + basic_machine=i386-mach + basic_os=mach + ;; + isi68 | isi) + basic_machine=m68k-isi + basic_os=sysv + ;; + m68knommu) + basic_machine=m68k-unknown + basic_os=linux + ;; + magnum | m3230) + basic_machine=mips-mips + basic_os=sysv + ;; + merlin) + basic_machine=ns32k-utek + basic_os=sysv + ;; + mingw64) + basic_machine=x86_64-pc + basic_os=mingw64 + ;; + mingw32) + basic_machine=i686-pc + basic_os=mingw32 + ;; + mingw32ce) + basic_machine=arm-unknown + basic_os=mingw32ce + ;; + monitor) + basic_machine=m68k-rom68k + basic_os=coff + ;; + morphos) + basic_machine=powerpc-unknown + basic_os=morphos + ;; + moxiebox) + basic_machine=moxie-unknown + basic_os=moxiebox + ;; + msdos) + basic_machine=i386-pc + basic_os=msdos + ;; + msys) + basic_machine=i686-pc + basic_os=msys + ;; + mvs) + basic_machine=i370-ibm + basic_os=mvs + ;; + nacl) + basic_machine=le32-unknown + basic_os=nacl + ;; + ncr3000) + basic_machine=i486-ncr + basic_os=sysv4 + ;; + netbsd386) + basic_machine=i386-pc + basic_os=netbsd + ;; + netwinder) + basic_machine=armv4l-rebel + basic_os=linux + ;; + news | news700 | news800 | news900) + basic_machine=m68k-sony + basic_os=newsos + ;; + news1000) + basic_machine=m68030-sony + basic_os=newsos + ;; + necv70) + basic_machine=v70-nec + basic_os=sysv + ;; + nh3000) + basic_machine=m68k-harris + basic_os=cxux + ;; + nh[45]000) + basic_machine=m88k-harris + basic_os=cxux + ;; + nindy960) + basic_machine=i960-intel + basic_os=nindy + ;; + mon960) + basic_machine=i960-intel + basic_os=mon960 + ;; + nonstopux) + basic_machine=mips-compaq + basic_os=nonstopux + ;; + os400) + basic_machine=powerpc-ibm + basic_os=os400 + ;; + OSE68000 | ose68000) + basic_machine=m68000-ericsson + basic_os=ose + ;; + os68k) + basic_machine=m68k-none + basic_os=os68k + ;; + paragon) + basic_machine=i860-intel + basic_os=osf + ;; + parisc) + basic_machine=hppa-unknown + basic_os=linux + ;; + psp) + basic_machine=mipsallegrexel-sony + basic_os=psp + ;; + pw32) + basic_machine=i586-unknown + basic_os=pw32 + ;; + rdos | rdos64) + basic_machine=x86_64-pc + basic_os=rdos + ;; + rdos32) + basic_machine=i386-pc + basic_os=rdos + ;; + rom68k) + basic_machine=m68k-rom68k + basic_os=coff + ;; + sa29200) + basic_machine=a29k-amd + basic_os=udi + ;; + sei) + basic_machine=mips-sei + basic_os=seiux + ;; + sequent) + basic_machine=i386-sequent + basic_os= + ;; + sps7) + basic_machine=m68k-bull + basic_os=sysv2 + ;; + st2000) + basic_machine=m68k-tandem + basic_os= + ;; + stratus) + basic_machine=i860-stratus + basic_os=sysv4 + ;; + sun2) + basic_machine=m68000-sun + basic_os= + ;; + sun2os3) + basic_machine=m68000-sun + basic_os=sunos3 + ;; + sun2os4) + basic_machine=m68000-sun + basic_os=sunos4 + ;; + sun3) + basic_machine=m68k-sun + basic_os= + ;; + sun3os3) + basic_machine=m68k-sun + basic_os=sunos3 + ;; + sun3os4) + basic_machine=m68k-sun + basic_os=sunos4 + ;; + sun4) + basic_machine=sparc-sun + basic_os= + ;; + sun4os3) + basic_machine=sparc-sun + basic_os=sunos3 + ;; + sun4os4) + basic_machine=sparc-sun + basic_os=sunos4 + ;; + sun4sol2) + basic_machine=sparc-sun + basic_os=solaris2 + ;; + sun386 | sun386i | roadrunner) + basic_machine=i386-sun + basic_os= + ;; + sv1) + basic_machine=sv1-cray + basic_os=unicos + ;; + symmetry) + basic_machine=i386-sequent + basic_os=dynix + ;; + t3e) + basic_machine=alphaev5-cray + basic_os=unicos + ;; + t90) + basic_machine=t90-cray + basic_os=unicos + ;; + toad1) + basic_machine=pdp10-xkl + basic_os=tops20 + ;; + tpf) + basic_machine=s390x-ibm + basic_os=tpf + ;; + udi29k) + basic_machine=a29k-amd + basic_os=udi + ;; + ultra3) + basic_machine=a29k-nyu + basic_os=sym1 + ;; + v810 | necv810) + basic_machine=v810-nec + basic_os=none + ;; + vaxv) + basic_machine=vax-dec + basic_os=sysv + ;; + vms) + basic_machine=vax-dec + basic_os=vms + ;; + vsta) + basic_machine=i386-pc + basic_os=vsta + ;; + vxworks960) + basic_machine=i960-wrs + basic_os=vxworks + ;; + vxworks68) + basic_machine=m68k-wrs + basic_os=vxworks + ;; + vxworks29k) + basic_machine=a29k-wrs + basic_os=vxworks + ;; + xbox) + basic_machine=i686-pc + basic_os=mingw32 + ;; + ymp) + basic_machine=ymp-cray + basic_os=unicos + ;; + *) + basic_machine=$1 + basic_os= + ;; + esac + ;; +esac + +# Decode 1-component or ad-hoc basic machines +case $basic_machine in + # Here we handle the default manufacturer of certain CPU types. It is in + # some cases the only manufacturer, in others, it is the most popular. + w89k) + cpu=hppa1.1 + vendor=winbond + ;; + op50n) + cpu=hppa1.1 + vendor=oki + ;; + op60c) + cpu=hppa1.1 + vendor=oki + ;; + ibm*) + cpu=i370 + vendor=ibm + ;; + orion105) + cpu=clipper + vendor=highlevel + ;; + mac | mpw | mac-mpw) + cpu=m68k + vendor=apple + ;; + pmac | pmac-mpw) + cpu=powerpc + vendor=apple + ;; + + # Recognize the various machine names and aliases which stand + # for a CPU type and a company and sometimes even an OS. + 3b1 | 7300 | 7300-att | att-7300 | pc7300 | safari | unixpc) + cpu=m68000 + vendor=att + ;; + 3b*) + cpu=we32k + vendor=att + ;; + bluegene*) + cpu=powerpc + vendor=ibm + basic_os=cnk + ;; + decsystem10* | dec10*) + cpu=pdp10 + vendor=dec + basic_os=tops10 + ;; + decsystem20* | dec20*) + cpu=pdp10 + vendor=dec + basic_os=tops20 + ;; + delta | 3300 | motorola-3300 | motorola-delta \ + | 3300-motorola | delta-motorola) + cpu=m68k + vendor=motorola + ;; + dpx2*) + cpu=m68k + vendor=bull + basic_os=sysv3 + ;; + encore | umax | mmax) + cpu=ns32k + vendor=encore + ;; + elxsi) + cpu=elxsi + vendor=elxsi + basic_os=${basic_os:-bsd} + ;; + fx2800) + cpu=i860 + vendor=alliant + ;; + genix) + cpu=ns32k + vendor=ns + ;; + h3050r* | hiux*) + cpu=hppa1.1 + vendor=hitachi + basic_os=hiuxwe2 + ;; + hp3k9[0-9][0-9] | hp9[0-9][0-9]) + cpu=hppa1.0 + vendor=hp + ;; + hp9k2[0-9][0-9] | hp9k31[0-9]) + cpu=m68000 + vendor=hp + ;; + hp9k3[2-9][0-9]) + cpu=m68k + vendor=hp + ;; + hp9k6[0-9][0-9] | hp6[0-9][0-9]) + cpu=hppa1.0 + vendor=hp + ;; + hp9k7[0-79][0-9] | hp7[0-79][0-9]) + cpu=hppa1.1 + vendor=hp + ;; + hp9k78[0-9] | hp78[0-9]) + # FIXME: really hppa2.0-hp + cpu=hppa1.1 + vendor=hp + ;; + hp9k8[67]1 | hp8[67]1 | hp9k80[24] | hp80[24] | hp9k8[78]9 | hp8[78]9 | hp9k893 | hp893) + # FIXME: really hppa2.0-hp + cpu=hppa1.1 + vendor=hp + ;; + hp9k8[0-9][13679] | hp8[0-9][13679]) + cpu=hppa1.1 + vendor=hp + ;; + hp9k8[0-9][0-9] | hp8[0-9][0-9]) + cpu=hppa1.0 + vendor=hp + ;; + i*86v32) + cpu=`echo "$1" | sed -e 's/86.*/86/'` + vendor=pc + basic_os=sysv32 + ;; + i*86v4*) + cpu=`echo "$1" | sed -e 's/86.*/86/'` + vendor=pc + basic_os=sysv4 + ;; + i*86v) + cpu=`echo "$1" | sed -e 's/86.*/86/'` + vendor=pc + basic_os=sysv + ;; + i*86sol2) + cpu=`echo "$1" | sed -e 's/86.*/86/'` + vendor=pc + basic_os=solaris2 + ;; + j90 | j90-cray) + cpu=j90 + vendor=cray + basic_os=${basic_os:-unicos} + ;; + iris | iris4d) + cpu=mips + vendor=sgi + case $basic_os in + irix*) + ;; + *) + basic_os=irix4 + ;; + esac + ;; + miniframe) + cpu=m68000 + vendor=convergent + ;; + *mint | mint[0-9]* | *MiNT | *MiNT[0-9]*) + cpu=m68k + vendor=atari + basic_os=mint + ;; + news-3600 | risc-news) + cpu=mips + vendor=sony + basic_os=newsos + ;; + next | m*-next) + cpu=m68k + vendor=next + case $basic_os in + openstep*) + ;; + nextstep*) + ;; + ns2*) + basic_os=nextstep2 + ;; + *) + basic_os=nextstep3 + ;; + esac + ;; + np1) + cpu=np1 + vendor=gould + ;; + op50n-* | op60c-*) + cpu=hppa1.1 + vendor=oki + basic_os=proelf + ;; + pa-hitachi) + cpu=hppa1.1 + vendor=hitachi + basic_os=hiuxwe2 + ;; + pbd) + cpu=sparc + vendor=tti + ;; + pbb) + cpu=m68k + vendor=tti + ;; + pc532) + cpu=ns32k + vendor=pc532 + ;; + pn) + cpu=pn + vendor=gould + ;; + power) + cpu=power + vendor=ibm + ;; + ps2) + cpu=i386 + vendor=ibm + ;; + rm[46]00) + cpu=mips + vendor=siemens + ;; + rtpc | rtpc-*) + cpu=romp + vendor=ibm + ;; + sde) + cpu=mipsisa32 + vendor=sde + basic_os=${basic_os:-elf} + ;; + simso-wrs) + cpu=sparclite + vendor=wrs + basic_os=vxworks + ;; + tower | tower-32) + cpu=m68k + vendor=ncr + ;; + vpp*|vx|vx-*) + cpu=f301 + vendor=fujitsu + ;; + w65) + cpu=w65 + vendor=wdc + ;; + w89k-*) + cpu=hppa1.1 + vendor=winbond + basic_os=proelf + ;; + none) + cpu=none + vendor=none + ;; + leon|leon[3-9]) + cpu=sparc + vendor=$basic_machine + ;; + leon-*|leon[3-9]-*) + cpu=sparc + vendor=`echo "$basic_machine" | sed 's/-.*//'` + ;; + + *-*) + # shellcheck disable=SC2162 + saved_IFS=$IFS + IFS="-" read cpu vendor <&2 + exit 1 + ;; + esac + ;; +esac + +# Here we canonicalize certain aliases for manufacturers. +case $vendor in + digital*) + vendor=dec + ;; + commodore*) + vendor=cbm + ;; + *) + ;; +esac + +# Decode manufacturer-specific aliases for certain operating systems. + +if test x$basic_os != x +then + +# First recognize some ad-hoc cases, or perhaps split kernel-os, or else just +# set os. +case $basic_os in + gnu/linux*) + kernel=linux + os=`echo "$basic_os" | sed -e 's|gnu/linux|gnu|'` + ;; + os2-emx) + kernel=os2 + os=`echo "$basic_os" | sed -e 's|os2-emx|emx|'` + ;; + nto-qnx*) + kernel=nto + os=`echo "$basic_os" | sed -e 's|nto-qnx|qnx|'` + ;; + *-*) + # shellcheck disable=SC2162 + saved_IFS=$IFS + IFS="-" read kernel os <&2 + exit 1 + ;; +esac + +# As a final step for OS-related things, validate the OS-kernel combination +# (given a valid OS), if there is a kernel. +case $kernel-$os in + linux-gnu* | linux-dietlibc* | linux-android* | linux-newlib* \ + | linux-musl* | linux-relibc* | linux-uclibc* | linux-mlibc* ) + ;; + uclinux-uclibc* ) + ;; + managarm-mlibc* | managarm-kernel* ) + ;; + windows*-gnu* | windows*-msvc*) + ;; + -dietlibc* | -newlib* | -musl* | -relibc* | -uclibc* | -mlibc* ) + # These are just libc implementations, not actual OSes, and thus + # require a kernel. + echo "Invalid configuration '$1': libc '$os' needs explicit kernel." 1>&2 + exit 1 + ;; + -kernel* ) + echo "Invalid configuration '$1': '$os' needs explicit kernel." 1>&2 + exit 1 + ;; + *-kernel* ) + echo "Invalid configuration '$1': '$kernel' does not support '$os'." 1>&2 + exit 1 + ;; + *-msvc* ) + echo "Invalid configuration '$1': '$os' needs 'windows'." 1>&2 + exit 1 + ;; + kfreebsd*-gnu* | kopensolaris*-gnu*) + ;; + vxworks-simlinux | vxworks-simwindows | vxworks-spe) + ;; + nto-qnx*) + ;; + os2-emx) + ;; + *-eabi* | *-gnueabi*) + ;; + none-coff* | none-elf*) + # None (no kernel, i.e. freestanding / bare metal), + # can be paired with an output format "OS" + ;; + -*) + # Blank kernel with real OS is always fine. + ;; + *-*) + echo "Invalid configuration '$1': Kernel '$kernel' not known to work with OS '$os'." 1>&2 + exit 1 + ;; +esac + +# Here we handle the case where we know the os, and the CPU type, but not the +# manufacturer. We pick the logical manufacturer. +case $vendor in + unknown) + case $cpu-$os in + *-riscix*) + vendor=acorn + ;; + *-sunos*) + vendor=sun + ;; + *-cnk* | *-aix*) + vendor=ibm + ;; + *-beos*) + vendor=be + ;; + *-hpux*) + vendor=hp + ;; + *-mpeix*) + vendor=hp + ;; + *-hiux*) + vendor=hitachi + ;; + *-unos*) + vendor=crds + ;; + *-dgux*) + vendor=dg + ;; + *-luna*) + vendor=omron + ;; + *-genix*) + vendor=ns + ;; + *-clix*) + vendor=intergraph + ;; + *-mvs* | *-opened*) + vendor=ibm + ;; + *-os400*) + vendor=ibm + ;; + s390-* | s390x-*) + vendor=ibm + ;; + *-ptx*) + vendor=sequent + ;; + *-tpf*) + vendor=ibm + ;; + *-vxsim* | *-vxworks* | *-windiss*) + vendor=wrs + ;; + *-aux*) + vendor=apple + ;; + *-hms*) + vendor=hitachi + ;; + *-mpw* | *-macos*) + vendor=apple + ;; + *-*mint | *-mint[0-9]* | *-*MiNT | *-MiNT[0-9]*) + vendor=atari + ;; + *-vos*) + vendor=stratus + ;; + esac + ;; +esac + +echo "$cpu-$vendor-${kernel:+$kernel-}$os" +exit + +# Local variables: +# eval: (add-hook 'before-save-hook 'time-stamp) +# time-stamp-start: "timestamp='" +# time-stamp-format: "%:y-%02m-%02d" +# time-stamp-end: "'" +# End: diff --git a/3rdparty/freetype-2.13.2/builds/unix/configure b/3rdparty/freetype-2.13.2/builds/unix/configure new file mode 100644 index 000000000..580f18c3c --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/configure @@ -0,0 +1,18950 @@ +#! /bin/sh +# Guess values for system-dependent variables and create Makefiles. +# Generated by GNU Autoconf 2.71 for FreeType 2.13.2. +# +# Report bugs to . +# +# +# Copyright (C) 1992-1996, 1998-2017, 2020-2021 Free Software Foundation, +# Inc. +# +# +# This configure script is free software; the Free Software Foundation +# gives unlimited permission to copy, distribute and modify it. +## -------------------- ## +## M4sh Initialization. ## +## -------------------- ## + +# Be more Bourne compatible +DUALCASE=1; export DUALCASE # for MKS sh +as_nop=: +if test ${ZSH_VERSION+y} && (emulate sh) >/dev/null 2>&1 +then : + emulate sh + NULLCMD=: + # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which + # is contrary to our usage. Disable this feature. + alias -g '${1+"$@"}'='"$@"' + setopt NO_GLOB_SUBST +else $as_nop + case `(set -o) 2>/dev/null` in #( + *posix*) : + set -o posix ;; #( + *) : + ;; +esac +fi + + + +# Reset variables that may have inherited troublesome values from +# the environment. + +# IFS needs to be set, to space, tab, and newline, in precisely that order. +# (If _AS_PATH_WALK were called with IFS unset, it would have the +# side effect of setting IFS to empty, thus disabling word splitting.) +# Quoting is to prevent editors from complaining about space-tab. +as_nl=' +' +export as_nl +IFS=" "" $as_nl" + +PS1='$ ' +PS2='> ' +PS4='+ ' + +# Ensure predictable behavior from utilities with locale-dependent output. +LC_ALL=C +export LC_ALL +LANGUAGE=C +export LANGUAGE + +# We cannot yet rely on "unset" to work, but we need these variables +# to be unset--not just set to an empty or harmless value--now, to +# avoid bugs in old shells (e.g. pre-3.0 UWIN ksh). This construct +# also avoids known problems related to "unset" and subshell syntax +# in other old shells (e.g. bash 2.01 and pdksh 5.2.14). +for as_var in BASH_ENV ENV MAIL MAILPATH CDPATH +do eval test \${$as_var+y} \ + && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || : +done + +# Ensure that fds 0, 1, and 2 are open. +if (exec 3>&0) 2>/dev/null; then :; else exec 0&1) 2>/dev/null; then :; else exec 1>/dev/null; fi +if (exec 3>&2) ; then :; else exec 2>/dev/null; fi + +# The user is always right. +if ${PATH_SEPARATOR+false} :; then + PATH_SEPARATOR=: + (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && { + (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 || + PATH_SEPARATOR=';' + } +fi + + +# Find who we are. Look in the path if we contain no directory separator. +as_myself= +case $0 in #(( + *[\\/]* ) as_myself=$0 ;; + *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + test -r "$as_dir$0" && as_myself=$as_dir$0 && break + done +IFS=$as_save_IFS + + ;; +esac +# We did not find ourselves, most probably we were run as `sh COMMAND' +# in which case we are not to be found in the path. +if test "x$as_myself" = x; then + as_myself=$0 +fi +if test ! -f "$as_myself"; then + printf "%s\n" "$as_myself: error: cannot find myself; rerun with an absolute file name" >&2 + exit 1 +fi + + +# Use a proper internal environment variable to ensure we don't fall + # into an infinite loop, continuously re-executing ourselves. + if test x"${_as_can_reexec}" != xno && test "x$CONFIG_SHELL" != x; then + _as_can_reexec=no; export _as_can_reexec; + # We cannot yet assume a decent shell, so we have to provide a +# neutralization value for shells without unset; and this also +# works around shells that cannot unset nonexistent variables. +# Preserve -v and -x to the replacement shell. +BASH_ENV=/dev/null +ENV=/dev/null +(unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV +case $- in # (((( + *v*x* | *x*v* ) as_opts=-vx ;; + *v* ) as_opts=-v ;; + *x* ) as_opts=-x ;; + * ) as_opts= ;; +esac +exec $CONFIG_SHELL $as_opts "$as_myself" ${1+"$@"} +# Admittedly, this is quite paranoid, since all the known shells bail +# out after a failed `exec'. +printf "%s\n" "$0: could not re-execute with $CONFIG_SHELL" >&2 +exit 255 + fi + # We don't want this to propagate to other subprocesses. + { _as_can_reexec=; unset _as_can_reexec;} +if test "x$CONFIG_SHELL" = x; then + as_bourne_compatible="as_nop=: +if test \${ZSH_VERSION+y} && (emulate sh) >/dev/null 2>&1 +then : + emulate sh + NULLCMD=: + # Pre-4.2 versions of Zsh do word splitting on \${1+\"\$@\"}, which + # is contrary to our usage. Disable this feature. + alias -g '\${1+\"\$@\"}'='\"\$@\"' + setopt NO_GLOB_SUBST +else \$as_nop + case \`(set -o) 2>/dev/null\` in #( + *posix*) : + set -o posix ;; #( + *) : + ;; +esac +fi +" + as_required="as_fn_return () { (exit \$1); } +as_fn_success () { as_fn_return 0; } +as_fn_failure () { as_fn_return 1; } +as_fn_ret_success () { return 0; } +as_fn_ret_failure () { return 1; } + +exitcode=0 +as_fn_success || { exitcode=1; echo as_fn_success failed.; } +as_fn_failure && { exitcode=1; echo as_fn_failure succeeded.; } +as_fn_ret_success || { exitcode=1; echo as_fn_ret_success failed.; } +as_fn_ret_failure && { exitcode=1; echo as_fn_ret_failure succeeded.; } +if ( set x; as_fn_ret_success y && test x = \"\$1\" ) +then : + +else \$as_nop + exitcode=1; echo positional parameters were not saved. +fi +test x\$exitcode = x0 || exit 1 +blah=\$(echo \$(echo blah)) +test x\"\$blah\" = xblah || exit 1 +test -x / || exit 1" + as_suggested=" as_lineno_1=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_1a=\$LINENO + as_lineno_2=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_2a=\$LINENO + eval 'test \"x\$as_lineno_1'\$as_run'\" != \"x\$as_lineno_2'\$as_run'\" && + test \"x\`expr \$as_lineno_1'\$as_run' + 1\`\" = \"x\$as_lineno_2'\$as_run'\"' || exit 1 + + test -n \"\${ZSH_VERSION+set}\${BASH_VERSION+set}\" || ( + ECHO='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' + ECHO=\$ECHO\$ECHO\$ECHO\$ECHO\$ECHO + ECHO=\$ECHO\$ECHO\$ECHO\$ECHO\$ECHO\$ECHO + PATH=/empty FPATH=/empty; export PATH FPATH + test \"X\`printf %s \$ECHO\`\" = \"X\$ECHO\" \\ + || test \"X\`print -r -- \$ECHO\`\" = \"X\$ECHO\" ) || exit 1 +test \$(( 1 + 1 )) = 2 || exit 1" + if (eval "$as_required") 2>/dev/null +then : + as_have_required=yes +else $as_nop + as_have_required=no +fi + if test x$as_have_required = xyes && (eval "$as_suggested") 2>/dev/null +then : + +else $as_nop + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +as_found=false +for as_dir in /bin$PATH_SEPARATOR/usr/bin$PATH_SEPARATOR$PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + as_found=: + case $as_dir in #( + /*) + for as_base in sh bash ksh sh5; do + # Try only shells that exist, to save several forks. + as_shell=$as_dir$as_base + if { test -f "$as_shell" || test -f "$as_shell.exe"; } && + as_run=a "$as_shell" -c "$as_bourne_compatible""$as_required" 2>/dev/null +then : + CONFIG_SHELL=$as_shell as_have_required=yes + if as_run=a "$as_shell" -c "$as_bourne_compatible""$as_suggested" 2>/dev/null +then : + break 2 +fi +fi + done;; + esac + as_found=false +done +IFS=$as_save_IFS +if $as_found +then : + +else $as_nop + if { test -f "$SHELL" || test -f "$SHELL.exe"; } && + as_run=a "$SHELL" -c "$as_bourne_compatible""$as_required" 2>/dev/null +then : + CONFIG_SHELL=$SHELL as_have_required=yes +fi +fi + + + if test "x$CONFIG_SHELL" != x +then : + export CONFIG_SHELL + # We cannot yet assume a decent shell, so we have to provide a +# neutralization value for shells without unset; and this also +# works around shells that cannot unset nonexistent variables. +# Preserve -v and -x to the replacement shell. +BASH_ENV=/dev/null +ENV=/dev/null +(unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV +case $- in # (((( + *v*x* | *x*v* ) as_opts=-vx ;; + *v* ) as_opts=-v ;; + *x* ) as_opts=-x ;; + * ) as_opts= ;; +esac +exec $CONFIG_SHELL $as_opts "$as_myself" ${1+"$@"} +# Admittedly, this is quite paranoid, since all the known shells bail +# out after a failed `exec'. +printf "%s\n" "$0: could not re-execute with $CONFIG_SHELL" >&2 +exit 255 +fi + + if test x$as_have_required = xno +then : + printf "%s\n" "$0: This script requires a shell more modern than all" + printf "%s\n" "$0: the shells that I found on your system." + if test ${ZSH_VERSION+y} ; then + printf "%s\n" "$0: In particular, zsh $ZSH_VERSION has bugs and should" + printf "%s\n" "$0: be upgraded to zsh 4.3.4 or later." + else + printf "%s\n" "$0: Please tell bug-autoconf@gnu.org and +$0: freetype@nongnu.org about your system, including any +$0: error possibly output before this message. Then install +$0: a modern shell, or manually run the script under such a +$0: shell if you do have one." + fi + exit 1 +fi +fi +fi +SHELL=${CONFIG_SHELL-/bin/sh} +export SHELL +# Unset more variables known to interfere with behavior of common tools. +CLICOLOR_FORCE= GREP_OPTIONS= +unset CLICOLOR_FORCE GREP_OPTIONS + +## --------------------- ## +## M4sh Shell Functions. ## +## --------------------- ## +# as_fn_unset VAR +# --------------- +# Portably unset VAR. +as_fn_unset () +{ + { eval $1=; unset $1;} +} +as_unset=as_fn_unset + + +# as_fn_set_status STATUS +# ----------------------- +# Set $? to STATUS, without forking. +as_fn_set_status () +{ + return $1 +} # as_fn_set_status + +# as_fn_exit STATUS +# ----------------- +# Exit the shell with STATUS, even in a "trap 0" or "set -e" context. +as_fn_exit () +{ + set +e + as_fn_set_status $1 + exit $1 +} # as_fn_exit +# as_fn_nop +# --------- +# Do nothing but, unlike ":", preserve the value of $?. +as_fn_nop () +{ + return $? +} +as_nop=as_fn_nop + +# as_fn_mkdir_p +# ------------- +# Create "$as_dir" as a directory, including parents if necessary. +as_fn_mkdir_p () +{ + + case $as_dir in #( + -*) as_dir=./$as_dir;; + esac + test -d "$as_dir" || eval $as_mkdir_p || { + as_dirs= + while :; do + case $as_dir in #( + *\'*) as_qdir=`printf "%s\n" "$as_dir" | sed "s/'/'\\\\\\\\''/g"`;; #'( + *) as_qdir=$as_dir;; + esac + as_dirs="'$as_qdir' $as_dirs" + as_dir=`$as_dirname -- "$as_dir" || +$as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ + X"$as_dir" : 'X\(//\)[^/]' \| \ + X"$as_dir" : 'X\(//\)$' \| \ + X"$as_dir" : 'X\(/\)' \| . 2>/dev/null || +printf "%s\n" X"$as_dir" | + sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ + s//\1/ + q + } + /^X\(\/\/\)[^/].*/{ + s//\1/ + q + } + /^X\(\/\/\)$/{ + s//\1/ + q + } + /^X\(\/\).*/{ + s//\1/ + q + } + s/.*/./; q'` + test -d "$as_dir" && break + done + test -z "$as_dirs" || eval "mkdir $as_dirs" + } || test -d "$as_dir" || as_fn_error $? "cannot create directory $as_dir" + + +} # as_fn_mkdir_p + +# as_fn_executable_p FILE +# ----------------------- +# Test if FILE is an executable regular file. +as_fn_executable_p () +{ + test -f "$1" && test -x "$1" +} # as_fn_executable_p +# as_fn_append VAR VALUE +# ---------------------- +# Append the text in VALUE to the end of the definition contained in VAR. Take +# advantage of any shell optimizations that allow amortized linear growth over +# repeated appends, instead of the typical quadratic growth present in naive +# implementations. +if (eval "as_var=1; as_var+=2; test x\$as_var = x12") 2>/dev/null +then : + eval 'as_fn_append () + { + eval $1+=\$2 + }' +else $as_nop + as_fn_append () + { + eval $1=\$$1\$2 + } +fi # as_fn_append + +# as_fn_arith ARG... +# ------------------ +# Perform arithmetic evaluation on the ARGs, and store the result in the +# global $as_val. Take advantage of shells that can avoid forks. The arguments +# must be portable across $(()) and expr. +if (eval "test \$(( 1 + 1 )) = 2") 2>/dev/null +then : + eval 'as_fn_arith () + { + as_val=$(( $* )) + }' +else $as_nop + as_fn_arith () + { + as_val=`expr "$@" || test $? -eq 1` + } +fi # as_fn_arith + +# as_fn_nop +# --------- +# Do nothing but, unlike ":", preserve the value of $?. +as_fn_nop () +{ + return $? +} +as_nop=as_fn_nop + +# as_fn_error STATUS ERROR [LINENO LOG_FD] +# ---------------------------------------- +# Output "`basename $0`: error: ERROR" to stderr. If LINENO and LOG_FD are +# provided, also output the error to LOG_FD, referencing LINENO. Then exit the +# script with STATUS, using 1 if that was 0. +as_fn_error () +{ + as_status=$1; test $as_status -eq 0 && as_status=1 + if test "$4"; then + as_lineno=${as_lineno-"$3"} as_lineno_stack=as_lineno_stack=$as_lineno_stack + printf "%s\n" "$as_me:${as_lineno-$LINENO}: error: $2" >&$4 + fi + printf "%s\n" "$as_me: error: $2" >&2 + as_fn_exit $as_status +} # as_fn_error + +if expr a : '\(a\)' >/dev/null 2>&1 && + test "X`expr 00001 : '.*\(...\)'`" = X001; then + as_expr=expr +else + as_expr=false +fi + +if (basename -- /) >/dev/null 2>&1 && test "X`basename -- / 2>&1`" = "X/"; then + as_basename=basename +else + as_basename=false +fi + +if (as_dir=`dirname -- /` && test "X$as_dir" = X/) >/dev/null 2>&1; then + as_dirname=dirname +else + as_dirname=false +fi + +as_me=`$as_basename -- "$0" || +$as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \ + X"$0" : 'X\(//\)$' \| \ + X"$0" : 'X\(/\)' \| . 2>/dev/null || +printf "%s\n" X/"$0" | + sed '/^.*\/\([^/][^/]*\)\/*$/{ + s//\1/ + q + } + /^X\/\(\/\/\)$/{ + s//\1/ + q + } + /^X\/\(\/\).*/{ + s//\1/ + q + } + s/.*/./; q'` + +# Avoid depending upon Character Ranges. +as_cr_letters='abcdefghijklmnopqrstuvwxyz' +as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ' +as_cr_Letters=$as_cr_letters$as_cr_LETTERS +as_cr_digits='0123456789' +as_cr_alnum=$as_cr_Letters$as_cr_digits + + + as_lineno_1=$LINENO as_lineno_1a=$LINENO + as_lineno_2=$LINENO as_lineno_2a=$LINENO + eval 'test "x$as_lineno_1'$as_run'" != "x$as_lineno_2'$as_run'" && + test "x`expr $as_lineno_1'$as_run' + 1`" = "x$as_lineno_2'$as_run'"' || { + # Blame Lee E. McMahon (1931-1989) for sed's syntax. :-) + sed -n ' + p + /[$]LINENO/= + ' <$as_myself | + sed ' + s/[$]LINENO.*/&-/ + t lineno + b + :lineno + N + :loop + s/[$]LINENO\([^'$as_cr_alnum'_].*\n\)\(.*\)/\2\1\2/ + t loop + s/-\n.*// + ' >$as_me.lineno && + chmod +x "$as_me.lineno" || + { printf "%s\n" "$as_me: error: cannot create $as_me.lineno; rerun with a POSIX shell" >&2; as_fn_exit 1; } + + # If we had to re-execute with $CONFIG_SHELL, we're ensured to have + # already done that, so ensure we don't try to do so again and fall + # in an infinite loop. This has already happened in practice. + _as_can_reexec=no; export _as_can_reexec + # Don't try to exec as it changes $[0], causing all sort of problems + # (the dirname of $[0] is not the place where we might find the + # original and so on. Autoconf is especially sensitive to this). + . "./$as_me.lineno" + # Exit status is that of the last command. + exit +} + + +# Determine whether it's possible to make 'echo' print without a newline. +# These variables are no longer used directly by Autoconf, but are AC_SUBSTed +# for compatibility with existing Makefiles. +ECHO_C= ECHO_N= ECHO_T= +case `echo -n x` in #((((( +-n*) + case `echo 'xy\c'` in + *c*) ECHO_T=' ';; # ECHO_T is single tab character. + xy) ECHO_C='\c';; + *) echo `echo ksh88 bug on AIX 6.1` > /dev/null + ECHO_T=' ';; + esac;; +*) + ECHO_N='-n';; +esac + +# For backward compatibility with old third-party macros, we provide +# the shell variables $as_echo and $as_echo_n. New code should use +# AS_ECHO(["message"]) and AS_ECHO_N(["message"]), respectively. +as_echo='printf %s\n' +as_echo_n='printf %s' + + +rm -f conf$$ conf$$.exe conf$$.file +if test -d conf$$.dir; then + rm -f conf$$.dir/conf$$.file +else + rm -f conf$$.dir + mkdir conf$$.dir 2>/dev/null +fi +if (echo >conf$$.file) 2>/dev/null; then + if ln -s conf$$.file conf$$ 2>/dev/null; then + as_ln_s='ln -s' + # ... but there are two gotchas: + # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail. + # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable. + # In both cases, we have to default to `cp -pR'. + ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe || + as_ln_s='cp -pR' + elif ln conf$$.file conf$$ 2>/dev/null; then + as_ln_s=ln + else + as_ln_s='cp -pR' + fi +else + as_ln_s='cp -pR' +fi +rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file +rmdir conf$$.dir 2>/dev/null + +if mkdir -p . 2>/dev/null; then + as_mkdir_p='mkdir -p "$as_dir"' +else + test -d ./-p && rmdir ./-p + as_mkdir_p=false +fi + +as_test_x='test -x' +as_executable_p=as_fn_executable_p + +# Sed expression to map a string onto a valid CPP name. +as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'" + +# Sed expression to map a string onto a valid variable name. +as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'" + +SHELL=${CONFIG_SHELL-/bin/sh} + + +test -n "$DJDIR" || exec 7<&0 &1 + +# Name of the host. +# hostname on some systems (SVR3.2, old GNU/Linux) returns a bogus exit status, +# so uname gets run too. +ac_hostname=`(hostname || uname -n) 2>/dev/null | sed 1q` + +# +# Initializations. +# +ac_default_prefix=/usr/local +ac_clean_files= +ac_config_libobj_dir=. +LIBOBJS= +cross_compiling=no +subdirs= +MFLAGS= +MAKEFLAGS= + +# Identity of this package. +PACKAGE_NAME='FreeType' +PACKAGE_TARNAME='freetype' +PACKAGE_VERSION='2.13.2' +PACKAGE_STRING='FreeType 2.13.2' +PACKAGE_BUGREPORT='freetype@nongnu.org' +PACKAGE_URL='' + +ac_unique_file="ftconfig.h.in" +# Factoring default headers for most tests. +ac_includes_default="\ +#include +#ifdef HAVE_STDIO_H +# include +#endif +#ifdef HAVE_STDLIB_H +# include +#endif +#ifdef HAVE_STRING_H +# include +#endif +#ifdef HAVE_INTTYPES_H +# include +#endif +#ifdef HAVE_STDINT_H +# include +#endif +#ifdef HAVE_STRINGS_H +# include +#endif +#ifdef HAVE_SYS_TYPES_H +# include +#endif +#ifdef HAVE_SYS_STAT_H +# include +#endif +#ifdef HAVE_UNISTD_H +# include +#endif" + +ac_header_c_list= +ac_func_c_list= +ac_subst_vars='LTLIBOBJS +LIBOBJS +build_libtool_libs +wl +hardcode_libdir_flag_spec +LIBSSTATIC_CONFIG +PKGCONFIG_LIBS_PRIVATE +PKGCONFIG_REQUIRES_PRIVATE +PKGCONFIG_LIBS +PKGCONFIG_REQUIRES +ftmac_c +PYTHON_VERSION +PYTHON +PTHREAD_CFLAGS +PTHREAD_LIBS +PTHREAD_CXX +PTHREAD_CC +ax_pthread_config +target_os +target_vendor +target_cpu +target +FT_DEMO_LDFLAGS +FT_DEMO_CFLAGS +LIBRSVG_LIBS +LIBRSVG_CFLAGS +BROTLI_LIBS +BROTLI_CFLAGS +HARFBUZZ_LIBS +HARFBUZZ_CFLAGS +have_libpng +LIBPNG_LIBS +LIBPNG_CFLAGS +BZIP2_LIBS +BZIP2_CFLAGS +SYSTEM_ZLIB +ZLIB_LIBS +ZLIB_CFLAGS +XX_ANSIFLAGS +XX_CFLAGS +FTSYS_SRC +INSTALL_FT2_CONFIG +MKDIR_P +INSTALL_DATA +INSTALL_SCRIPT +INSTALL_PROGRAM +EXEEXT_BUILD +CC_BUILD +RC +LT_SYS_LIBRARY_PATH +OTOOL64 +OTOOL +LIPO +NMEDIT +DSYMUTIL +MANIFEST_TOOL +AWK +RANLIB +STRIP +ac_ct_AR +AR +FILECMD +LN_S +NM +ac_ct_DUMPBIN +DUMPBIN +LD +FGREP +EGREP +GREP +SED +LIBTOOL +OBJDUMP +DLLTOOL +AS +PKG_CONFIG_LIBDIR +PKG_CONFIG_PATH +PKG_CONFIG +CPP +OBJEXT +EXEEXT +ac_ct_CC +CPPFLAGS +LDFLAGS +CFLAGS +CC +host_os +host_vendor +host_cpu +host +build_os +build_vendor +build_cpu +build +ft_version +version_info +target_alias +host_alias +build_alias +LIBS +ECHO_T +ECHO_N +ECHO_C +DEFS +mandir +localedir +libdir +psdir +pdfdir +dvidir +htmldir +infodir +docdir +oldincludedir +includedir +runstatedir +localstatedir +sharedstatedir +sysconfdir +datadir +datarootdir +libexecdir +sbindir +bindir +program_transform_name +prefix +exec_prefix +PACKAGE_URL +PACKAGE_BUGREPORT +PACKAGE_STRING +PACKAGE_VERSION +PACKAGE_TARNAME +PACKAGE_NAME +PATH_SEPARATOR +SHELL' +ac_subst_files='' +ac_user_opts=' +enable_option_checking +enable_shared +enable_static +with_pic +enable_fast_install +with_aix_soname +with_gnu_ld +with_sysroot +enable_libtool_lock +enable_freetype_config +enable_largefile +enable_mmap +with_zlib +with_bzip2 +with_png +with_harfbuzz +with_brotli +with_librsvg +with_old_mac_fonts +with_fsspec +with_fsref +with_quickdraw_toolbox +with_quickdraw_carbon +with_ats +' + ac_precious_vars='build_alias +host_alias +target_alias +CC +CFLAGS +LDFLAGS +LIBS +CPPFLAGS +CPP +PKG_CONFIG +PKG_CONFIG_PATH +PKG_CONFIG_LIBDIR +LT_SYS_LIBRARY_PATH +ZLIB_CFLAGS +ZLIB_LIBS +BZIP2_CFLAGS +BZIP2_LIBS +LIBPNG_CFLAGS +LIBPNG_LIBS +HARFBUZZ_CFLAGS +HARFBUZZ_LIBS +BROTLI_CFLAGS +BROTLI_LIBS +LIBRSVG_CFLAGS +LIBRSVG_LIBS' + + +# Initialize some variables set by options. +ac_init_help= +ac_init_version=false +ac_unrecognized_opts= +ac_unrecognized_sep= +# The variables have the same names as the options, with +# dashes changed to underlines. +cache_file=/dev/null +exec_prefix=NONE +no_create= +no_recursion= +prefix=NONE +program_prefix=NONE +program_suffix=NONE +program_transform_name=s,x,x, +silent= +site= +srcdir= +verbose= +x_includes=NONE +x_libraries=NONE + +# Installation directory options. +# These are left unexpanded so users can "make install exec_prefix=/foo" +# and all the variables that are supposed to be based on exec_prefix +# by default will actually change. +# Use braces instead of parens because sh, perl, etc. also accept them. +# (The list follows the same order as the GNU Coding Standards.) +bindir='${exec_prefix}/bin' +sbindir='${exec_prefix}/sbin' +libexecdir='${exec_prefix}/libexec' +datarootdir='${prefix}/share' +datadir='${datarootdir}' +sysconfdir='${prefix}/etc' +sharedstatedir='${prefix}/com' +localstatedir='${prefix}/var' +runstatedir='${localstatedir}/run' +includedir='${prefix}/include' +oldincludedir='/usr/include' +docdir='${datarootdir}/doc/${PACKAGE_TARNAME}' +infodir='${datarootdir}/info' +htmldir='${docdir}' +dvidir='${docdir}' +pdfdir='${docdir}' +psdir='${docdir}' +libdir='${exec_prefix}/lib' +localedir='${datarootdir}/locale' +mandir='${datarootdir}/man' + +ac_prev= +ac_dashdash= +for ac_option +do + # If the previous option needs an argument, assign it. + if test -n "$ac_prev"; then + eval $ac_prev=\$ac_option + ac_prev= + continue + fi + + case $ac_option in + *=?*) ac_optarg=`expr "X$ac_option" : '[^=]*=\(.*\)'` ;; + *=) ac_optarg= ;; + *) ac_optarg=yes ;; + esac + + case $ac_dashdash$ac_option in + --) + ac_dashdash=yes ;; + + -bindir | --bindir | --bindi | --bind | --bin | --bi) + ac_prev=bindir ;; + -bindir=* | --bindir=* | --bindi=* | --bind=* | --bin=* | --bi=*) + bindir=$ac_optarg ;; + + -build | --build | --buil | --bui | --bu) + ac_prev=build_alias ;; + -build=* | --build=* | --buil=* | --bui=* | --bu=*) + build_alias=$ac_optarg ;; + + -cache-file | --cache-file | --cache-fil | --cache-fi \ + | --cache-f | --cache- | --cache | --cach | --cac | --ca | --c) + ac_prev=cache_file ;; + -cache-file=* | --cache-file=* | --cache-fil=* | --cache-fi=* \ + | --cache-f=* | --cache-=* | --cache=* | --cach=* | --cac=* | --ca=* | --c=*) + cache_file=$ac_optarg ;; + + --config-cache | -C) + cache_file=config.cache ;; + + -datadir | --datadir | --datadi | --datad) + ac_prev=datadir ;; + -datadir=* | --datadir=* | --datadi=* | --datad=*) + datadir=$ac_optarg ;; + + -datarootdir | --datarootdir | --datarootdi | --datarootd | --dataroot \ + | --dataroo | --dataro | --datar) + ac_prev=datarootdir ;; + -datarootdir=* | --datarootdir=* | --datarootdi=* | --datarootd=* \ + | --dataroot=* | --dataroo=* | --dataro=* | --datar=*) + datarootdir=$ac_optarg ;; + + -disable-* | --disable-*) + ac_useropt=`expr "x$ac_option" : 'x-*disable-\(.*\)'` + # Reject names that are not valid shell variable names. + expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && + as_fn_error $? "invalid feature name: \`$ac_useropt'" + ac_useropt_orig=$ac_useropt + ac_useropt=`printf "%s\n" "$ac_useropt" | sed 's/[-+.]/_/g'` + case $ac_user_opts in + *" +"enable_$ac_useropt" +"*) ;; + *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--disable-$ac_useropt_orig" + ac_unrecognized_sep=', ';; + esac + eval enable_$ac_useropt=no ;; + + -docdir | --docdir | --docdi | --doc | --do) + ac_prev=docdir ;; + -docdir=* | --docdir=* | --docdi=* | --doc=* | --do=*) + docdir=$ac_optarg ;; + + -dvidir | --dvidir | --dvidi | --dvid | --dvi | --dv) + ac_prev=dvidir ;; + -dvidir=* | --dvidir=* | --dvidi=* | --dvid=* | --dvi=* | --dv=*) + dvidir=$ac_optarg ;; + + -enable-* | --enable-*) + ac_useropt=`expr "x$ac_option" : 'x-*enable-\([^=]*\)'` + # Reject names that are not valid shell variable names. + expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && + as_fn_error $? "invalid feature name: \`$ac_useropt'" + ac_useropt_orig=$ac_useropt + ac_useropt=`printf "%s\n" "$ac_useropt" | sed 's/[-+.]/_/g'` + case $ac_user_opts in + *" +"enable_$ac_useropt" +"*) ;; + *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--enable-$ac_useropt_orig" + ac_unrecognized_sep=', ';; + esac + eval enable_$ac_useropt=\$ac_optarg ;; + + -exec-prefix | --exec_prefix | --exec-prefix | --exec-prefi \ + | --exec-pref | --exec-pre | --exec-pr | --exec-p | --exec- \ + | --exec | --exe | --ex) + ac_prev=exec_prefix ;; + -exec-prefix=* | --exec_prefix=* | --exec-prefix=* | --exec-prefi=* \ + | --exec-pref=* | --exec-pre=* | --exec-pr=* | --exec-p=* | --exec-=* \ + | --exec=* | --exe=* | --ex=*) + exec_prefix=$ac_optarg ;; + + -gas | --gas | --ga | --g) + # Obsolete; use --with-gas. + with_gas=yes ;; + + -help | --help | --hel | --he | -h) + ac_init_help=long ;; + -help=r* | --help=r* | --hel=r* | --he=r* | -hr*) + ac_init_help=recursive ;; + -help=s* | --help=s* | --hel=s* | --he=s* | -hs*) + ac_init_help=short ;; + + -host | --host | --hos | --ho) + ac_prev=host_alias ;; + -host=* | --host=* | --hos=* | --ho=*) + host_alias=$ac_optarg ;; + + -htmldir | --htmldir | --htmldi | --htmld | --html | --htm | --ht) + ac_prev=htmldir ;; + -htmldir=* | --htmldir=* | --htmldi=* | --htmld=* | --html=* | --htm=* \ + | --ht=*) + htmldir=$ac_optarg ;; + + -includedir | --includedir | --includedi | --included | --include \ + | --includ | --inclu | --incl | --inc) + ac_prev=includedir ;; + -includedir=* | --includedir=* | --includedi=* | --included=* | --include=* \ + | --includ=* | --inclu=* | --incl=* | --inc=*) + includedir=$ac_optarg ;; + + -infodir | --infodir | --infodi | --infod | --info | --inf) + ac_prev=infodir ;; + -infodir=* | --infodir=* | --infodi=* | --infod=* | --info=* | --inf=*) + infodir=$ac_optarg ;; + + -libdir | --libdir | --libdi | --libd) + ac_prev=libdir ;; + -libdir=* | --libdir=* | --libdi=* | --libd=*) + libdir=$ac_optarg ;; + + -libexecdir | --libexecdir | --libexecdi | --libexecd | --libexec \ + | --libexe | --libex | --libe) + ac_prev=libexecdir ;; + -libexecdir=* | --libexecdir=* | --libexecdi=* | --libexecd=* | --libexec=* \ + | --libexe=* | --libex=* | --libe=*) + libexecdir=$ac_optarg ;; + + -localedir | --localedir | --localedi | --localed | --locale) + ac_prev=localedir ;; + -localedir=* | --localedir=* | --localedi=* | --localed=* | --locale=*) + localedir=$ac_optarg ;; + + -localstatedir | --localstatedir | --localstatedi | --localstated \ + | --localstate | --localstat | --localsta | --localst | --locals) + ac_prev=localstatedir ;; + -localstatedir=* | --localstatedir=* | --localstatedi=* | --localstated=* \ + | --localstate=* | --localstat=* | --localsta=* | --localst=* | --locals=*) + localstatedir=$ac_optarg ;; + + -mandir | --mandir | --mandi | --mand | --man | --ma | --m) + ac_prev=mandir ;; + -mandir=* | --mandir=* | --mandi=* | --mand=* | --man=* | --ma=* | --m=*) + mandir=$ac_optarg ;; + + -nfp | --nfp | --nf) + # Obsolete; use --without-fp. + with_fp=no ;; + + -no-create | --no-create | --no-creat | --no-crea | --no-cre \ + | --no-cr | --no-c | -n) + no_create=yes ;; + + -no-recursion | --no-recursion | --no-recursio | --no-recursi \ + | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r) + no_recursion=yes ;; + + -oldincludedir | --oldincludedir | --oldincludedi | --oldincluded \ + | --oldinclude | --oldinclud | --oldinclu | --oldincl | --oldinc \ + | --oldin | --oldi | --old | --ol | --o) + ac_prev=oldincludedir ;; + -oldincludedir=* | --oldincludedir=* | --oldincludedi=* | --oldincluded=* \ + | --oldinclude=* | --oldinclud=* | --oldinclu=* | --oldincl=* | --oldinc=* \ + | --oldin=* | --oldi=* | --old=* | --ol=* | --o=*) + oldincludedir=$ac_optarg ;; + + -prefix | --prefix | --prefi | --pref | --pre | --pr | --p) + ac_prev=prefix ;; + -prefix=* | --prefix=* | --prefi=* | --pref=* | --pre=* | --pr=* | --p=*) + prefix=$ac_optarg ;; + + -program-prefix | --program-prefix | --program-prefi | --program-pref \ + | --program-pre | --program-pr | --program-p) + ac_prev=program_prefix ;; + -program-prefix=* | --program-prefix=* | --program-prefi=* \ + | --program-pref=* | --program-pre=* | --program-pr=* | --program-p=*) + program_prefix=$ac_optarg ;; + + -program-suffix | --program-suffix | --program-suffi | --program-suff \ + | --program-suf | --program-su | --program-s) + ac_prev=program_suffix ;; + -program-suffix=* | --program-suffix=* | --program-suffi=* \ + | --program-suff=* | --program-suf=* | --program-su=* | --program-s=*) + program_suffix=$ac_optarg ;; + + -program-transform-name | --program-transform-name \ + | --program-transform-nam | --program-transform-na \ + | --program-transform-n | --program-transform- \ + | --program-transform | --program-transfor \ + | --program-transfo | --program-transf \ + | --program-trans | --program-tran \ + | --progr-tra | --program-tr | --program-t) + ac_prev=program_transform_name ;; + -program-transform-name=* | --program-transform-name=* \ + | --program-transform-nam=* | --program-transform-na=* \ + | --program-transform-n=* | --program-transform-=* \ + | --program-transform=* | --program-transfor=* \ + | --program-transfo=* | --program-transf=* \ + | --program-trans=* | --program-tran=* \ + | --progr-tra=* | --program-tr=* | --program-t=*) + program_transform_name=$ac_optarg ;; + + -pdfdir | --pdfdir | --pdfdi | --pdfd | --pdf | --pd) + ac_prev=pdfdir ;; + -pdfdir=* | --pdfdir=* | --pdfdi=* | --pdfd=* | --pdf=* | --pd=*) + pdfdir=$ac_optarg ;; + + -psdir | --psdir | --psdi | --psd | --ps) + ac_prev=psdir ;; + -psdir=* | --psdir=* | --psdi=* | --psd=* | --ps=*) + psdir=$ac_optarg ;; + + -q | -quiet | --quiet | --quie | --qui | --qu | --q \ + | -silent | --silent | --silen | --sile | --sil) + silent=yes ;; + + -runstatedir | --runstatedir | --runstatedi | --runstated \ + | --runstate | --runstat | --runsta | --runst | --runs \ + | --run | --ru | --r) + ac_prev=runstatedir ;; + -runstatedir=* | --runstatedir=* | --runstatedi=* | --runstated=* \ + | --runstate=* | --runstat=* | --runsta=* | --runst=* | --runs=* \ + | --run=* | --ru=* | --r=*) + runstatedir=$ac_optarg ;; + + -sbindir | --sbindir | --sbindi | --sbind | --sbin | --sbi | --sb) + ac_prev=sbindir ;; + -sbindir=* | --sbindir=* | --sbindi=* | --sbind=* | --sbin=* \ + | --sbi=* | --sb=*) + sbindir=$ac_optarg ;; + + -sharedstatedir | --sharedstatedir | --sharedstatedi \ + | --sharedstated | --sharedstate | --sharedstat | --sharedsta \ + | --sharedst | --shareds | --shared | --share | --shar \ + | --sha | --sh) + ac_prev=sharedstatedir ;; + -sharedstatedir=* | --sharedstatedir=* | --sharedstatedi=* \ + | --sharedstated=* | --sharedstate=* | --sharedstat=* | --sharedsta=* \ + | --sharedst=* | --shareds=* | --shared=* | --share=* | --shar=* \ + | --sha=* | --sh=*) + sharedstatedir=$ac_optarg ;; + + -site | --site | --sit) + ac_prev=site ;; + -site=* | --site=* | --sit=*) + site=$ac_optarg ;; + + -srcdir | --srcdir | --srcdi | --srcd | --src | --sr) + ac_prev=srcdir ;; + -srcdir=* | --srcdir=* | --srcdi=* | --srcd=* | --src=* | --sr=*) + srcdir=$ac_optarg ;; + + -sysconfdir | --sysconfdir | --sysconfdi | --sysconfd | --sysconf \ + | --syscon | --sysco | --sysc | --sys | --sy) + ac_prev=sysconfdir ;; + -sysconfdir=* | --sysconfdir=* | --sysconfdi=* | --sysconfd=* | --sysconf=* \ + | --syscon=* | --sysco=* | --sysc=* | --sys=* | --sy=*) + sysconfdir=$ac_optarg ;; + + -target | --target | --targe | --targ | --tar | --ta | --t) + ac_prev=target_alias ;; + -target=* | --target=* | --targe=* | --targ=* | --tar=* | --ta=* | --t=*) + target_alias=$ac_optarg ;; + + -v | -verbose | --verbose | --verbos | --verbo | --verb) + verbose=yes ;; + + -version | --version | --versio | --versi | --vers | -V) + ac_init_version=: ;; + + -with-* | --with-*) + ac_useropt=`expr "x$ac_option" : 'x-*with-\([^=]*\)'` + # Reject names that are not valid shell variable names. + expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && + as_fn_error $? "invalid package name: \`$ac_useropt'" + ac_useropt_orig=$ac_useropt + ac_useropt=`printf "%s\n" "$ac_useropt" | sed 's/[-+.]/_/g'` + case $ac_user_opts in + *" +"with_$ac_useropt" +"*) ;; + *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--with-$ac_useropt_orig" + ac_unrecognized_sep=', ';; + esac + eval with_$ac_useropt=\$ac_optarg ;; + + -without-* | --without-*) + ac_useropt=`expr "x$ac_option" : 'x-*without-\(.*\)'` + # Reject names that are not valid shell variable names. + expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && + as_fn_error $? "invalid package name: \`$ac_useropt'" + ac_useropt_orig=$ac_useropt + ac_useropt=`printf "%s\n" "$ac_useropt" | sed 's/[-+.]/_/g'` + case $ac_user_opts in + *" +"with_$ac_useropt" +"*) ;; + *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--without-$ac_useropt_orig" + ac_unrecognized_sep=', ';; + esac + eval with_$ac_useropt=no ;; + + --x) + # Obsolete; use --with-x. + with_x=yes ;; + + -x-includes | --x-includes | --x-include | --x-includ | --x-inclu \ + | --x-incl | --x-inc | --x-in | --x-i) + ac_prev=x_includes ;; + -x-includes=* | --x-includes=* | --x-include=* | --x-includ=* | --x-inclu=* \ + | --x-incl=* | --x-inc=* | --x-in=* | --x-i=*) + x_includes=$ac_optarg ;; + + -x-libraries | --x-libraries | --x-librarie | --x-librari \ + | --x-librar | --x-libra | --x-libr | --x-lib | --x-li | --x-l) + ac_prev=x_libraries ;; + -x-libraries=* | --x-libraries=* | --x-librarie=* | --x-librari=* \ + | --x-librar=* | --x-libra=* | --x-libr=* | --x-lib=* | --x-li=* | --x-l=*) + x_libraries=$ac_optarg ;; + + -*) as_fn_error $? "unrecognized option: \`$ac_option' +Try \`$0 --help' for more information" + ;; + + *=*) + ac_envvar=`expr "x$ac_option" : 'x\([^=]*\)='` + # Reject names that are not valid shell variable names. + case $ac_envvar in #( + '' | [0-9]* | *[!_$as_cr_alnum]* ) + as_fn_error $? "invalid variable name: \`$ac_envvar'" ;; + esac + eval $ac_envvar=\$ac_optarg + export $ac_envvar ;; + + *) + # FIXME: should be removed in autoconf 3.0. + printf "%s\n" "$as_me: WARNING: you should use --build, --host, --target" >&2 + expr "x$ac_option" : ".*[^-._$as_cr_alnum]" >/dev/null && + printf "%s\n" "$as_me: WARNING: invalid host type: $ac_option" >&2 + : "${build_alias=$ac_option} ${host_alias=$ac_option} ${target_alias=$ac_option}" + ;; + + esac +done + +if test -n "$ac_prev"; then + ac_option=--`echo $ac_prev | sed 's/_/-/g'` + as_fn_error $? "missing argument to $ac_option" +fi + +if test -n "$ac_unrecognized_opts"; then + case $enable_option_checking in + no) ;; + fatal) as_fn_error $? "unrecognized options: $ac_unrecognized_opts" ;; + *) printf "%s\n" "$as_me: WARNING: unrecognized options: $ac_unrecognized_opts" >&2 ;; + esac +fi + +# Check all directory arguments for consistency. +for ac_var in exec_prefix prefix bindir sbindir libexecdir datarootdir \ + datadir sysconfdir sharedstatedir localstatedir includedir \ + oldincludedir docdir infodir htmldir dvidir pdfdir psdir \ + libdir localedir mandir runstatedir +do + eval ac_val=\$$ac_var + # Remove trailing slashes. + case $ac_val in + */ ) + ac_val=`expr "X$ac_val" : 'X\(.*[^/]\)' \| "X$ac_val" : 'X\(.*\)'` + eval $ac_var=\$ac_val;; + esac + # Be sure to have absolute directory names. + case $ac_val in + [\\/$]* | ?:[\\/]* ) continue;; + NONE | '' ) case $ac_var in *prefix ) continue;; esac;; + esac + as_fn_error $? "expected an absolute directory name for --$ac_var: $ac_val" +done + +# There might be people who depend on the old broken behavior: `$host' +# used to hold the argument of --host etc. +# FIXME: To remove some day. +build=$build_alias +host=$host_alias +target=$target_alias + +# FIXME: To remove some day. +if test "x$host_alias" != x; then + if test "x$build_alias" = x; then + cross_compiling=maybe + elif test "x$build_alias" != "x$host_alias"; then + cross_compiling=yes + fi +fi + +ac_tool_prefix= +test -n "$host_alias" && ac_tool_prefix=$host_alias- + +test "$silent" = yes && exec 6>/dev/null + + +ac_pwd=`pwd` && test -n "$ac_pwd" && +ac_ls_di=`ls -di .` && +ac_pwd_ls_di=`cd "$ac_pwd" && ls -di .` || + as_fn_error $? "working directory cannot be determined" +test "X$ac_ls_di" = "X$ac_pwd_ls_di" || + as_fn_error $? "pwd does not report name of working directory" + + +# Find the source files, if location was not specified. +if test -z "$srcdir"; then + ac_srcdir_defaulted=yes + # Try the directory containing this script, then the parent directory. + ac_confdir=`$as_dirname -- "$as_myself" || +$as_expr X"$as_myself" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ + X"$as_myself" : 'X\(//\)[^/]' \| \ + X"$as_myself" : 'X\(//\)$' \| \ + X"$as_myself" : 'X\(/\)' \| . 2>/dev/null || +printf "%s\n" X"$as_myself" | + sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ + s//\1/ + q + } + /^X\(\/\/\)[^/].*/{ + s//\1/ + q + } + /^X\(\/\/\)$/{ + s//\1/ + q + } + /^X\(\/\).*/{ + s//\1/ + q + } + s/.*/./; q'` + srcdir=$ac_confdir + if test ! -r "$srcdir/$ac_unique_file"; then + srcdir=.. + fi +else + ac_srcdir_defaulted=no +fi +if test ! -r "$srcdir/$ac_unique_file"; then + test "$ac_srcdir_defaulted" = yes && srcdir="$ac_confdir or .." + as_fn_error $? "cannot find sources ($ac_unique_file) in $srcdir" +fi +ac_msg="sources are in $srcdir, but \`cd $srcdir' does not work" +ac_abs_confdir=`( + cd "$srcdir" && test -r "./$ac_unique_file" || as_fn_error $? "$ac_msg" + pwd)` +# When building in place, set srcdir=. +if test "$ac_abs_confdir" = "$ac_pwd"; then + srcdir=. +fi +# Remove unnecessary trailing slashes from srcdir. +# Double slashes in file names in object file debugging info +# mess up M-x gdb in Emacs. +case $srcdir in +*/) srcdir=`expr "X$srcdir" : 'X\(.*[^/]\)' \| "X$srcdir" : 'X\(.*\)'`;; +esac +for ac_var in $ac_precious_vars; do + eval ac_env_${ac_var}_set=\${${ac_var}+set} + eval ac_env_${ac_var}_value=\$${ac_var} + eval ac_cv_env_${ac_var}_set=\${${ac_var}+set} + eval ac_cv_env_${ac_var}_value=\$${ac_var} +done + +# +# Report the --help message. +# +if test "$ac_init_help" = "long"; then + # Omit some internal or obsolete options to make the list less imposing. + # This message is too long to be a string in the A/UX 3.1 sh. + cat <<_ACEOF +\`configure' configures FreeType 2.13.2 to adapt to many kinds of systems. + +Usage: $0 [OPTION]... [VAR=VALUE]... + +To assign environment variables (e.g., CC, CFLAGS...), specify them as +VAR=VALUE. See below for descriptions of some of the useful variables. + +Defaults for the options are specified in brackets. + +Configuration: + -h, --help display this help and exit + --help=short display options specific to this package + --help=recursive display the short help of all the included packages + -V, --version display version information and exit + -q, --quiet, --silent do not print \`checking ...' messages + --cache-file=FILE cache test results in FILE [disabled] + -C, --config-cache alias for \`--cache-file=config.cache' + -n, --no-create do not create output files + --srcdir=DIR find the sources in DIR [configure dir or \`..'] + +Installation directories: + --prefix=PREFIX install architecture-independent files in PREFIX + [$ac_default_prefix] + --exec-prefix=EPREFIX install architecture-dependent files in EPREFIX + [PREFIX] + +By default, \`make install' will install all the files in +\`$ac_default_prefix/bin', \`$ac_default_prefix/lib' etc. You can specify +an installation prefix other than \`$ac_default_prefix' using \`--prefix', +for instance \`--prefix=\$HOME'. + +For better control, use the options below. + +Fine tuning of the installation directories: + --bindir=DIR user executables [EPREFIX/bin] + --sbindir=DIR system admin executables [EPREFIX/sbin] + --libexecdir=DIR program executables [EPREFIX/libexec] + --sysconfdir=DIR read-only single-machine data [PREFIX/etc] + --sharedstatedir=DIR modifiable architecture-independent data [PREFIX/com] + --localstatedir=DIR modifiable single-machine data [PREFIX/var] + --runstatedir=DIR modifiable per-process data [LOCALSTATEDIR/run] + --libdir=DIR object code libraries [EPREFIX/lib] + --includedir=DIR C header files [PREFIX/include] + --oldincludedir=DIR C header files for non-gcc [/usr/include] + --datarootdir=DIR read-only arch.-independent data root [PREFIX/share] + --datadir=DIR read-only architecture-independent data [DATAROOTDIR] + --infodir=DIR info documentation [DATAROOTDIR/info] + --localedir=DIR locale-dependent data [DATAROOTDIR/locale] + --mandir=DIR man documentation [DATAROOTDIR/man] + --docdir=DIR documentation root [DATAROOTDIR/doc/freetype] + --htmldir=DIR html documentation [DOCDIR] + --dvidir=DIR dvi documentation [DOCDIR] + --pdfdir=DIR pdf documentation [DOCDIR] + --psdir=DIR ps documentation [DOCDIR] +_ACEOF + + cat <<\_ACEOF + +System types: + --build=BUILD configure for building on BUILD [guessed] + --host=HOST cross-compile to build programs to run on HOST [BUILD] + --target=TARGET configure for building compilers for TARGET [HOST] +_ACEOF +fi + +if test -n "$ac_init_help"; then + case $ac_init_help in + short | recursive ) echo "Configuration of FreeType 2.13.2:";; + esac + cat <<\_ACEOF + +Optional Features: + --disable-option-checking ignore unrecognized --enable/--with options + --disable-FEATURE do not include FEATURE (same as --enable-FEATURE=no) + --enable-FEATURE[=ARG] include FEATURE [ARG=yes] + --enable-shared[=PKGS] build shared libraries [default=yes] + --enable-static[=PKGS] build static libraries [default=yes] + --enable-fast-install[=PKGS] + optimize for fast installation [default=yes] + --disable-libtool-lock avoid locking (might break parallel builds) + --enable-freetype-config + install freetype-config + --disable-largefile omit support for large files + --disable-mmap do not check mmap() and do not use + +Optional Packages: + --with-PACKAGE[=ARG] use PACKAGE [ARG=yes] + --without-PACKAGE do not use PACKAGE (same as --with-PACKAGE=no) + --with-pic[=PKGS] try to use only PIC/non-PIC objects [default=use + both] + --with-aix-soname=aix|svr4|both + shared library versioning (aka "SONAME") variant to + provide on AIX, [default=aix]. + --with-gnu-ld assume the C compiler uses GNU ld [default=no] + --with-sysroot[=DIR] Search for dependent libraries within DIR (or the + compiler's sysroot if not specified). + --with-zlib=[yes|no|auto] + use system zlib instead of internal library + [default=auto] + --with-bzip2=[yes|no|auto] + support bzip2 compressed fonts [default=auto] + --with-png=[yes|no|auto] + support png compressed OpenType embedded bitmaps + [default=auto] + --with-harfbuzz=[yes|no|auto] + improve auto-hinting of OpenType fonts + [default=auto] + --with-brotli=[yes|no|auto] + support decompression of WOFF2 streams + [default=auto] + --with-librsvg=[yes|no|auto] + support OpenType SVG fonts in FreeType demo programs + [default=auto] + --with-old-mac-fonts allow Mac resource-based fonts to be used + --with-fsspec use obsolete FSSpec API of MacOS, if available + (default=yes) + --with-fsref use Carbon FSRef API of MacOS, if available + (default=yes) + --with-quickdraw-toolbox + use MacOS QuickDraw in ToolBox, if available + (default=yes) + --with-quickdraw-carbon use MacOS QuickDraw in Carbon, if available + (default=yes) + --with-ats use AppleTypeService, if available (default=yes) + +Some influential environment variables: + CC C compiler command + CFLAGS C compiler flags + LDFLAGS linker flags, e.g. -L if you have libraries in a + nonstandard directory + LIBS libraries to pass to the linker, e.g. -l + CPPFLAGS (Objective) C/C++ preprocessor flags, e.g. -I if + you have headers in a nonstandard directory + CPP C preprocessor + PKG_CONFIG path to pkg-config utility + PKG_CONFIG_PATH + directories to add to pkg-config's search path + PKG_CONFIG_LIBDIR + path overriding pkg-config's built-in search path + LT_SYS_LIBRARY_PATH + User-defined run-time library search path. + ZLIB_CFLAGS C compiler flags for ZLIB, overriding pkg-config + ZLIB_LIBS linker flags for ZLIB, overriding pkg-config + BZIP2_CFLAGS + C compiler flags for BZIP2, overriding pkg-config + BZIP2_LIBS linker flags for BZIP2, overriding pkg-config + LIBPNG_CFLAGS + C compiler flags for LIBPNG, overriding pkg-config + LIBPNG_LIBS linker flags for LIBPNG, overriding pkg-config + HARFBUZZ_CFLAGS + C compiler flags for HARFBUZZ, overriding pkg-config + HARFBUZZ_LIBS + linker flags for HARFBUZZ, overriding pkg-config + BROTLI_CFLAGS + C compiler flags for BROTLI, overriding pkg-config + BROTLI_LIBS linker flags for BROTLI, overriding pkg-config + LIBRSVG_CFLAGS + C compiler flags for LIBRSVG, overriding pkg-config + LIBRSVG_LIBS + linker flags for LIBRSVG, overriding pkg-config + +Use these variables to override the choices made by `configure' or to help +it to find libraries and programs with nonstandard names/locations. + +Report bugs to . +_ACEOF +ac_status=$? +fi + +if test "$ac_init_help" = "recursive"; then + # If there are subdirs, report their specific --help. + for ac_dir in : $ac_subdirs_all; do test "x$ac_dir" = x: && continue + test -d "$ac_dir" || + { cd "$srcdir" && ac_pwd=`pwd` && srcdir=. && test -d "$ac_dir"; } || + continue + ac_builddir=. + +case "$ac_dir" in +.) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;; +*) + ac_dir_suffix=/`printf "%s\n" "$ac_dir" | sed 's|^\.[\\/]||'` + # A ".." for each directory in $ac_dir_suffix. + ac_top_builddir_sub=`printf "%s\n" "$ac_dir_suffix" | sed 's|/[^\\/]*|/..|g;s|/||'` + case $ac_top_builddir_sub in + "") ac_top_builddir_sub=. ac_top_build_prefix= ;; + *) ac_top_build_prefix=$ac_top_builddir_sub/ ;; + esac ;; +esac +ac_abs_top_builddir=$ac_pwd +ac_abs_builddir=$ac_pwd$ac_dir_suffix +# for backward compatibility: +ac_top_builddir=$ac_top_build_prefix + +case $srcdir in + .) # We are building in place. + ac_srcdir=. + ac_top_srcdir=$ac_top_builddir_sub + ac_abs_top_srcdir=$ac_pwd ;; + [\\/]* | ?:[\\/]* ) # Absolute name. + ac_srcdir=$srcdir$ac_dir_suffix; + ac_top_srcdir=$srcdir + ac_abs_top_srcdir=$srcdir ;; + *) # Relative name. + ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix + ac_top_srcdir=$ac_top_build_prefix$srcdir + ac_abs_top_srcdir=$ac_pwd/$srcdir ;; +esac +ac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix + + cd "$ac_dir" || { ac_status=$?; continue; } + # Check for configure.gnu first; this name is used for a wrapper for + # Metaconfig's "Configure" on case-insensitive file systems. + if test -f "$ac_srcdir/configure.gnu"; then + echo && + $SHELL "$ac_srcdir/configure.gnu" --help=recursive + elif test -f "$ac_srcdir/configure"; then + echo && + $SHELL "$ac_srcdir/configure" --help=recursive + else + printf "%s\n" "$as_me: WARNING: no configuration information is in $ac_dir" >&2 + fi || ac_status=$? + cd "$ac_pwd" || { ac_status=$?; break; } + done +fi + +test -n "$ac_init_help" && exit $ac_status +if $ac_init_version; then + cat <<\_ACEOF +FreeType configure 2.13.2 +generated by GNU Autoconf 2.71 + +Copyright (C) 2021 Free Software Foundation, Inc. +This configure script is free software; the Free Software Foundation +gives unlimited permission to copy, distribute and modify it. +_ACEOF + exit +fi + +## ------------------------ ## +## Autoconf initialization. ## +## ------------------------ ## + +# ac_fn_c_try_compile LINENO +# -------------------------- +# Try to compile conftest.$ac_ext, and return whether this succeeded. +ac_fn_c_try_compile () +{ + as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack + rm -f conftest.$ac_objext conftest.beam + if { { ac_try="$ac_compile" +case "(($ac_try" in + *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; + *) ac_try_echo=$ac_try;; +esac +eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" +printf "%s\n" "$ac_try_echo"; } >&5 + (eval "$ac_compile") 2>conftest.err + ac_status=$? + if test -s conftest.err; then + grep -v '^ *+' conftest.err >conftest.er1 + cat conftest.er1 >&5 + mv -f conftest.er1 conftest.err + fi + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } && { + test -z "$ac_c_werror_flag" || + test ! -s conftest.err + } && test -s conftest.$ac_objext +then : + ac_retval=0 +else $as_nop + printf "%s\n" "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + + ac_retval=1 +fi + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno + as_fn_set_status $ac_retval + +} # ac_fn_c_try_compile + +# ac_fn_c_try_cpp LINENO +# ---------------------- +# Try to preprocess conftest.$ac_ext, and return whether this succeeded. +ac_fn_c_try_cpp () +{ + as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack + if { { ac_try="$ac_cpp conftest.$ac_ext" +case "(($ac_try" in + *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; + *) ac_try_echo=$ac_try;; +esac +eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" +printf "%s\n" "$ac_try_echo"; } >&5 + (eval "$ac_cpp conftest.$ac_ext") 2>conftest.err + ac_status=$? + if test -s conftest.err; then + grep -v '^ *+' conftest.err >conftest.er1 + cat conftest.er1 >&5 + mv -f conftest.er1 conftest.err + fi + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } > conftest.i && { + test -z "$ac_c_preproc_warn_flag$ac_c_werror_flag" || + test ! -s conftest.err + } +then : + ac_retval=0 +else $as_nop + printf "%s\n" "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + + ac_retval=1 +fi + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno + as_fn_set_status $ac_retval + +} # ac_fn_c_try_cpp + +# ac_fn_c_try_link LINENO +# ----------------------- +# Try to link conftest.$ac_ext, and return whether this succeeded. +ac_fn_c_try_link () +{ + as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack + rm -f conftest.$ac_objext conftest.beam conftest$ac_exeext + if { { ac_try="$ac_link" +case "(($ac_try" in + *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; + *) ac_try_echo=$ac_try;; +esac +eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" +printf "%s\n" "$ac_try_echo"; } >&5 + (eval "$ac_link") 2>conftest.err + ac_status=$? + if test -s conftest.err; then + grep -v '^ *+' conftest.err >conftest.er1 + cat conftest.er1 >&5 + mv -f conftest.er1 conftest.err + fi + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } && { + test -z "$ac_c_werror_flag" || + test ! -s conftest.err + } && test -s conftest$ac_exeext && { + test "$cross_compiling" = yes || + test -x conftest$ac_exeext + } +then : + ac_retval=0 +else $as_nop + printf "%s\n" "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + + ac_retval=1 +fi + # Delete the IPA/IPO (Inter Procedural Analysis/Optimization) information + # created by the PGI compiler (conftest_ipa8_conftest.oo), as it would + # interfere with the next link command; also delete a directory that is + # left behind by Apple's compiler. We do this before executing the actions. + rm -rf conftest.dSYM conftest_ipa8_conftest.oo + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno + as_fn_set_status $ac_retval + +} # ac_fn_c_try_link + +# ac_fn_c_check_header_compile LINENO HEADER VAR INCLUDES +# ------------------------------------------------------- +# Tests whether HEADER exists and can be compiled using the include files in +# INCLUDES, setting the cache variable VAR accordingly. +ac_fn_c_check_header_compile () +{ + as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $2" >&5 +printf %s "checking for $2... " >&6; } +if eval test \${$3+y} +then : + printf %s "(cached) " >&6 +else $as_nop + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +$4 +#include <$2> +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + eval "$3=yes" +else $as_nop + eval "$3=no" +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext +fi +eval ac_res=\$$3 + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 +printf "%s\n" "$ac_res" >&6; } + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno + +} # ac_fn_c_check_header_compile + +# ac_fn_c_check_func LINENO FUNC VAR +# ---------------------------------- +# Tests whether FUNC exists, setting the cache variable VAR accordingly +ac_fn_c_check_func () +{ + as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $2" >&5 +printf %s "checking for $2... " >&6; } +if eval test \${$3+y} +then : + printf %s "(cached) " >&6 +else $as_nop + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +/* Define $2 to an innocuous variant, in case declares $2. + For example, HP-UX 11i declares gettimeofday. */ +#define $2 innocuous_$2 + +/* System header to define __stub macros and hopefully few prototypes, + which can conflict with char $2 (); below. */ + +#include +#undef $2 + +/* Override any GCC internal prototype to avoid an error. + Use char because int might match the return type of a GCC + builtin and then its argument prototype would still apply. */ +#ifdef __cplusplus +extern "C" +#endif +char $2 (); +/* The GNU C library defines this for functions which it implements + to always fail with ENOSYS. Some functions are actually named + something starting with __ and the normal name is an alias. */ +#if defined __stub_$2 || defined __stub___$2 +choke me +#endif + +int +main (void) +{ +return $2 (); + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + eval "$3=yes" +else $as_nop + eval "$3=no" +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext +fi +eval ac_res=\$$3 + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 +printf "%s\n" "$ac_res" >&6; } + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno + +} # ac_fn_c_check_func + +# ac_fn_c_try_run LINENO +# ---------------------- +# Try to run conftest.$ac_ext, and return whether this succeeded. Assumes that +# executables *can* be run. +ac_fn_c_try_run () +{ + as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack + if { { ac_try="$ac_link" +case "(($ac_try" in + *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; + *) ac_try_echo=$ac_try;; +esac +eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" +printf "%s\n" "$ac_try_echo"; } >&5 + (eval "$ac_link") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } && { ac_try='./conftest$ac_exeext' + { { case "(($ac_try" in + *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; + *) ac_try_echo=$ac_try;; +esac +eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" +printf "%s\n" "$ac_try_echo"; } >&5 + (eval "$ac_try") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; } +then : + ac_retval=0 +else $as_nop + printf "%s\n" "$as_me: program exited with status $ac_status" >&5 + printf "%s\n" "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + + ac_retval=$ac_status +fi + rm -rf conftest.dSYM conftest_ipa8_conftest.oo + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno + as_fn_set_status $ac_retval + +} # ac_fn_c_try_run + +# ac_fn_check_decl LINENO SYMBOL VAR INCLUDES EXTRA-OPTIONS FLAG-VAR +# ------------------------------------------------------------------ +# Tests whether SYMBOL is declared in INCLUDES, setting cache variable VAR +# accordingly. Pass EXTRA-OPTIONS to the compiler, using FLAG-VAR. +ac_fn_check_decl () +{ + as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack + as_decl_name=`echo $2|sed 's/ *(.*//'` + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether $as_decl_name is declared" >&5 +printf %s "checking whether $as_decl_name is declared... " >&6; } +if eval test \${$3+y} +then : + printf %s "(cached) " >&6 +else $as_nop + as_decl_use=`echo $2|sed -e 's/(/((/' -e 's/)/) 0&/' -e 's/,/) 0& (/g'` + eval ac_save_FLAGS=\$$6 + as_fn_append $6 " $5" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +$4 +int +main (void) +{ +#ifndef $as_decl_name +#ifdef __cplusplus + (void) $as_decl_use; +#else + (void) $as_decl_name; +#endif +#endif + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + eval "$3=yes" +else $as_nop + eval "$3=no" +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext + eval $6=\$ac_save_FLAGS + +fi +eval ac_res=\$$3 + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 +printf "%s\n" "$ac_res" >&6; } + eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno + +} # ac_fn_check_decl +ac_configure_args_raw= +for ac_arg +do + case $ac_arg in + *\'*) + ac_arg=`printf "%s\n" "$ac_arg" | sed "s/'/'\\\\\\\\''/g"` ;; + esac + as_fn_append ac_configure_args_raw " '$ac_arg'" +done + +case $ac_configure_args_raw in + *$as_nl*) + ac_safe_unquote= ;; + *) + ac_unsafe_z='|&;<>()$`\\"*?[ '' ' # This string ends in space, tab. + ac_unsafe_a="$ac_unsafe_z#~" + ac_safe_unquote="s/ '\\([^$ac_unsafe_a][^$ac_unsafe_z]*\\)'/ \\1/g" + ac_configure_args_raw=` printf "%s\n" "$ac_configure_args_raw" | sed "$ac_safe_unquote"`;; +esac + +cat >config.log <<_ACEOF +This file contains any messages produced by compilers while +running configure, to aid debugging if configure makes a mistake. + +It was created by FreeType $as_me 2.13.2, which was +generated by GNU Autoconf 2.71. Invocation command line was + + $ $0$ac_configure_args_raw + +_ACEOF +exec 5>>config.log +{ +cat <<_ASUNAME +## --------- ## +## Platform. ## +## --------- ## + +hostname = `(hostname || uname -n) 2>/dev/null | sed 1q` +uname -m = `(uname -m) 2>/dev/null || echo unknown` +uname -r = `(uname -r) 2>/dev/null || echo unknown` +uname -s = `(uname -s) 2>/dev/null || echo unknown` +uname -v = `(uname -v) 2>/dev/null || echo unknown` + +/usr/bin/uname -p = `(/usr/bin/uname -p) 2>/dev/null || echo unknown` +/bin/uname -X = `(/bin/uname -X) 2>/dev/null || echo unknown` + +/bin/arch = `(/bin/arch) 2>/dev/null || echo unknown` +/usr/bin/arch -k = `(/usr/bin/arch -k) 2>/dev/null || echo unknown` +/usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null || echo unknown` +/usr/bin/hostinfo = `(/usr/bin/hostinfo) 2>/dev/null || echo unknown` +/bin/machine = `(/bin/machine) 2>/dev/null || echo unknown` +/usr/bin/oslevel = `(/usr/bin/oslevel) 2>/dev/null || echo unknown` +/bin/universe = `(/bin/universe) 2>/dev/null || echo unknown` + +_ASUNAME + +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + printf "%s\n" "PATH: $as_dir" + done +IFS=$as_save_IFS + +} >&5 + +cat >&5 <<_ACEOF + + +## ----------- ## +## Core tests. ## +## ----------- ## + +_ACEOF + + +# Keep a trace of the command line. +# Strip out --no-create and --no-recursion so they do not pile up. +# Strip out --silent because we don't want to record it for future runs. +# Also quote any args containing shell meta-characters. +# Make two passes to allow for proper duplicate-argument suppression. +ac_configure_args= +ac_configure_args0= +ac_configure_args1= +ac_must_keep_next=false +for ac_pass in 1 2 +do + for ac_arg + do + case $ac_arg in + -no-create | --no-c* | -n | -no-recursion | --no-r*) continue ;; + -q | -quiet | --quiet | --quie | --qui | --qu | --q \ + | -silent | --silent | --silen | --sile | --sil) + continue ;; + *\'*) + ac_arg=`printf "%s\n" "$ac_arg" | sed "s/'/'\\\\\\\\''/g"` ;; + esac + case $ac_pass in + 1) as_fn_append ac_configure_args0 " '$ac_arg'" ;; + 2) + as_fn_append ac_configure_args1 " '$ac_arg'" + if test $ac_must_keep_next = true; then + ac_must_keep_next=false # Got value, back to normal. + else + case $ac_arg in + *=* | --config-cache | -C | -disable-* | --disable-* \ + | -enable-* | --enable-* | -gas | --g* | -nfp | --nf* \ + | -q | -quiet | --q* | -silent | --sil* | -v | -verb* \ + | -with-* | --with-* | -without-* | --without-* | --x) + case "$ac_configure_args0 " in + "$ac_configure_args1"*" '$ac_arg' "* ) continue ;; + esac + ;; + -* ) ac_must_keep_next=true ;; + esac + fi + as_fn_append ac_configure_args " '$ac_arg'" + ;; + esac + done +done +{ ac_configure_args0=; unset ac_configure_args0;} +{ ac_configure_args1=; unset ac_configure_args1;} + +# When interrupted or exit'd, cleanup temporary files, and complete +# config.log. We remove comments because anyway the quotes in there +# would cause problems or look ugly. +# WARNING: Use '\'' to represent an apostrophe within the trap. +# WARNING: Do not start the trap code with a newline, due to a FreeBSD 4.0 bug. +trap 'exit_status=$? + # Sanitize IFS. + IFS=" "" $as_nl" + # Save into config.log some information that might help in debugging. + { + echo + + printf "%s\n" "## ---------------- ## +## Cache variables. ## +## ---------------- ##" + echo + # The following way of writing the cache mishandles newlines in values, +( + for ac_var in `(set) 2>&1 | sed -n '\''s/^\([a-zA-Z_][a-zA-Z0-9_]*\)=.*/\1/p'\''`; do + eval ac_val=\$$ac_var + case $ac_val in #( + *${as_nl}*) + case $ac_var in #( + *_cv_*) { printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline" >&5 +printf "%s\n" "$as_me: WARNING: cache variable $ac_var contains a newline" >&2;} ;; + esac + case $ac_var in #( + _ | IFS | as_nl) ;; #( + BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #( + *) { eval $ac_var=; unset $ac_var;} ;; + esac ;; + esac + done + (set) 2>&1 | + case $as_nl`(ac_space='\'' '\''; set) 2>&1` in #( + *${as_nl}ac_space=\ *) + sed -n \ + "s/'\''/'\''\\\\'\'''\''/g; + s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='\''\\2'\''/p" + ;; #( + *) + sed -n "/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p" + ;; + esac | + sort +) + echo + + printf "%s\n" "## ----------------- ## +## Output variables. ## +## ----------------- ##" + echo + for ac_var in $ac_subst_vars + do + eval ac_val=\$$ac_var + case $ac_val in + *\'\''*) ac_val=`printf "%s\n" "$ac_val" | sed "s/'\''/'\''\\\\\\\\'\'''\''/g"`;; + esac + printf "%s\n" "$ac_var='\''$ac_val'\''" + done | sort + echo + + if test -n "$ac_subst_files"; then + printf "%s\n" "## ------------------- ## +## File substitutions. ## +## ------------------- ##" + echo + for ac_var in $ac_subst_files + do + eval ac_val=\$$ac_var + case $ac_val in + *\'\''*) ac_val=`printf "%s\n" "$ac_val" | sed "s/'\''/'\''\\\\\\\\'\'''\''/g"`;; + esac + printf "%s\n" "$ac_var='\''$ac_val'\''" + done | sort + echo + fi + + if test -s confdefs.h; then + printf "%s\n" "## ----------- ## +## confdefs.h. ## +## ----------- ##" + echo + cat confdefs.h + echo + fi + test "$ac_signal" != 0 && + printf "%s\n" "$as_me: caught signal $ac_signal" + printf "%s\n" "$as_me: exit $exit_status" + } >&5 + rm -f core *.core core.conftest.* && + rm -f -r conftest* confdefs* conf$$* $ac_clean_files && + exit $exit_status +' 0 +for ac_signal in 1 2 13 15; do + trap 'ac_signal='$ac_signal'; as_fn_exit 1' $ac_signal +done +ac_signal=0 + +# confdefs.h avoids OS command line length limits that DEFS can exceed. +rm -f -r conftest* confdefs.h + +printf "%s\n" "/* confdefs.h */" > confdefs.h + +# Predefined preprocessor variables. + +printf "%s\n" "#define PACKAGE_NAME \"$PACKAGE_NAME\"" >>confdefs.h + +printf "%s\n" "#define PACKAGE_TARNAME \"$PACKAGE_TARNAME\"" >>confdefs.h + +printf "%s\n" "#define PACKAGE_VERSION \"$PACKAGE_VERSION\"" >>confdefs.h + +printf "%s\n" "#define PACKAGE_STRING \"$PACKAGE_STRING\"" >>confdefs.h + +printf "%s\n" "#define PACKAGE_BUGREPORT \"$PACKAGE_BUGREPORT\"" >>confdefs.h + +printf "%s\n" "#define PACKAGE_URL \"$PACKAGE_URL\"" >>confdefs.h + + +# Let the site file select an alternate cache file if it wants to. +# Prefer an explicitly selected file to automatically selected ones. +if test -n "$CONFIG_SITE"; then + ac_site_files="$CONFIG_SITE" +elif test "x$prefix" != xNONE; then + ac_site_files="$prefix/share/config.site $prefix/etc/config.site" +else + ac_site_files="$ac_default_prefix/share/config.site $ac_default_prefix/etc/config.site" +fi + +for ac_site_file in $ac_site_files +do + case $ac_site_file in #( + */*) : + ;; #( + *) : + ac_site_file=./$ac_site_file ;; +esac + if test -f "$ac_site_file" && test -r "$ac_site_file"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: loading site script $ac_site_file" >&5 +printf "%s\n" "$as_me: loading site script $ac_site_file" >&6;} + sed 's/^/| /' "$ac_site_file" >&5 + . "$ac_site_file" \ + || { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 +printf "%s\n" "$as_me: error: in \`$ac_pwd':" >&2;} +as_fn_error $? "failed to load site script $ac_site_file +See \`config.log' for more details" "$LINENO" 5; } + fi +done + +if test -r "$cache_file"; then + # Some versions of bash will fail to source /dev/null (special files + # actually), so we avoid doing that. DJGPP emulates it as a regular file. + if test /dev/null != "$cache_file" && test -f "$cache_file"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: loading cache $cache_file" >&5 +printf "%s\n" "$as_me: loading cache $cache_file" >&6;} + case $cache_file in + [\\/]* | ?:[\\/]* ) . "$cache_file";; + *) . "./$cache_file";; + esac + fi +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: creating cache $cache_file" >&5 +printf "%s\n" "$as_me: creating cache $cache_file" >&6;} + >$cache_file +fi + +# Test code for whether the C compiler supports C89 (global declarations) +ac_c_conftest_c89_globals=' +/* Does the compiler advertise C89 conformance? + Do not test the value of __STDC__, because some compilers set it to 0 + while being otherwise adequately conformant. */ +#if !defined __STDC__ +# error "Compiler does not advertise C89 conformance" +#endif + +#include +#include +struct stat; +/* Most of the following tests are stolen from RCS 5.7 src/conf.sh. */ +struct buf { int x; }; +struct buf * (*rcsopen) (struct buf *, struct stat *, int); +static char *e (p, i) + char **p; + int i; +{ + return p[i]; +} +static char *f (char * (*g) (char **, int), char **p, ...) +{ + char *s; + va_list v; + va_start (v,p); + s = g (p, va_arg (v,int)); + va_end (v); + return s; +} + +/* OSF 4.0 Compaq cc is some sort of almost-ANSI by default. It has + function prototypes and stuff, but not \xHH hex character constants. + These do not provoke an error unfortunately, instead are silently treated + as an "x". The following induces an error, until -std is added to get + proper ANSI mode. Curiously \x00 != x always comes out true, for an + array size at least. It is necessary to write \x00 == 0 to get something + that is true only with -std. */ +int osf4_cc_array ['\''\x00'\'' == 0 ? 1 : -1]; + +/* IBM C 6 for AIX is almost-ANSI by default, but it replaces macro parameters + inside strings and character constants. */ +#define FOO(x) '\''x'\'' +int xlc6_cc_array[FOO(a) == '\''x'\'' ? 1 : -1]; + +int test (int i, double x); +struct s1 {int (*f) (int a);}; +struct s2 {int (*f) (double a);}; +int pairnames (int, char **, int *(*)(struct buf *, struct stat *, int), + int, int);' + +# Test code for whether the C compiler supports C89 (body of main). +ac_c_conftest_c89_main=' +ok |= (argc == 0 || f (e, argv, 0) != argv[0] || f (e, argv, 1) != argv[1]); +' + +# Test code for whether the C compiler supports C99 (global declarations) +ac_c_conftest_c99_globals=' +// Does the compiler advertise C99 conformance? +#if !defined __STDC_VERSION__ || __STDC_VERSION__ < 199901L +# error "Compiler does not advertise C99 conformance" +#endif + +#include +extern int puts (const char *); +extern int printf (const char *, ...); +extern int dprintf (int, const char *, ...); +extern void *malloc (size_t); + +// Check varargs macros. These examples are taken from C99 6.10.3.5. +// dprintf is used instead of fprintf to avoid needing to declare +// FILE and stderr. +#define debug(...) dprintf (2, __VA_ARGS__) +#define showlist(...) puts (#__VA_ARGS__) +#define report(test,...) ((test) ? puts (#test) : printf (__VA_ARGS__)) +static void +test_varargs_macros (void) +{ + int x = 1234; + int y = 5678; + debug ("Flag"); + debug ("X = %d\n", x); + showlist (The first, second, and third items.); + report (x>y, "x is %d but y is %d", x, y); +} + +// Check long long types. +#define BIG64 18446744073709551615ull +#define BIG32 4294967295ul +#define BIG_OK (BIG64 / BIG32 == 4294967297ull && BIG64 % BIG32 == 0) +#if !BIG_OK + #error "your preprocessor is broken" +#endif +#if BIG_OK +#else + #error "your preprocessor is broken" +#endif +static long long int bignum = -9223372036854775807LL; +static unsigned long long int ubignum = BIG64; + +struct incomplete_array +{ + int datasize; + double data[]; +}; + +struct named_init { + int number; + const wchar_t *name; + double average; +}; + +typedef const char *ccp; + +static inline int +test_restrict (ccp restrict text) +{ + // See if C++-style comments work. + // Iterate through items via the restricted pointer. + // Also check for declarations in for loops. + for (unsigned int i = 0; *(text+i) != '\''\0'\''; ++i) + continue; + return 0; +} + +// Check varargs and va_copy. +static bool +test_varargs (const char *format, ...) +{ + va_list args; + va_start (args, format); + va_list args_copy; + va_copy (args_copy, args); + + const char *str = ""; + int number = 0; + float fnumber = 0; + + while (*format) + { + switch (*format++) + { + case '\''s'\'': // string + str = va_arg (args_copy, const char *); + break; + case '\''d'\'': // int + number = va_arg (args_copy, int); + break; + case '\''f'\'': // float + fnumber = va_arg (args_copy, double); + break; + default: + break; + } + } + va_end (args_copy); + va_end (args); + + return *str && number && fnumber; +} +' + +# Test code for whether the C compiler supports C99 (body of main). +ac_c_conftest_c99_main=' + // Check bool. + _Bool success = false; + success |= (argc != 0); + + // Check restrict. + if (test_restrict ("String literal") == 0) + success = true; + char *restrict newvar = "Another string"; + + // Check varargs. + success &= test_varargs ("s, d'\'' f .", "string", 65, 34.234); + test_varargs_macros (); + + // Check flexible array members. + struct incomplete_array *ia = + malloc (sizeof (struct incomplete_array) + (sizeof (double) * 10)); + ia->datasize = 10; + for (int i = 0; i < ia->datasize; ++i) + ia->data[i] = i * 1.234; + + // Check named initializers. + struct named_init ni = { + .number = 34, + .name = L"Test wide string", + .average = 543.34343, + }; + + ni.number = 58; + + int dynamic_array[ni.number]; + dynamic_array[0] = argv[0][0]; + dynamic_array[ni.number - 1] = 543; + + // work around unused variable warnings + ok |= (!success || bignum == 0LL || ubignum == 0uLL || newvar[0] == '\''x'\'' + || dynamic_array[ni.number - 1] != 543); +' + +# Test code for whether the C compiler supports C11 (global declarations) +ac_c_conftest_c11_globals=' +// Does the compiler advertise C11 conformance? +#if !defined __STDC_VERSION__ || __STDC_VERSION__ < 201112L +# error "Compiler does not advertise C11 conformance" +#endif + +// Check _Alignas. +char _Alignas (double) aligned_as_double; +char _Alignas (0) no_special_alignment; +extern char aligned_as_int; +char _Alignas (0) _Alignas (int) aligned_as_int; + +// Check _Alignof. +enum +{ + int_alignment = _Alignof (int), + int_array_alignment = _Alignof (int[100]), + char_alignment = _Alignof (char) +}; +_Static_assert (0 < -_Alignof (int), "_Alignof is signed"); + +// Check _Noreturn. +int _Noreturn does_not_return (void) { for (;;) continue; } + +// Check _Static_assert. +struct test_static_assert +{ + int x; + _Static_assert (sizeof (int) <= sizeof (long int), + "_Static_assert does not work in struct"); + long int y; +}; + +// Check UTF-8 literals. +#define u8 syntax error! +char const utf8_literal[] = u8"happens to be ASCII" "another string"; + +// Check duplicate typedefs. +typedef long *long_ptr; +typedef long int *long_ptr; +typedef long_ptr long_ptr; + +// Anonymous structures and unions -- taken from C11 6.7.2.1 Example 1. +struct anonymous +{ + union { + struct { int i; int j; }; + struct { int k; long int l; } w; + }; + int m; +} v1; +' + +# Test code for whether the C compiler supports C11 (body of main). +ac_c_conftest_c11_main=' + _Static_assert ((offsetof (struct anonymous, i) + == offsetof (struct anonymous, w.k)), + "Anonymous union alignment botch"); + v1.i = 2; + v1.w.k = 5; + ok |= v1.i != 5; +' + +# Test code for whether the C compiler supports C11 (complete). +ac_c_conftest_c11_program="${ac_c_conftest_c89_globals} +${ac_c_conftest_c99_globals} +${ac_c_conftest_c11_globals} + +int +main (int argc, char **argv) +{ + int ok = 0; + ${ac_c_conftest_c89_main} + ${ac_c_conftest_c99_main} + ${ac_c_conftest_c11_main} + return ok; +} +" + +# Test code for whether the C compiler supports C99 (complete). +ac_c_conftest_c99_program="${ac_c_conftest_c89_globals} +${ac_c_conftest_c99_globals} + +int +main (int argc, char **argv) +{ + int ok = 0; + ${ac_c_conftest_c89_main} + ${ac_c_conftest_c99_main} + return ok; +} +" + +# Test code for whether the C compiler supports C89 (complete). +ac_c_conftest_c89_program="${ac_c_conftest_c89_globals} + +int +main (int argc, char **argv) +{ + int ok = 0; + ${ac_c_conftest_c89_main} + return ok; +} +" + +as_fn_append ac_header_c_list " stdio.h stdio_h HAVE_STDIO_H" +as_fn_append ac_header_c_list " stdlib.h stdlib_h HAVE_STDLIB_H" +as_fn_append ac_header_c_list " string.h string_h HAVE_STRING_H" +as_fn_append ac_header_c_list " inttypes.h inttypes_h HAVE_INTTYPES_H" +as_fn_append ac_header_c_list " stdint.h stdint_h HAVE_STDINT_H" +as_fn_append ac_header_c_list " strings.h strings_h HAVE_STRINGS_H" +as_fn_append ac_header_c_list " sys/stat.h sys_stat_h HAVE_SYS_STAT_H" +as_fn_append ac_header_c_list " sys/types.h sys_types_h HAVE_SYS_TYPES_H" +as_fn_append ac_header_c_list " unistd.h unistd_h HAVE_UNISTD_H" +as_fn_append ac_header_c_list " sys/param.h sys_param_h HAVE_SYS_PARAM_H" +as_fn_append ac_func_c_list " getpagesize HAVE_GETPAGESIZE" + +# Auxiliary files required by this configure script. +ac_aux_files="install-sh ltmain.sh config.guess config.sub" + +# Locations in which to look for auxiliary files. +ac_aux_dir_candidates="${srcdir}${PATH_SEPARATOR}${srcdir}/..${PATH_SEPARATOR}${srcdir}/../.." + +# Search for a directory containing all of the required auxiliary files, +# $ac_aux_files, from the $PATH-style list $ac_aux_dir_candidates. +# If we don't find one directory that contains all the files we need, +# we report the set of missing files from the *first* directory in +# $ac_aux_dir_candidates and give up. +ac_missing_aux_files="" +ac_first_candidate=: +printf "%s\n" "$as_me:${as_lineno-$LINENO}: looking for aux files: $ac_aux_files" >&5 +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +as_found=false +for as_dir in $ac_aux_dir_candidates +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + as_found=: + + printf "%s\n" "$as_me:${as_lineno-$LINENO}: trying $as_dir" >&5 + ac_aux_dir_found=yes + ac_install_sh= + for ac_aux in $ac_aux_files + do + # As a special case, if "install-sh" is required, that requirement + # can be satisfied by any of "install-sh", "install.sh", or "shtool", + # and $ac_install_sh is set appropriately for whichever one is found. + if test x"$ac_aux" = x"install-sh" + then + if test -f "${as_dir}install-sh"; then + printf "%s\n" "$as_me:${as_lineno-$LINENO}: ${as_dir}install-sh found" >&5 + ac_install_sh="${as_dir}install-sh -c" + elif test -f "${as_dir}install.sh"; then + printf "%s\n" "$as_me:${as_lineno-$LINENO}: ${as_dir}install.sh found" >&5 + ac_install_sh="${as_dir}install.sh -c" + elif test -f "${as_dir}shtool"; then + printf "%s\n" "$as_me:${as_lineno-$LINENO}: ${as_dir}shtool found" >&5 + ac_install_sh="${as_dir}shtool install -c" + else + ac_aux_dir_found=no + if $ac_first_candidate; then + ac_missing_aux_files="${ac_missing_aux_files} install-sh" + else + break + fi + fi + else + if test -f "${as_dir}${ac_aux}"; then + printf "%s\n" "$as_me:${as_lineno-$LINENO}: ${as_dir}${ac_aux} found" >&5 + else + ac_aux_dir_found=no + if $ac_first_candidate; then + ac_missing_aux_files="${ac_missing_aux_files} ${ac_aux}" + else + break + fi + fi + fi + done + if test "$ac_aux_dir_found" = yes; then + ac_aux_dir="$as_dir" + break + fi + ac_first_candidate=false + + as_found=false +done +IFS=$as_save_IFS +if $as_found +then : + +else $as_nop + as_fn_error $? "cannot find required auxiliary files:$ac_missing_aux_files" "$LINENO" 5 +fi + + +# These three variables are undocumented and unsupported, +# and are intended to be withdrawn in a future Autoconf release. +# They can cause serious problems if a builder's source tree is in a directory +# whose full name contains unusual characters. +if test -f "${ac_aux_dir}config.guess"; then + ac_config_guess="$SHELL ${ac_aux_dir}config.guess" +fi +if test -f "${ac_aux_dir}config.sub"; then + ac_config_sub="$SHELL ${ac_aux_dir}config.sub" +fi +if test -f "$ac_aux_dir/configure"; then + ac_configure="$SHELL ${ac_aux_dir}configure" +fi + +# Check that the precious variables saved in the cache have kept the same +# value. +ac_cache_corrupted=false +for ac_var in $ac_precious_vars; do + eval ac_old_set=\$ac_cv_env_${ac_var}_set + eval ac_new_set=\$ac_env_${ac_var}_set + eval ac_old_val=\$ac_cv_env_${ac_var}_value + eval ac_new_val=\$ac_env_${ac_var}_value + case $ac_old_set,$ac_new_set in + set,) + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&5 +printf "%s\n" "$as_me: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&2;} + ac_cache_corrupted=: ;; + ,set) + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' was not set in the previous run" >&5 +printf "%s\n" "$as_me: error: \`$ac_var' was not set in the previous run" >&2;} + ac_cache_corrupted=: ;; + ,);; + *) + if test "x$ac_old_val" != "x$ac_new_val"; then + # differences in whitespace do not lead to failure. + ac_old_val_w=`echo x $ac_old_val` + ac_new_val_w=`echo x $ac_new_val` + if test "$ac_old_val_w" != "$ac_new_val_w"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' has changed since the previous run:" >&5 +printf "%s\n" "$as_me: error: \`$ac_var' has changed since the previous run:" >&2;} + ac_cache_corrupted=: + else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: warning: ignoring whitespace changes in \`$ac_var' since the previous run:" >&5 +printf "%s\n" "$as_me: warning: ignoring whitespace changes in \`$ac_var' since the previous run:" >&2;} + eval $ac_var=\$ac_old_val + fi + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: former value: \`$ac_old_val'" >&5 +printf "%s\n" "$as_me: former value: \`$ac_old_val'" >&2;} + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: current value: \`$ac_new_val'" >&5 +printf "%s\n" "$as_me: current value: \`$ac_new_val'" >&2;} + fi;; + esac + # Pass precious variables to config.status. + if test "$ac_new_set" = set; then + case $ac_new_val in + *\'*) ac_arg=$ac_var=`printf "%s\n" "$ac_new_val" | sed "s/'/'\\\\\\\\''/g"` ;; + *) ac_arg=$ac_var=$ac_new_val ;; + esac + case " $ac_configure_args " in + *" '$ac_arg' "*) ;; # Avoid dups. Use of quotes ensures accuracy. + *) as_fn_append ac_configure_args " '$ac_arg'" ;; + esac + fi +done +if $ac_cache_corrupted; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 +printf "%s\n" "$as_me: error: in \`$ac_pwd':" >&2;} + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: error: changes in the environment can compromise the build" >&5 +printf "%s\n" "$as_me: error: changes in the environment can compromise the build" >&2;} + as_fn_error $? "run \`${MAKE-make} distclean' and/or \`rm $cache_file' + and start over" "$LINENO" 5 +fi +## -------------------- ## +## Main body of script. ## +## -------------------- ## + +ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu + + + + + +# Don't forget to update `docs/VERSIONS.TXT'! + +version_info='26:1:20' + +ft_version=`echo $version_info | tr : .` + + + +# checks for system type + + + + + # Make sure we can run config.sub. +$SHELL "${ac_aux_dir}config.sub" sun4 >/dev/null 2>&1 || + as_fn_error $? "cannot run $SHELL ${ac_aux_dir}config.sub" "$LINENO" 5 + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking build system type" >&5 +printf %s "checking build system type... " >&6; } +if test ${ac_cv_build+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ac_build_alias=$build_alias +test "x$ac_build_alias" = x && + ac_build_alias=`$SHELL "${ac_aux_dir}config.guess"` +test "x$ac_build_alias" = x && + as_fn_error $? "cannot guess build type; you must specify one" "$LINENO" 5 +ac_cv_build=`$SHELL "${ac_aux_dir}config.sub" $ac_build_alias` || + as_fn_error $? "$SHELL ${ac_aux_dir}config.sub $ac_build_alias failed" "$LINENO" 5 + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_build" >&5 +printf "%s\n" "$ac_cv_build" >&6; } +case $ac_cv_build in +*-*-*) ;; +*) as_fn_error $? "invalid value of canonical build" "$LINENO" 5;; +esac +build=$ac_cv_build +ac_save_IFS=$IFS; IFS='-' +set x $ac_cv_build +shift +build_cpu=$1 +build_vendor=$2 +shift; shift +# Remember, the first character of IFS is used to create $*, +# except with old shells: +build_os=$* +IFS=$ac_save_IFS +case $build_os in *\ *) build_os=`echo "$build_os" | sed 's/ /-/g'`;; esac + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking host system type" >&5 +printf %s "checking host system type... " >&6; } +if test ${ac_cv_host+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test "x$host_alias" = x; then + ac_cv_host=$ac_cv_build +else + ac_cv_host=`$SHELL "${ac_aux_dir}config.sub" $host_alias` || + as_fn_error $? "$SHELL ${ac_aux_dir}config.sub $host_alias failed" "$LINENO" 5 +fi + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_host" >&5 +printf "%s\n" "$ac_cv_host" >&6; } +case $ac_cv_host in +*-*-*) ;; +*) as_fn_error $? "invalid value of canonical host" "$LINENO" 5;; +esac +host=$ac_cv_host +ac_save_IFS=$IFS; IFS='-' +set x $ac_cv_host +shift +host_cpu=$1 +host_vendor=$2 +shift; shift +# Remember, the first character of IFS is used to create $*, +# except with old shells: +host_os=$* +IFS=$ac_save_IFS +case $host_os in *\ *) host_os=`echo "$host_os" | sed 's/ /-/g'`;; esac + + + + +# checks for programs + + + + + + + + + + +ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu +if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}gcc", so it can be a program name with args. +set dummy ${ac_tool_prefix}gcc; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_CC+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$CC"; then + ac_cv_prog_CC="$CC" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_CC="${ac_tool_prefix}gcc" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +CC=$ac_cv_prog_CC +if test -n "$CC"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $CC" >&5 +printf "%s\n" "$CC" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_CC"; then + ac_ct_CC=$CC + # Extract the first word of "gcc", so it can be a program name with args. +set dummy gcc; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_CC+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_CC"; then + ac_cv_prog_ac_ct_CC="$ac_ct_CC" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_CC="gcc" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_CC=$ac_cv_prog_ac_ct_CC +if test -n "$ac_ct_CC"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_CC" >&5 +printf "%s\n" "$ac_ct_CC" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_ct_CC" = x; then + CC="" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + CC=$ac_ct_CC + fi +else + CC="$ac_cv_prog_CC" +fi + +if test -z "$CC"; then + if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}cc", so it can be a program name with args. +set dummy ${ac_tool_prefix}cc; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_CC+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$CC"; then + ac_cv_prog_CC="$CC" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_CC="${ac_tool_prefix}cc" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +CC=$ac_cv_prog_CC +if test -n "$CC"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $CC" >&5 +printf "%s\n" "$CC" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + fi +fi +if test -z "$CC"; then + # Extract the first word of "cc", so it can be a program name with args. +set dummy cc; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_CC+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$CC"; then + ac_cv_prog_CC="$CC" # Let the user override the test. +else + ac_prog_rejected=no +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + if test "$as_dir$ac_word$ac_exec_ext" = "/usr/ucb/cc"; then + ac_prog_rejected=yes + continue + fi + ac_cv_prog_CC="cc" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +if test $ac_prog_rejected = yes; then + # We found a bogon in the path, so make sure we never use it. + set dummy $ac_cv_prog_CC + shift + if test $# != 0; then + # We chose a different compiler from the bogus one. + # However, it has the same basename, so the bogon will be chosen + # first if we set CC to just the basename; use the full file name. + shift + ac_cv_prog_CC="$as_dir$ac_word${1+' '}$@" + fi +fi +fi +fi +CC=$ac_cv_prog_CC +if test -n "$CC"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $CC" >&5 +printf "%s\n" "$CC" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$CC"; then + if test -n "$ac_tool_prefix"; then + for ac_prog in cl.exe + do + # Extract the first word of "$ac_tool_prefix$ac_prog", so it can be a program name with args. +set dummy $ac_tool_prefix$ac_prog; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_CC+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$CC"; then + ac_cv_prog_CC="$CC" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_CC="$ac_tool_prefix$ac_prog" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +CC=$ac_cv_prog_CC +if test -n "$CC"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $CC" >&5 +printf "%s\n" "$CC" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + test -n "$CC" && break + done +fi +if test -z "$CC"; then + ac_ct_CC=$CC + for ac_prog in cl.exe +do + # Extract the first word of "$ac_prog", so it can be a program name with args. +set dummy $ac_prog; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_CC+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_CC"; then + ac_cv_prog_ac_ct_CC="$ac_ct_CC" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_CC="$ac_prog" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_CC=$ac_cv_prog_ac_ct_CC +if test -n "$ac_ct_CC"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_CC" >&5 +printf "%s\n" "$ac_ct_CC" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + test -n "$ac_ct_CC" && break +done + + if test "x$ac_ct_CC" = x; then + CC="" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + CC=$ac_ct_CC + fi +fi + +fi +if test -z "$CC"; then + if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}clang", so it can be a program name with args. +set dummy ${ac_tool_prefix}clang; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_CC+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$CC"; then + ac_cv_prog_CC="$CC" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_CC="${ac_tool_prefix}clang" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +CC=$ac_cv_prog_CC +if test -n "$CC"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $CC" >&5 +printf "%s\n" "$CC" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_CC"; then + ac_ct_CC=$CC + # Extract the first word of "clang", so it can be a program name with args. +set dummy clang; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_CC+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_CC"; then + ac_cv_prog_ac_ct_CC="$ac_ct_CC" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_CC="clang" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_CC=$ac_cv_prog_ac_ct_CC +if test -n "$ac_ct_CC"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_CC" >&5 +printf "%s\n" "$ac_ct_CC" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_ct_CC" = x; then + CC="" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + CC=$ac_ct_CC + fi +else + CC="$ac_cv_prog_CC" +fi + +fi + + +test -z "$CC" && { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 +printf "%s\n" "$as_me: error: in \`$ac_pwd':" >&2;} +as_fn_error $? "no acceptable C compiler found in \$PATH +See \`config.log' for more details" "$LINENO" 5; } + +# Provide some information about the compiler. +printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for C compiler version" >&5 +set X $ac_compile +ac_compiler=$2 +for ac_option in --version -v -V -qversion -version; do + { { ac_try="$ac_compiler $ac_option >&5" +case "(($ac_try" in + *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; + *) ac_try_echo=$ac_try;; +esac +eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" +printf "%s\n" "$ac_try_echo"; } >&5 + (eval "$ac_compiler $ac_option >&5") 2>conftest.err + ac_status=$? + if test -s conftest.err; then + sed '10a\ +... rest of stderr output deleted ... + 10q' conftest.err >conftest.er1 + cat conftest.er1 >&5 + fi + rm -f conftest.er1 conftest.err + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } +done + +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +int +main (void) +{ + + ; + return 0; +} +_ACEOF +ac_clean_files_save=$ac_clean_files +ac_clean_files="$ac_clean_files a.out a.out.dSYM a.exe b.out" +# Try to create an executable without -o first, disregard a.out. +# It will help us diagnose broken compilers, and finding out an intuition +# of exeext. +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether the C compiler works" >&5 +printf %s "checking whether the C compiler works... " >&6; } +ac_link_default=`printf "%s\n" "$ac_link" | sed 's/ -o *conftest[^ ]*//'` + +# The possible output files: +ac_files="a.out conftest.exe conftest a.exe a_out.exe b.out conftest.*" + +ac_rmfiles= +for ac_file in $ac_files +do + case $ac_file in + *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) ;; + * ) ac_rmfiles="$ac_rmfiles $ac_file";; + esac +done +rm -f $ac_rmfiles + +if { { ac_try="$ac_link_default" +case "(($ac_try" in + *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; + *) ac_try_echo=$ac_try;; +esac +eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" +printf "%s\n" "$ac_try_echo"; } >&5 + (eval "$ac_link_default") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } +then : + # Autoconf-2.13 could set the ac_cv_exeext variable to `no'. +# So ignore a value of `no', otherwise this would lead to `EXEEXT = no' +# in a Makefile. We should not override ac_cv_exeext if it was cached, +# so that the user can short-circuit this test for compilers unknown to +# Autoconf. +for ac_file in $ac_files '' +do + test -f "$ac_file" || continue + case $ac_file in + *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) + ;; + [ab].out ) + # We found the default executable, but exeext='' is most + # certainly right. + break;; + *.* ) + if test ${ac_cv_exeext+y} && test "$ac_cv_exeext" != no; + then :; else + ac_cv_exeext=`expr "$ac_file" : '[^.]*\(\..*\)'` + fi + # We set ac_cv_exeext here because the later test for it is not + # safe: cross compilers may not add the suffix if given an `-o' + # argument, so we may need to know it at that point already. + # Even if this section looks crufty: it has the advantage of + # actually working. + break;; + * ) + break;; + esac +done +test "$ac_cv_exeext" = no && ac_cv_exeext= + +else $as_nop + ac_file='' +fi +if test -z "$ac_file" +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +printf "%s\n" "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +{ { printf "%s\n" "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 +printf "%s\n" "$as_me: error: in \`$ac_pwd':" >&2;} +as_fn_error 77 "C compiler cannot create executables +See \`config.log' for more details" "$LINENO" 5; } +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +printf "%s\n" "yes" >&6; } +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for C compiler default output file name" >&5 +printf %s "checking for C compiler default output file name... " >&6; } +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_file" >&5 +printf "%s\n" "$ac_file" >&6; } +ac_exeext=$ac_cv_exeext + +rm -f -r a.out a.out.dSYM a.exe conftest$ac_cv_exeext b.out +ac_clean_files=$ac_clean_files_save +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for suffix of executables" >&5 +printf %s "checking for suffix of executables... " >&6; } +if { { ac_try="$ac_link" +case "(($ac_try" in + *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; + *) ac_try_echo=$ac_try;; +esac +eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" +printf "%s\n" "$ac_try_echo"; } >&5 + (eval "$ac_link") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } +then : + # If both `conftest.exe' and `conftest' are `present' (well, observable) +# catch `conftest.exe'. For instance with Cygwin, `ls conftest' will +# work properly (i.e., refer to `conftest.exe'), while it won't with +# `rm'. +for ac_file in conftest.exe conftest conftest.*; do + test -f "$ac_file" || continue + case $ac_file in + *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) ;; + *.* ) ac_cv_exeext=`expr "$ac_file" : '[^.]*\(\..*\)'` + break;; + * ) break;; + esac +done +else $as_nop + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 +printf "%s\n" "$as_me: error: in \`$ac_pwd':" >&2;} +as_fn_error $? "cannot compute suffix of executables: cannot compile and link +See \`config.log' for more details" "$LINENO" 5; } +fi +rm -f conftest conftest$ac_cv_exeext +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_exeext" >&5 +printf "%s\n" "$ac_cv_exeext" >&6; } + +rm -f conftest.$ac_ext +EXEEXT=$ac_cv_exeext +ac_exeext=$EXEEXT +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#include +int +main (void) +{ +FILE *f = fopen ("conftest.out", "w"); + return ferror (f) || fclose (f) != 0; + + ; + return 0; +} +_ACEOF +ac_clean_files="$ac_clean_files conftest.out" +# Check that the compiler produces executables we can run. If not, either +# the compiler is broken, or we cross compile. +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether we are cross compiling" >&5 +printf %s "checking whether we are cross compiling... " >&6; } +if test "$cross_compiling" != yes; then + { { ac_try="$ac_link" +case "(($ac_try" in + *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; + *) ac_try_echo=$ac_try;; +esac +eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" +printf "%s\n" "$ac_try_echo"; } >&5 + (eval "$ac_link") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } + if { ac_try='./conftest$ac_cv_exeext' + { { case "(($ac_try" in + *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; + *) ac_try_echo=$ac_try;; +esac +eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" +printf "%s\n" "$ac_try_echo"; } >&5 + (eval "$ac_try") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; }; then + cross_compiling=no + else + if test "$cross_compiling" = maybe; then + cross_compiling=yes + else + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 +printf "%s\n" "$as_me: error: in \`$ac_pwd':" >&2;} +as_fn_error 77 "cannot run C compiled programs. +If you meant to cross compile, use \`--host'. +See \`config.log' for more details" "$LINENO" 5; } + fi + fi +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $cross_compiling" >&5 +printf "%s\n" "$cross_compiling" >&6; } + +rm -f conftest.$ac_ext conftest$ac_cv_exeext conftest.out +ac_clean_files=$ac_clean_files_save +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for suffix of object files" >&5 +printf %s "checking for suffix of object files... " >&6; } +if test ${ac_cv_objext+y} +then : + printf %s "(cached) " >&6 +else $as_nop + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +int +main (void) +{ + + ; + return 0; +} +_ACEOF +rm -f conftest.o conftest.obj +if { { ac_try="$ac_compile" +case "(($ac_try" in + *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; + *) ac_try_echo=$ac_try;; +esac +eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" +printf "%s\n" "$ac_try_echo"; } >&5 + (eval "$ac_compile") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } +then : + for ac_file in conftest.o conftest.obj conftest.*; do + test -f "$ac_file" || continue; + case $ac_file in + *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM ) ;; + *) ac_cv_objext=`expr "$ac_file" : '.*\.\(.*\)'` + break;; + esac +done +else $as_nop + printf "%s\n" "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +{ { printf "%s\n" "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 +printf "%s\n" "$as_me: error: in \`$ac_pwd':" >&2;} +as_fn_error $? "cannot compute suffix of object files: cannot compile +See \`config.log' for more details" "$LINENO" 5; } +fi +rm -f conftest.$ac_cv_objext conftest.$ac_ext +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_objext" >&5 +printf "%s\n" "$ac_cv_objext" >&6; } +OBJEXT=$ac_cv_objext +ac_objext=$OBJEXT +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether the compiler supports GNU C" >&5 +printf %s "checking whether the compiler supports GNU C... " >&6; } +if test ${ac_cv_c_compiler_gnu+y} +then : + printf %s "(cached) " >&6 +else $as_nop + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +int +main (void) +{ +#ifndef __GNUC__ + choke me +#endif + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + ac_compiler_gnu=yes +else $as_nop + ac_compiler_gnu=no +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext +ac_cv_c_compiler_gnu=$ac_compiler_gnu + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_c_compiler_gnu" >&5 +printf "%s\n" "$ac_cv_c_compiler_gnu" >&6; } +ac_compiler_gnu=$ac_cv_c_compiler_gnu + +if test $ac_compiler_gnu = yes; then + GCC=yes +else + GCC= +fi +ac_test_CFLAGS=${CFLAGS+y} +ac_save_CFLAGS=$CFLAGS +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether $CC accepts -g" >&5 +printf %s "checking whether $CC accepts -g... " >&6; } +if test ${ac_cv_prog_cc_g+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ac_save_c_werror_flag=$ac_c_werror_flag + ac_c_werror_flag=yes + ac_cv_prog_cc_g=no + CFLAGS="-g" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +int +main (void) +{ + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + ac_cv_prog_cc_g=yes +else $as_nop + CFLAGS="" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +int +main (void) +{ + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + +else $as_nop + ac_c_werror_flag=$ac_save_c_werror_flag + CFLAGS="-g" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +int +main (void) +{ + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + ac_cv_prog_cc_g=yes +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext + ac_c_werror_flag=$ac_save_c_werror_flag +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_g" >&5 +printf "%s\n" "$ac_cv_prog_cc_g" >&6; } +if test $ac_test_CFLAGS; then + CFLAGS=$ac_save_CFLAGS +elif test $ac_cv_prog_cc_g = yes; then + if test "$GCC" = yes; then + CFLAGS="-g -O2" + else + CFLAGS="-g" + fi +else + if test "$GCC" = yes; then + CFLAGS="-O2" + else + CFLAGS= + fi +fi +ac_prog_cc_stdc=no +if test x$ac_prog_cc_stdc = xno +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $CC option to enable C11 features" >&5 +printf %s "checking for $CC option to enable C11 features... " >&6; } +if test ${ac_cv_prog_cc_c11+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ac_cv_prog_cc_c11=no +ac_save_CC=$CC +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +$ac_c_conftest_c11_program +_ACEOF +for ac_arg in '' -std=gnu11 +do + CC="$ac_save_CC $ac_arg" + if ac_fn_c_try_compile "$LINENO" +then : + ac_cv_prog_cc_c11=$ac_arg +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam + test "x$ac_cv_prog_cc_c11" != "xno" && break +done +rm -f conftest.$ac_ext +CC=$ac_save_CC +fi + +if test "x$ac_cv_prog_cc_c11" = xno +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: unsupported" >&5 +printf "%s\n" "unsupported" >&6; } +else $as_nop + if test "x$ac_cv_prog_cc_c11" = x +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: none needed" >&5 +printf "%s\n" "none needed" >&6; } +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_c11" >&5 +printf "%s\n" "$ac_cv_prog_cc_c11" >&6; } + CC="$CC $ac_cv_prog_cc_c11" +fi + ac_cv_prog_cc_stdc=$ac_cv_prog_cc_c11 + ac_prog_cc_stdc=c11 +fi +fi +if test x$ac_prog_cc_stdc = xno +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $CC option to enable C99 features" >&5 +printf %s "checking for $CC option to enable C99 features... " >&6; } +if test ${ac_cv_prog_cc_c99+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ac_cv_prog_cc_c99=no +ac_save_CC=$CC +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +$ac_c_conftest_c99_program +_ACEOF +for ac_arg in '' -std=gnu99 -std=c99 -c99 -qlanglvl=extc1x -qlanglvl=extc99 -AC99 -D_STDC_C99= +do + CC="$ac_save_CC $ac_arg" + if ac_fn_c_try_compile "$LINENO" +then : + ac_cv_prog_cc_c99=$ac_arg +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam + test "x$ac_cv_prog_cc_c99" != "xno" && break +done +rm -f conftest.$ac_ext +CC=$ac_save_CC +fi + +if test "x$ac_cv_prog_cc_c99" = xno +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: unsupported" >&5 +printf "%s\n" "unsupported" >&6; } +else $as_nop + if test "x$ac_cv_prog_cc_c99" = x +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: none needed" >&5 +printf "%s\n" "none needed" >&6; } +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_c99" >&5 +printf "%s\n" "$ac_cv_prog_cc_c99" >&6; } + CC="$CC $ac_cv_prog_cc_c99" +fi + ac_cv_prog_cc_stdc=$ac_cv_prog_cc_c99 + ac_prog_cc_stdc=c99 +fi +fi +if test x$ac_prog_cc_stdc = xno +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $CC option to enable C89 features" >&5 +printf %s "checking for $CC option to enable C89 features... " >&6; } +if test ${ac_cv_prog_cc_c89+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ac_cv_prog_cc_c89=no +ac_save_CC=$CC +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +$ac_c_conftest_c89_program +_ACEOF +for ac_arg in '' -qlanglvl=extc89 -qlanglvl=ansi -std -Ae "-Aa -D_HPUX_SOURCE" "-Xc -D__EXTENSIONS__" +do + CC="$ac_save_CC $ac_arg" + if ac_fn_c_try_compile "$LINENO" +then : + ac_cv_prog_cc_c89=$ac_arg +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam + test "x$ac_cv_prog_cc_c89" != "xno" && break +done +rm -f conftest.$ac_ext +CC=$ac_save_CC +fi + +if test "x$ac_cv_prog_cc_c89" = xno +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: unsupported" >&5 +printf "%s\n" "unsupported" >&6; } +else $as_nop + if test "x$ac_cv_prog_cc_c89" = x +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: none needed" >&5 +printf "%s\n" "none needed" >&6; } +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_c89" >&5 +printf "%s\n" "$ac_cv_prog_cc_c89" >&6; } + CC="$CC $ac_cv_prog_cc_c89" +fi + ac_cv_prog_cc_stdc=$ac_cv_prog_cc_c89 + ac_prog_cc_stdc=c89 +fi +fi + +ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu + +ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking how to run the C preprocessor" >&5 +printf %s "checking how to run the C preprocessor... " >&6; } +# On Suns, sometimes $CPP names a directory. +if test -n "$CPP" && test -d "$CPP"; then + CPP= +fi +if test -z "$CPP"; then + if test ${ac_cv_prog_CPP+y} +then : + printf %s "(cached) " >&6 +else $as_nop + # Double quotes because $CC needs to be expanded + for CPP in "$CC -E" "$CC -E -traditional-cpp" cpp /lib/cpp + do + ac_preproc_ok=false +for ac_c_preproc_warn_flag in '' yes +do + # Use a header file that comes with gcc, so configuring glibc + # with a fresh cross-compiler works. + # On the NeXT, cc -E runs the code through the compiler's parser, + # not just through cpp. "Syntax error" is here to catch this case. + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#include + Syntax error +_ACEOF +if ac_fn_c_try_cpp "$LINENO" +then : + +else $as_nop + # Broken: fails on valid input. +continue +fi +rm -f conftest.err conftest.i conftest.$ac_ext + + # OK, works on sane cases. Now check whether nonexistent headers + # can be detected and how. + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#include +_ACEOF +if ac_fn_c_try_cpp "$LINENO" +then : + # Broken: success on invalid input. +continue +else $as_nop + # Passes both tests. +ac_preproc_ok=: +break +fi +rm -f conftest.err conftest.i conftest.$ac_ext + +done +# Because of `break', _AC_PREPROC_IFELSE's cleaning code was skipped. +rm -f conftest.i conftest.err conftest.$ac_ext +if $ac_preproc_ok +then : + break +fi + + done + ac_cv_prog_CPP=$CPP + +fi + CPP=$ac_cv_prog_CPP +else + ac_cv_prog_CPP=$CPP +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $CPP" >&5 +printf "%s\n" "$CPP" >&6; } +ac_preproc_ok=false +for ac_c_preproc_warn_flag in '' yes +do + # Use a header file that comes with gcc, so configuring glibc + # with a fresh cross-compiler works. + # On the NeXT, cc -E runs the code through the compiler's parser, + # not just through cpp. "Syntax error" is here to catch this case. + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#include + Syntax error +_ACEOF +if ac_fn_c_try_cpp "$LINENO" +then : + +else $as_nop + # Broken: fails on valid input. +continue +fi +rm -f conftest.err conftest.i conftest.$ac_ext + + # OK, works on sane cases. Now check whether nonexistent headers + # can be detected and how. + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#include +_ACEOF +if ac_fn_c_try_cpp "$LINENO" +then : + # Broken: success on invalid input. +continue +else $as_nop + # Passes both tests. +ac_preproc_ok=: +break +fi +rm -f conftest.err conftest.i conftest.$ac_ext + +done +# Because of `break', _AC_PREPROC_IFELSE's cleaning code was skipped. +rm -f conftest.i conftest.err conftest.$ac_ext +if $ac_preproc_ok +then : + +else $as_nop + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 +printf "%s\n" "$as_me: error: in \`$ac_pwd':" >&2;} +as_fn_error $? "C preprocessor \"$CPP\" fails sanity check +See \`config.log' for more details" "$LINENO" 5; } +fi + +ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu + + + + + + + + + + +if test "x$ac_cv_env_PKG_CONFIG_set" != "xset"; then + if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}pkg-config", so it can be a program name with args. +set dummy ${ac_tool_prefix}pkg-config; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_path_PKG_CONFIG+y} +then : + printf %s "(cached) " >&6 +else $as_nop + case $PKG_CONFIG in + [\\/]* | ?:[\\/]*) + ac_cv_path_PKG_CONFIG="$PKG_CONFIG" # Let the user override the test with a path. + ;; + *) + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_path_PKG_CONFIG="$as_dir$ac_word$ac_exec_ext" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + + ;; +esac +fi +PKG_CONFIG=$ac_cv_path_PKG_CONFIG +if test -n "$PKG_CONFIG"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $PKG_CONFIG" >&5 +printf "%s\n" "$PKG_CONFIG" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_path_PKG_CONFIG"; then + ac_pt_PKG_CONFIG=$PKG_CONFIG + # Extract the first word of "pkg-config", so it can be a program name with args. +set dummy pkg-config; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_path_ac_pt_PKG_CONFIG+y} +then : + printf %s "(cached) " >&6 +else $as_nop + case $ac_pt_PKG_CONFIG in + [\\/]* | ?:[\\/]*) + ac_cv_path_ac_pt_PKG_CONFIG="$ac_pt_PKG_CONFIG" # Let the user override the test with a path. + ;; + *) + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_path_ac_pt_PKG_CONFIG="$as_dir$ac_word$ac_exec_ext" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + + ;; +esac +fi +ac_pt_PKG_CONFIG=$ac_cv_path_ac_pt_PKG_CONFIG +if test -n "$ac_pt_PKG_CONFIG"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_pt_PKG_CONFIG" >&5 +printf "%s\n" "$ac_pt_PKG_CONFIG" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_pt_PKG_CONFIG" = x; then + PKG_CONFIG="" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + PKG_CONFIG=$ac_pt_PKG_CONFIG + fi +else + PKG_CONFIG="$ac_cv_path_PKG_CONFIG" +fi + +fi +if test -n "$PKG_CONFIG"; then + _pkg_min_version=0.24 + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking pkg-config is at least version $_pkg_min_version" >&5 +printf %s "checking pkg-config is at least version $_pkg_min_version... " >&6; } + if $PKG_CONFIG --atleast-pkgconfig-version $_pkg_min_version; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +printf "%s\n" "yes" >&6; } + else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } + PKG_CONFIG="" + fi +fi + + +case `pwd` in + *\ * | *\ *) + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: Libtool does not cope well with whitespace in \`pwd\`" >&5 +printf "%s\n" "$as_me: WARNING: Libtool does not cope well with whitespace in \`pwd\`" >&2;} ;; +esac + + + +macro_version='2.4.7' +macro_revision='2.4.7' + + + + + + + + + + + + + + +ltmain=$ac_aux_dir/ltmain.sh + +# Backslashify metacharacters that are still active within +# double-quoted strings. +sed_quote_subst='s/\(["`$\\]\)/\\\1/g' + +# Same as above, but do not quote variable references. +double_quote_subst='s/\(["`\\]\)/\\\1/g' + +# Sed substitution to delay expansion of an escaped shell variable in a +# double_quote_subst'ed string. +delay_variable_subst='s/\\\\\\\\\\\$/\\\\\\$/g' + +# Sed substitution to delay expansion of an escaped single quote. +delay_single_quote_subst='s/'\''/'\'\\\\\\\'\''/g' + +# Sed substitution to avoid accidental globbing in evaled expressions +no_glob_subst='s/\*/\\\*/g' + +ECHO='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' +ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO +ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO$ECHO + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking how to print strings" >&5 +printf %s "checking how to print strings... " >&6; } +# Test print first, because it will be a builtin if present. +if test "X`( print -r -- -n ) 2>/dev/null`" = X-n && \ + test "X`print -r -- $ECHO 2>/dev/null`" = "X$ECHO"; then + ECHO='print -r --' +elif test "X`printf %s $ECHO 2>/dev/null`" = "X$ECHO"; then + ECHO='printf %s\n' +else + # Use this function as a fallback that always works. + func_fallback_echo () + { + eval 'cat <<_LTECHO_EOF +$1 +_LTECHO_EOF' + } + ECHO='func_fallback_echo' +fi + +# func_echo_all arg... +# Invoke $ECHO with all args, space-separated. +func_echo_all () +{ + $ECHO "" +} + +case $ECHO in + printf*) { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: printf" >&5 +printf "%s\n" "printf" >&6; } ;; + print*) { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: print -r" >&5 +printf "%s\n" "print -r" >&6; } ;; + *) { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: cat" >&5 +printf "%s\n" "cat" >&6; } ;; +esac + + + + + + + + + + + + + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for a sed that does not truncate output" >&5 +printf %s "checking for a sed that does not truncate output... " >&6; } +if test ${ac_cv_path_SED+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ac_script=s/aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa/bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb/ + for ac_i in 1 2 3 4 5 6 7; do + ac_script="$ac_script$as_nl$ac_script" + done + echo "$ac_script" 2>/dev/null | sed 99q >conftest.sed + { ac_script=; unset ac_script;} + if test -z "$SED"; then + ac_path_SED_found=false + # Loop through the user's path and test for each of PROGNAME-LIST + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_prog in sed gsed + do + for ac_exec_ext in '' $ac_executable_extensions; do + ac_path_SED="$as_dir$ac_prog$ac_exec_ext" + as_fn_executable_p "$ac_path_SED" || continue +# Check for GNU ac_path_SED and select it if it is found. + # Check for GNU $ac_path_SED +case `"$ac_path_SED" --version 2>&1` in +*GNU*) + ac_cv_path_SED="$ac_path_SED" ac_path_SED_found=:;; +*) + ac_count=0 + printf %s 0123456789 >"conftest.in" + while : + do + cat "conftest.in" "conftest.in" >"conftest.tmp" + mv "conftest.tmp" "conftest.in" + cp "conftest.in" "conftest.nl" + printf "%s\n" '' >> "conftest.nl" + "$ac_path_SED" -f conftest.sed < "conftest.nl" >"conftest.out" 2>/dev/null || break + diff "conftest.out" "conftest.nl" >/dev/null 2>&1 || break + as_fn_arith $ac_count + 1 && ac_count=$as_val + if test $ac_count -gt ${ac_path_SED_max-0}; then + # Best one so far, save it but keep looking for a better one + ac_cv_path_SED="$ac_path_SED" + ac_path_SED_max=$ac_count + fi + # 10*(2^10) chars as input seems more than enough + test $ac_count -gt 10 && break + done + rm -f conftest.in conftest.tmp conftest.nl conftest.out;; +esac + + $ac_path_SED_found && break 3 + done + done + done +IFS=$as_save_IFS + if test -z "$ac_cv_path_SED"; then + as_fn_error $? "no acceptable sed could be found in \$PATH" "$LINENO" 5 + fi +else + ac_cv_path_SED=$SED +fi + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_SED" >&5 +printf "%s\n" "$ac_cv_path_SED" >&6; } + SED="$ac_cv_path_SED" + rm -f conftest.sed + +test -z "$SED" && SED=sed +Xsed="$SED -e 1s/^X//" + + + + + + + + + + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for grep that handles long lines and -e" >&5 +printf %s "checking for grep that handles long lines and -e... " >&6; } +if test ${ac_cv_path_GREP+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -z "$GREP"; then + ac_path_GREP_found=false + # Loop through the user's path and test for each of PROGNAME-LIST + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH$PATH_SEPARATOR/usr/xpg4/bin +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_prog in grep ggrep + do + for ac_exec_ext in '' $ac_executable_extensions; do + ac_path_GREP="$as_dir$ac_prog$ac_exec_ext" + as_fn_executable_p "$ac_path_GREP" || continue +# Check for GNU ac_path_GREP and select it if it is found. + # Check for GNU $ac_path_GREP +case `"$ac_path_GREP" --version 2>&1` in +*GNU*) + ac_cv_path_GREP="$ac_path_GREP" ac_path_GREP_found=:;; +*) + ac_count=0 + printf %s 0123456789 >"conftest.in" + while : + do + cat "conftest.in" "conftest.in" >"conftest.tmp" + mv "conftest.tmp" "conftest.in" + cp "conftest.in" "conftest.nl" + printf "%s\n" 'GREP' >> "conftest.nl" + "$ac_path_GREP" -e 'GREP$' -e '-(cannot match)-' < "conftest.nl" >"conftest.out" 2>/dev/null || break + diff "conftest.out" "conftest.nl" >/dev/null 2>&1 || break + as_fn_arith $ac_count + 1 && ac_count=$as_val + if test $ac_count -gt ${ac_path_GREP_max-0}; then + # Best one so far, save it but keep looking for a better one + ac_cv_path_GREP="$ac_path_GREP" + ac_path_GREP_max=$ac_count + fi + # 10*(2^10) chars as input seems more than enough + test $ac_count -gt 10 && break + done + rm -f conftest.in conftest.tmp conftest.nl conftest.out;; +esac + + $ac_path_GREP_found && break 3 + done + done + done +IFS=$as_save_IFS + if test -z "$ac_cv_path_GREP"; then + as_fn_error $? "no acceptable grep could be found in $PATH$PATH_SEPARATOR/usr/xpg4/bin" "$LINENO" 5 + fi +else + ac_cv_path_GREP=$GREP +fi + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_GREP" >&5 +printf "%s\n" "$ac_cv_path_GREP" >&6; } + GREP="$ac_cv_path_GREP" + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for egrep" >&5 +printf %s "checking for egrep... " >&6; } +if test ${ac_cv_path_EGREP+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if echo a | $GREP -E '(a|b)' >/dev/null 2>&1 + then ac_cv_path_EGREP="$GREP -E" + else + if test -z "$EGREP"; then + ac_path_EGREP_found=false + # Loop through the user's path and test for each of PROGNAME-LIST + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH$PATH_SEPARATOR/usr/xpg4/bin +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_prog in egrep + do + for ac_exec_ext in '' $ac_executable_extensions; do + ac_path_EGREP="$as_dir$ac_prog$ac_exec_ext" + as_fn_executable_p "$ac_path_EGREP" || continue +# Check for GNU ac_path_EGREP and select it if it is found. + # Check for GNU $ac_path_EGREP +case `"$ac_path_EGREP" --version 2>&1` in +*GNU*) + ac_cv_path_EGREP="$ac_path_EGREP" ac_path_EGREP_found=:;; +*) + ac_count=0 + printf %s 0123456789 >"conftest.in" + while : + do + cat "conftest.in" "conftest.in" >"conftest.tmp" + mv "conftest.tmp" "conftest.in" + cp "conftest.in" "conftest.nl" + printf "%s\n" 'EGREP' >> "conftest.nl" + "$ac_path_EGREP" 'EGREP$' < "conftest.nl" >"conftest.out" 2>/dev/null || break + diff "conftest.out" "conftest.nl" >/dev/null 2>&1 || break + as_fn_arith $ac_count + 1 && ac_count=$as_val + if test $ac_count -gt ${ac_path_EGREP_max-0}; then + # Best one so far, save it but keep looking for a better one + ac_cv_path_EGREP="$ac_path_EGREP" + ac_path_EGREP_max=$ac_count + fi + # 10*(2^10) chars as input seems more than enough + test $ac_count -gt 10 && break + done + rm -f conftest.in conftest.tmp conftest.nl conftest.out;; +esac + + $ac_path_EGREP_found && break 3 + done + done + done +IFS=$as_save_IFS + if test -z "$ac_cv_path_EGREP"; then + as_fn_error $? "no acceptable egrep could be found in $PATH$PATH_SEPARATOR/usr/xpg4/bin" "$LINENO" 5 + fi +else + ac_cv_path_EGREP=$EGREP +fi + + fi +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_EGREP" >&5 +printf "%s\n" "$ac_cv_path_EGREP" >&6; } + EGREP="$ac_cv_path_EGREP" + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for fgrep" >&5 +printf %s "checking for fgrep... " >&6; } +if test ${ac_cv_path_FGREP+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if echo 'ab*c' | $GREP -F 'ab*c' >/dev/null 2>&1 + then ac_cv_path_FGREP="$GREP -F" + else + if test -z "$FGREP"; then + ac_path_FGREP_found=false + # Loop through the user's path and test for each of PROGNAME-LIST + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH$PATH_SEPARATOR/usr/xpg4/bin +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_prog in fgrep + do + for ac_exec_ext in '' $ac_executable_extensions; do + ac_path_FGREP="$as_dir$ac_prog$ac_exec_ext" + as_fn_executable_p "$ac_path_FGREP" || continue +# Check for GNU ac_path_FGREP and select it if it is found. + # Check for GNU $ac_path_FGREP +case `"$ac_path_FGREP" --version 2>&1` in +*GNU*) + ac_cv_path_FGREP="$ac_path_FGREP" ac_path_FGREP_found=:;; +*) + ac_count=0 + printf %s 0123456789 >"conftest.in" + while : + do + cat "conftest.in" "conftest.in" >"conftest.tmp" + mv "conftest.tmp" "conftest.in" + cp "conftest.in" "conftest.nl" + printf "%s\n" 'FGREP' >> "conftest.nl" + "$ac_path_FGREP" FGREP < "conftest.nl" >"conftest.out" 2>/dev/null || break + diff "conftest.out" "conftest.nl" >/dev/null 2>&1 || break + as_fn_arith $ac_count + 1 && ac_count=$as_val + if test $ac_count -gt ${ac_path_FGREP_max-0}; then + # Best one so far, save it but keep looking for a better one + ac_cv_path_FGREP="$ac_path_FGREP" + ac_path_FGREP_max=$ac_count + fi + # 10*(2^10) chars as input seems more than enough + test $ac_count -gt 10 && break + done + rm -f conftest.in conftest.tmp conftest.nl conftest.out;; +esac + + $ac_path_FGREP_found && break 3 + done + done + done +IFS=$as_save_IFS + if test -z "$ac_cv_path_FGREP"; then + as_fn_error $? "no acceptable fgrep could be found in $PATH$PATH_SEPARATOR/usr/xpg4/bin" "$LINENO" 5 + fi +else + ac_cv_path_FGREP=$FGREP +fi + + fi +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_FGREP" >&5 +printf "%s\n" "$ac_cv_path_FGREP" >&6; } + FGREP="$ac_cv_path_FGREP" + + +test -z "$GREP" && GREP=grep + + + + + + + + + + + + + + + + + + + +# Check whether --with-gnu-ld was given. +if test ${with_gnu_ld+y} +then : + withval=$with_gnu_ld; test no = "$withval" || with_gnu_ld=yes +else $as_nop + with_gnu_ld=no +fi + +ac_prog=ld +if test yes = "$GCC"; then + # Check if gcc -print-prog-name=ld gives a path. + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for ld used by $CC" >&5 +printf %s "checking for ld used by $CC... " >&6; } + case $host in + *-*-mingw*) + # gcc leaves a trailing carriage return, which upsets mingw + ac_prog=`($CC -print-prog-name=ld) 2>&5 | tr -d '\015'` ;; + *) + ac_prog=`($CC -print-prog-name=ld) 2>&5` ;; + esac + case $ac_prog in + # Accept absolute paths. + [\\/]* | ?:[\\/]*) + re_direlt='/[^/][^/]*/\.\./' + # Canonicalize the pathname of ld + ac_prog=`$ECHO "$ac_prog"| $SED 's%\\\\%/%g'` + while $ECHO "$ac_prog" | $GREP "$re_direlt" > /dev/null 2>&1; do + ac_prog=`$ECHO $ac_prog| $SED "s%$re_direlt%/%"` + done + test -z "$LD" && LD=$ac_prog + ;; + "") + # If it fails, then pretend we aren't using GCC. + ac_prog=ld + ;; + *) + # If it is relative, then search for the first ld in PATH. + with_gnu_ld=unknown + ;; + esac +elif test yes = "$with_gnu_ld"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for GNU ld" >&5 +printf %s "checking for GNU ld... " >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for non-GNU ld" >&5 +printf %s "checking for non-GNU ld... " >&6; } +fi +if test ${lt_cv_path_LD+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -z "$LD"; then + lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR + for ac_dir in $PATH; do + IFS=$lt_save_ifs + test -z "$ac_dir" && ac_dir=. + if test -f "$ac_dir/$ac_prog" || test -f "$ac_dir/$ac_prog$ac_exeext"; then + lt_cv_path_LD=$ac_dir/$ac_prog + # Check to see if the program is GNU ld. I'd rather use --version, + # but apparently some variants of GNU ld only accept -v. + # Break only if it was the GNU/non-GNU ld that we prefer. + case `"$lt_cv_path_LD" -v 2>&1 &5 +printf "%s\n" "$LD" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi +test -z "$LD" && as_fn_error $? "no acceptable ld found in \$PATH" "$LINENO" 5 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking if the linker ($LD) is GNU ld" >&5 +printf %s "checking if the linker ($LD) is GNU ld... " >&6; } +if test ${lt_cv_prog_gnu_ld+y} +then : + printf %s "(cached) " >&6 +else $as_nop + # I'd rather use --version here, but apparently some GNU lds only accept -v. +case `$LD -v 2>&1 &5 +printf "%s\n" "$lt_cv_prog_gnu_ld" >&6; } +with_gnu_ld=$lt_cv_prog_gnu_ld + + + + + + + + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for BSD- or MS-compatible name lister (nm)" >&5 +printf %s "checking for BSD- or MS-compatible name lister (nm)... " >&6; } +if test ${lt_cv_path_NM+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$NM"; then + # Let the user override the test. + lt_cv_path_NM=$NM +else + lt_nm_to_check=${ac_tool_prefix}nm + if test -n "$ac_tool_prefix" && test "$build" = "$host"; then + lt_nm_to_check="$lt_nm_to_check nm" + fi + for lt_tmp_nm in $lt_nm_to_check; do + lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR + for ac_dir in $PATH /usr/ccs/bin/elf /usr/ccs/bin /usr/ucb /bin; do + IFS=$lt_save_ifs + test -z "$ac_dir" && ac_dir=. + tmp_nm=$ac_dir/$lt_tmp_nm + if test -f "$tmp_nm" || test -f "$tmp_nm$ac_exeext"; then + # Check to see if the nm accepts a BSD-compat flag. + # Adding the 'sed 1q' prevents false positives on HP-UX, which says: + # nm: unknown option "B" ignored + # Tru64's nm complains that /dev/null is an invalid object file + # MSYS converts /dev/null to NUL, MinGW nm treats NUL as empty + case $build_os in + mingw*) lt_bad_file=conftest.nm/nofile ;; + *) lt_bad_file=/dev/null ;; + esac + case `"$tmp_nm" -B $lt_bad_file 2>&1 | $SED '1q'` in + *$lt_bad_file* | *'Invalid file or object type'*) + lt_cv_path_NM="$tmp_nm -B" + break 2 + ;; + *) + case `"$tmp_nm" -p /dev/null 2>&1 | $SED '1q'` in + */dev/null*) + lt_cv_path_NM="$tmp_nm -p" + break 2 + ;; + *) + lt_cv_path_NM=${lt_cv_path_NM="$tmp_nm"} # keep the first match, but + continue # so that we can try to find one that supports BSD flags + ;; + esac + ;; + esac + fi + done + IFS=$lt_save_ifs + done + : ${lt_cv_path_NM=no} +fi +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_path_NM" >&5 +printf "%s\n" "$lt_cv_path_NM" >&6; } +if test no != "$lt_cv_path_NM"; then + NM=$lt_cv_path_NM +else + # Didn't find any BSD compatible name lister, look for dumpbin. + if test -n "$DUMPBIN"; then : + # Let the user override the test. + else + if test -n "$ac_tool_prefix"; then + for ac_prog in dumpbin "link -dump" + do + # Extract the first word of "$ac_tool_prefix$ac_prog", so it can be a program name with args. +set dummy $ac_tool_prefix$ac_prog; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_DUMPBIN+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$DUMPBIN"; then + ac_cv_prog_DUMPBIN="$DUMPBIN" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_DUMPBIN="$ac_tool_prefix$ac_prog" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +DUMPBIN=$ac_cv_prog_DUMPBIN +if test -n "$DUMPBIN"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $DUMPBIN" >&5 +printf "%s\n" "$DUMPBIN" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + test -n "$DUMPBIN" && break + done +fi +if test -z "$DUMPBIN"; then + ac_ct_DUMPBIN=$DUMPBIN + for ac_prog in dumpbin "link -dump" +do + # Extract the first word of "$ac_prog", so it can be a program name with args. +set dummy $ac_prog; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_DUMPBIN+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_DUMPBIN"; then + ac_cv_prog_ac_ct_DUMPBIN="$ac_ct_DUMPBIN" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_DUMPBIN="$ac_prog" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_DUMPBIN=$ac_cv_prog_ac_ct_DUMPBIN +if test -n "$ac_ct_DUMPBIN"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_DUMPBIN" >&5 +printf "%s\n" "$ac_ct_DUMPBIN" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + test -n "$ac_ct_DUMPBIN" && break +done + + if test "x$ac_ct_DUMPBIN" = x; then + DUMPBIN=":" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + DUMPBIN=$ac_ct_DUMPBIN + fi +fi + + case `$DUMPBIN -symbols -headers /dev/null 2>&1 | $SED '1q'` in + *COFF*) + DUMPBIN="$DUMPBIN -symbols -headers" + ;; + *) + DUMPBIN=: + ;; + esac + fi + + if test : != "$DUMPBIN"; then + NM=$DUMPBIN + fi +fi +test -z "$NM" && NM=nm + + + + + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking the name lister ($NM) interface" >&5 +printf %s "checking the name lister ($NM) interface... " >&6; } +if test ${lt_cv_nm_interface+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_nm_interface="BSD nm" + echo "int some_variable = 0;" > conftest.$ac_ext + (eval echo "\"\$as_me:$LINENO: $ac_compile\"" >&5) + (eval "$ac_compile" 2>conftest.err) + cat conftest.err >&5 + (eval echo "\"\$as_me:$LINENO: $NM \\\"conftest.$ac_objext\\\"\"" >&5) + (eval "$NM \"conftest.$ac_objext\"" 2>conftest.err > conftest.out) + cat conftest.err >&5 + (eval echo "\"\$as_me:$LINENO: output\"" >&5) + cat conftest.out >&5 + if $GREP 'External.*some_variable' conftest.out > /dev/null; then + lt_cv_nm_interface="MS dumpbin" + fi + rm -f conftest* +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_nm_interface" >&5 +printf "%s\n" "$lt_cv_nm_interface" >&6; } + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether ln -s works" >&5 +printf %s "checking whether ln -s works... " >&6; } +LN_S=$as_ln_s +if test "$LN_S" = "ln -s"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +printf "%s\n" "yes" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no, using $LN_S" >&5 +printf "%s\n" "no, using $LN_S" >&6; } +fi + +# find the maximum length of command line arguments +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking the maximum length of command line arguments" >&5 +printf %s "checking the maximum length of command line arguments... " >&6; } +if test ${lt_cv_sys_max_cmd_len+y} +then : + printf %s "(cached) " >&6 +else $as_nop + i=0 + teststring=ABCD + + case $build_os in + msdosdjgpp*) + # On DJGPP, this test can blow up pretty badly due to problems in libc + # (any single argument exceeding 2000 bytes causes a buffer overrun + # during glob expansion). Even if it were fixed, the result of this + # check would be larger than it should be. + lt_cv_sys_max_cmd_len=12288; # 12K is about right + ;; + + gnu*) + # Under GNU Hurd, this test is not required because there is + # no limit to the length of command line arguments. + # Libtool will interpret -1 as no limit whatsoever + lt_cv_sys_max_cmd_len=-1; + ;; + + cygwin* | mingw* | cegcc*) + # On Win9x/ME, this test blows up -- it succeeds, but takes + # about 5 minutes as the teststring grows exponentially. + # Worse, since 9x/ME are not pre-emptively multitasking, + # you end up with a "frozen" computer, even though with patience + # the test eventually succeeds (with a max line length of 256k). + # Instead, let's just punt: use the minimum linelength reported by + # all of the supported platforms: 8192 (on NT/2K/XP). + lt_cv_sys_max_cmd_len=8192; + ;; + + mint*) + # On MiNT this can take a long time and run out of memory. + lt_cv_sys_max_cmd_len=8192; + ;; + + amigaos*) + # On AmigaOS with pdksh, this test takes hours, literally. + # So we just punt and use a minimum line length of 8192. + lt_cv_sys_max_cmd_len=8192; + ;; + + bitrig* | darwin* | dragonfly* | freebsd* | midnightbsd* | netbsd* | openbsd*) + # This has been around since 386BSD, at least. Likely further. + if test -x /sbin/sysctl; then + lt_cv_sys_max_cmd_len=`/sbin/sysctl -n kern.argmax` + elif test -x /usr/sbin/sysctl; then + lt_cv_sys_max_cmd_len=`/usr/sbin/sysctl -n kern.argmax` + else + lt_cv_sys_max_cmd_len=65536 # usable default for all BSDs + fi + # And add a safety zone + lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \/ 4` + lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \* 3` + ;; + + interix*) + # We know the value 262144 and hardcode it with a safety zone (like BSD) + lt_cv_sys_max_cmd_len=196608 + ;; + + os2*) + # The test takes a long time on OS/2. + lt_cv_sys_max_cmd_len=8192 + ;; + + osf*) + # Dr. Hans Ekkehard Plesser reports seeing a kernel panic running configure + # due to this test when exec_disable_arg_limit is 1 on Tru64. It is not + # nice to cause kernel panics so lets avoid the loop below. + # First set a reasonable default. + lt_cv_sys_max_cmd_len=16384 + # + if test -x /sbin/sysconfig; then + case `/sbin/sysconfig -q proc exec_disable_arg_limit` in + *1*) lt_cv_sys_max_cmd_len=-1 ;; + esac + fi + ;; + sco3.2v5*) + lt_cv_sys_max_cmd_len=102400 + ;; + sysv5* | sco5v6* | sysv4.2uw2*) + kargmax=`grep ARG_MAX /etc/conf/cf.d/stune 2>/dev/null` + if test -n "$kargmax"; then + lt_cv_sys_max_cmd_len=`echo $kargmax | $SED 's/.*[ ]//'` + else + lt_cv_sys_max_cmd_len=32768 + fi + ;; + *) + lt_cv_sys_max_cmd_len=`(getconf ARG_MAX) 2> /dev/null` + if test -n "$lt_cv_sys_max_cmd_len" && \ + test undefined != "$lt_cv_sys_max_cmd_len"; then + lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \/ 4` + lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \* 3` + else + # Make teststring a little bigger before we do anything with it. + # a 1K string should be a reasonable start. + for i in 1 2 3 4 5 6 7 8; do + teststring=$teststring$teststring + done + SHELL=${SHELL-${CONFIG_SHELL-/bin/sh}} + # If test is not a shell built-in, we'll probably end up computing a + # maximum length that is only half of the actual maximum length, but + # we can't tell. + while { test X`env echo "$teststring$teststring" 2>/dev/null` \ + = "X$teststring$teststring"; } >/dev/null 2>&1 && + test 17 != "$i" # 1/2 MB should be enough + do + i=`expr $i + 1` + teststring=$teststring$teststring + done + # Only check the string length outside the loop. + lt_cv_sys_max_cmd_len=`expr "X$teststring" : ".*" 2>&1` + teststring= + # Add a significant safety factor because C++ compilers can tack on + # massive amounts of additional arguments before passing them to the + # linker. It appears as though 1/2 is a usable value. + lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \/ 2` + fi + ;; + esac + +fi + +if test -n "$lt_cv_sys_max_cmd_len"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_sys_max_cmd_len" >&5 +printf "%s\n" "$lt_cv_sys_max_cmd_len" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: none" >&5 +printf "%s\n" "none" >&6; } +fi +max_cmd_len=$lt_cv_sys_max_cmd_len + + + + + + +: ${CP="cp -f"} +: ${MV="mv -f"} +: ${RM="rm -f"} + +if ( (MAIL=60; unset MAIL) || exit) >/dev/null 2>&1; then + lt_unset=unset +else + lt_unset=false +fi + + + + + +# test EBCDIC or ASCII +case `echo X|tr X '\101'` in + A) # ASCII based system + # \n is not interpreted correctly by Solaris 8 /usr/ucb/tr + lt_SP2NL='tr \040 \012' + lt_NL2SP='tr \015\012 \040\040' + ;; + *) # EBCDIC based system + lt_SP2NL='tr \100 \n' + lt_NL2SP='tr \r\n \100\100' + ;; +esac + + + + + + + + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking how to convert $build file names to $host format" >&5 +printf %s "checking how to convert $build file names to $host format... " >&6; } +if test ${lt_cv_to_host_file_cmd+y} +then : + printf %s "(cached) " >&6 +else $as_nop + case $host in + *-*-mingw* ) + case $build in + *-*-mingw* ) # actually msys + lt_cv_to_host_file_cmd=func_convert_file_msys_to_w32 + ;; + *-*-cygwin* ) + lt_cv_to_host_file_cmd=func_convert_file_cygwin_to_w32 + ;; + * ) # otherwise, assume *nix + lt_cv_to_host_file_cmd=func_convert_file_nix_to_w32 + ;; + esac + ;; + *-*-cygwin* ) + case $build in + *-*-mingw* ) # actually msys + lt_cv_to_host_file_cmd=func_convert_file_msys_to_cygwin + ;; + *-*-cygwin* ) + lt_cv_to_host_file_cmd=func_convert_file_noop + ;; + * ) # otherwise, assume *nix + lt_cv_to_host_file_cmd=func_convert_file_nix_to_cygwin + ;; + esac + ;; + * ) # unhandled hosts (and "normal" native builds) + lt_cv_to_host_file_cmd=func_convert_file_noop + ;; +esac + +fi + +to_host_file_cmd=$lt_cv_to_host_file_cmd +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_to_host_file_cmd" >&5 +printf "%s\n" "$lt_cv_to_host_file_cmd" >&6; } + + + + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking how to convert $build file names to toolchain format" >&5 +printf %s "checking how to convert $build file names to toolchain format... " >&6; } +if test ${lt_cv_to_tool_file_cmd+y} +then : + printf %s "(cached) " >&6 +else $as_nop + #assume ordinary cross tools, or native build. +lt_cv_to_tool_file_cmd=func_convert_file_noop +case $host in + *-*-mingw* ) + case $build in + *-*-mingw* ) # actually msys + lt_cv_to_tool_file_cmd=func_convert_file_msys_to_w32 + ;; + esac + ;; +esac + +fi + +to_tool_file_cmd=$lt_cv_to_tool_file_cmd +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_to_tool_file_cmd" >&5 +printf "%s\n" "$lt_cv_to_tool_file_cmd" >&6; } + + + + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $LD option to reload object files" >&5 +printf %s "checking for $LD option to reload object files... " >&6; } +if test ${lt_cv_ld_reload_flag+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_ld_reload_flag='-r' +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_ld_reload_flag" >&5 +printf "%s\n" "$lt_cv_ld_reload_flag" >&6; } +reload_flag=$lt_cv_ld_reload_flag +case $reload_flag in +"" | " "*) ;; +*) reload_flag=" $reload_flag" ;; +esac +reload_cmds='$LD$reload_flag -o $output$reload_objs' +case $host_os in + cygwin* | mingw* | pw32* | cegcc*) + if test yes != "$GCC"; then + reload_cmds=false + fi + ;; + darwin*) + if test yes = "$GCC"; then + reload_cmds='$LTCC $LTCFLAGS -nostdlib $wl-r -o $output$reload_objs' + else + reload_cmds='$LD$reload_flag -o $output$reload_objs' + fi + ;; +esac + + + + + + + + + +if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}file", so it can be a program name with args. +set dummy ${ac_tool_prefix}file; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_FILECMD+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$FILECMD"; then + ac_cv_prog_FILECMD="$FILECMD" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_FILECMD="${ac_tool_prefix}file" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +FILECMD=$ac_cv_prog_FILECMD +if test -n "$FILECMD"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $FILECMD" >&5 +printf "%s\n" "$FILECMD" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_FILECMD"; then + ac_ct_FILECMD=$FILECMD + # Extract the first word of "file", so it can be a program name with args. +set dummy file; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_FILECMD+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_FILECMD"; then + ac_cv_prog_ac_ct_FILECMD="$ac_ct_FILECMD" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_FILECMD="file" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_FILECMD=$ac_cv_prog_ac_ct_FILECMD +if test -n "$ac_ct_FILECMD"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_FILECMD" >&5 +printf "%s\n" "$ac_ct_FILECMD" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_ct_FILECMD" = x; then + FILECMD=":" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + FILECMD=$ac_ct_FILECMD + fi +else + FILECMD="$ac_cv_prog_FILECMD" +fi + + + + + + + +if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}objdump", so it can be a program name with args. +set dummy ${ac_tool_prefix}objdump; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_OBJDUMP+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$OBJDUMP"; then + ac_cv_prog_OBJDUMP="$OBJDUMP" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_OBJDUMP="${ac_tool_prefix}objdump" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +OBJDUMP=$ac_cv_prog_OBJDUMP +if test -n "$OBJDUMP"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $OBJDUMP" >&5 +printf "%s\n" "$OBJDUMP" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_OBJDUMP"; then + ac_ct_OBJDUMP=$OBJDUMP + # Extract the first word of "objdump", so it can be a program name with args. +set dummy objdump; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_OBJDUMP+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_OBJDUMP"; then + ac_cv_prog_ac_ct_OBJDUMP="$ac_ct_OBJDUMP" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_OBJDUMP="objdump" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_OBJDUMP=$ac_cv_prog_ac_ct_OBJDUMP +if test -n "$ac_ct_OBJDUMP"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_OBJDUMP" >&5 +printf "%s\n" "$ac_ct_OBJDUMP" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_ct_OBJDUMP" = x; then + OBJDUMP="false" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + OBJDUMP=$ac_ct_OBJDUMP + fi +else + OBJDUMP="$ac_cv_prog_OBJDUMP" +fi + +test -z "$OBJDUMP" && OBJDUMP=objdump + + + + + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking how to recognize dependent libraries" >&5 +printf %s "checking how to recognize dependent libraries... " >&6; } +if test ${lt_cv_deplibs_check_method+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_file_magic_cmd='$MAGIC_CMD' +lt_cv_file_magic_test_file= +lt_cv_deplibs_check_method='unknown' +# Need to set the preceding variable on all platforms that support +# interlibrary dependencies. +# 'none' -- dependencies not supported. +# 'unknown' -- same as none, but documents that we really don't know. +# 'pass_all' -- all dependencies passed with no checks. +# 'test_compile' -- check by making test program. +# 'file_magic [[regex]]' -- check by looking for files in library path +# that responds to the $file_magic_cmd with a given extended regex. +# If you have 'file' or equivalent on your system and you're not sure +# whether 'pass_all' will *always* work, you probably want this one. + +case $host_os in +aix[4-9]*) + lt_cv_deplibs_check_method=pass_all + ;; + +beos*) + lt_cv_deplibs_check_method=pass_all + ;; + +bsdi[45]*) + lt_cv_deplibs_check_method='file_magic ELF [0-9][0-9]*-bit [ML]SB (shared object|dynamic lib)' + lt_cv_file_magic_cmd='$FILECMD -L' + lt_cv_file_magic_test_file=/shlib/libc.so + ;; + +cygwin*) + # func_win32_libid is a shell function defined in ltmain.sh + lt_cv_deplibs_check_method='file_magic ^x86 archive import|^x86 DLL' + lt_cv_file_magic_cmd='func_win32_libid' + ;; + +mingw* | pw32*) + # Base MSYS/MinGW do not provide the 'file' command needed by + # func_win32_libid shell function, so use a weaker test based on 'objdump', + # unless we find 'file', for example because we are cross-compiling. + if ( file / ) >/dev/null 2>&1; then + lt_cv_deplibs_check_method='file_magic ^x86 archive import|^x86 DLL' + lt_cv_file_magic_cmd='func_win32_libid' + else + # Keep this pattern in sync with the one in func_win32_libid. + lt_cv_deplibs_check_method='file_magic file format (pei*-i386(.*architecture: i386)?|pe-arm-wince|pe-x86-64)' + lt_cv_file_magic_cmd='$OBJDUMP -f' + fi + ;; + +cegcc*) + # use the weaker test based on 'objdump'. See mingw*. + lt_cv_deplibs_check_method='file_magic file format pe-arm-.*little(.*architecture: arm)?' + lt_cv_file_magic_cmd='$OBJDUMP -f' + ;; + +darwin* | rhapsody*) + lt_cv_deplibs_check_method=pass_all + ;; + +freebsd* | dragonfly* | midnightbsd*) + if echo __ELF__ | $CC -E - | $GREP __ELF__ > /dev/null; then + case $host_cpu in + i*86 ) + # Not sure whether the presence of OpenBSD here was a mistake. + # Let's accept both of them until this is cleared up. + lt_cv_deplibs_check_method='file_magic (FreeBSD|OpenBSD|DragonFly)/i[3-9]86 (compact )?demand paged shared library' + lt_cv_file_magic_cmd=$FILECMD + lt_cv_file_magic_test_file=`echo /usr/lib/libc.so.*` + ;; + esac + else + lt_cv_deplibs_check_method=pass_all + fi + ;; + +haiku*) + lt_cv_deplibs_check_method=pass_all + ;; + +hpux10.20* | hpux11*) + lt_cv_file_magic_cmd=$FILECMD + case $host_cpu in + ia64*) + lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|ELF-[0-9][0-9]) shared object file - IA64' + lt_cv_file_magic_test_file=/usr/lib/hpux32/libc.so + ;; + hppa*64*) + lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|ELF[ -][0-9][0-9])(-bit)?( [LM]SB)? shared object( file)?[, -]* PA-RISC [0-9]\.[0-9]' + lt_cv_file_magic_test_file=/usr/lib/pa20_64/libc.sl + ;; + *) + lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|PA-RISC[0-9]\.[0-9]) shared library' + lt_cv_file_magic_test_file=/usr/lib/libc.sl + ;; + esac + ;; + +interix[3-9]*) + # PIC code is broken on Interix 3.x, that's why |\.a not |_pic\.a here + lt_cv_deplibs_check_method='match_pattern /lib[^/]+(\.so|\.a)$' + ;; + +irix5* | irix6* | nonstopux*) + case $LD in + *-32|*"-32 ") libmagic=32-bit;; + *-n32|*"-n32 ") libmagic=N32;; + *-64|*"-64 ") libmagic=64-bit;; + *) libmagic=never-match;; + esac + lt_cv_deplibs_check_method=pass_all + ;; + +# This must be glibc/ELF. +linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) + lt_cv_deplibs_check_method=pass_all + ;; + +netbsd*) + if echo __ELF__ | $CC -E - | $GREP __ELF__ > /dev/null; then + lt_cv_deplibs_check_method='match_pattern /lib[^/]+(\.so\.[0-9]+\.[0-9]+|_pic\.a)$' + else + lt_cv_deplibs_check_method='match_pattern /lib[^/]+(\.so|_pic\.a)$' + fi + ;; + +newos6*) + lt_cv_deplibs_check_method='file_magic ELF [0-9][0-9]*-bit [ML]SB (executable|dynamic lib)' + lt_cv_file_magic_cmd=$FILECMD + lt_cv_file_magic_test_file=/usr/lib/libnls.so + ;; + +*nto* | *qnx*) + lt_cv_deplibs_check_method=pass_all + ;; + +openbsd* | bitrig*) + if test -z "`echo __ELF__ | $CC -E - | $GREP __ELF__`"; then + lt_cv_deplibs_check_method='match_pattern /lib[^/]+(\.so\.[0-9]+\.[0-9]+|\.so|_pic\.a)$' + else + lt_cv_deplibs_check_method='match_pattern /lib[^/]+(\.so\.[0-9]+\.[0-9]+|_pic\.a)$' + fi + ;; + +osf3* | osf4* | osf5*) + lt_cv_deplibs_check_method=pass_all + ;; + +rdos*) + lt_cv_deplibs_check_method=pass_all + ;; + +solaris*) + lt_cv_deplibs_check_method=pass_all + ;; + +sysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX* | sysv4*uw2*) + lt_cv_deplibs_check_method=pass_all + ;; + +sysv4 | sysv4.3*) + case $host_vendor in + motorola) + lt_cv_deplibs_check_method='file_magic ELF [0-9][0-9]*-bit [ML]SB (shared object|dynamic lib) M[0-9][0-9]* Version [0-9]' + lt_cv_file_magic_test_file=`echo /usr/lib/libc.so*` + ;; + ncr) + lt_cv_deplibs_check_method=pass_all + ;; + sequent) + lt_cv_file_magic_cmd='/bin/file' + lt_cv_deplibs_check_method='file_magic ELF [0-9][0-9]*-bit [LM]SB (shared object|dynamic lib )' + ;; + sni) + lt_cv_file_magic_cmd='/bin/file' + lt_cv_deplibs_check_method="file_magic ELF [0-9][0-9]*-bit [LM]SB dynamic lib" + lt_cv_file_magic_test_file=/lib/libc.so + ;; + siemens) + lt_cv_deplibs_check_method=pass_all + ;; + pc) + lt_cv_deplibs_check_method=pass_all + ;; + esac + ;; + +tpf*) + lt_cv_deplibs_check_method=pass_all + ;; +os2*) + lt_cv_deplibs_check_method=pass_all + ;; +esac + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_deplibs_check_method" >&5 +printf "%s\n" "$lt_cv_deplibs_check_method" >&6; } + +file_magic_glob= +want_nocaseglob=no +if test "$build" = "$host"; then + case $host_os in + mingw* | pw32*) + if ( shopt | grep nocaseglob ) >/dev/null 2>&1; then + want_nocaseglob=yes + else + file_magic_glob=`echo aAbBcCdDeEfFgGhHiIjJkKlLmMnNoOpPqQrRsStTuUvVwWxXyYzZ | $SED -e "s/\(..\)/s\/[\1]\/[\1]\/g;/g"` + fi + ;; + esac +fi + +file_magic_cmd=$lt_cv_file_magic_cmd +deplibs_check_method=$lt_cv_deplibs_check_method +test -z "$deplibs_check_method" && deplibs_check_method=unknown + + + + + + + + + + + + + + + + + + + + + + +if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}dlltool", so it can be a program name with args. +set dummy ${ac_tool_prefix}dlltool; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_DLLTOOL+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$DLLTOOL"; then + ac_cv_prog_DLLTOOL="$DLLTOOL" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_DLLTOOL="${ac_tool_prefix}dlltool" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +DLLTOOL=$ac_cv_prog_DLLTOOL +if test -n "$DLLTOOL"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $DLLTOOL" >&5 +printf "%s\n" "$DLLTOOL" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_DLLTOOL"; then + ac_ct_DLLTOOL=$DLLTOOL + # Extract the first word of "dlltool", so it can be a program name with args. +set dummy dlltool; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_DLLTOOL+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_DLLTOOL"; then + ac_cv_prog_ac_ct_DLLTOOL="$ac_ct_DLLTOOL" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_DLLTOOL="dlltool" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_DLLTOOL=$ac_cv_prog_ac_ct_DLLTOOL +if test -n "$ac_ct_DLLTOOL"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_DLLTOOL" >&5 +printf "%s\n" "$ac_ct_DLLTOOL" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_ct_DLLTOOL" = x; then + DLLTOOL="false" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + DLLTOOL=$ac_ct_DLLTOOL + fi +else + DLLTOOL="$ac_cv_prog_DLLTOOL" +fi + +test -z "$DLLTOOL" && DLLTOOL=dlltool + + + + + + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking how to associate runtime and link libraries" >&5 +printf %s "checking how to associate runtime and link libraries... " >&6; } +if test ${lt_cv_sharedlib_from_linklib_cmd+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_sharedlib_from_linklib_cmd='unknown' + +case $host_os in +cygwin* | mingw* | pw32* | cegcc*) + # two different shell functions defined in ltmain.sh; + # decide which one to use based on capabilities of $DLLTOOL + case `$DLLTOOL --help 2>&1` in + *--identify-strict*) + lt_cv_sharedlib_from_linklib_cmd=func_cygming_dll_for_implib + ;; + *) + lt_cv_sharedlib_from_linklib_cmd=func_cygming_dll_for_implib_fallback + ;; + esac + ;; +*) + # fallback: assume linklib IS sharedlib + lt_cv_sharedlib_from_linklib_cmd=$ECHO + ;; +esac + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_sharedlib_from_linklib_cmd" >&5 +printf "%s\n" "$lt_cv_sharedlib_from_linklib_cmd" >&6; } +sharedlib_from_linklib_cmd=$lt_cv_sharedlib_from_linklib_cmd +test -z "$sharedlib_from_linklib_cmd" && sharedlib_from_linklib_cmd=$ECHO + + + + + + + + +if test -n "$ac_tool_prefix"; then + for ac_prog in ar + do + # Extract the first word of "$ac_tool_prefix$ac_prog", so it can be a program name with args. +set dummy $ac_tool_prefix$ac_prog; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_AR+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$AR"; then + ac_cv_prog_AR="$AR" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_AR="$ac_tool_prefix$ac_prog" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +AR=$ac_cv_prog_AR +if test -n "$AR"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $AR" >&5 +printf "%s\n" "$AR" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + test -n "$AR" && break + done +fi +if test -z "$AR"; then + ac_ct_AR=$AR + for ac_prog in ar +do + # Extract the first word of "$ac_prog", so it can be a program name with args. +set dummy $ac_prog; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_AR+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_AR"; then + ac_cv_prog_ac_ct_AR="$ac_ct_AR" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_AR="$ac_prog" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_AR=$ac_cv_prog_ac_ct_AR +if test -n "$ac_ct_AR"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_AR" >&5 +printf "%s\n" "$ac_ct_AR" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + test -n "$ac_ct_AR" && break +done + + if test "x$ac_ct_AR" = x; then + AR="false" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + AR=$ac_ct_AR + fi +fi + +: ${AR=ar} + + + + + + +# Use ARFLAGS variable as AR's operation code to sync the variable naming with +# Automake. If both AR_FLAGS and ARFLAGS are specified, AR_FLAGS should have +# higher priority because thats what people were doing historically (setting +# ARFLAGS for automake and AR_FLAGS for libtool). FIXME: Make the AR_FLAGS +# variable obsoleted/removed. + +test ${AR_FLAGS+y} || AR_FLAGS=${ARFLAGS-cr} +lt_ar_flags=$AR_FLAGS + + + + + + +# Make AR_FLAGS overridable by 'make ARFLAGS='. Don't try to run-time override +# by AR_FLAGS because that was never working and AR_FLAGS is about to die. + + + + + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for archiver @FILE support" >&5 +printf %s "checking for archiver @FILE support... " >&6; } +if test ${lt_cv_ar_at_file+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_ar_at_file=no + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +int +main (void) +{ + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + echo conftest.$ac_objext > conftest.lst + lt_ar_try='$AR $AR_FLAGS libconftest.a @conftest.lst >&5' + { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$lt_ar_try\""; } >&5 + (eval $lt_ar_try) 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } + if test 0 -eq "$ac_status"; then + # Ensure the archiver fails upon bogus file names. + rm -f conftest.$ac_objext libconftest.a + { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$lt_ar_try\""; } >&5 + (eval $lt_ar_try) 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } + if test 0 -ne "$ac_status"; then + lt_cv_ar_at_file=@ + fi + fi + rm -f conftest.* libconftest.a + +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_ar_at_file" >&5 +printf "%s\n" "$lt_cv_ar_at_file" >&6; } + +if test no = "$lt_cv_ar_at_file"; then + archiver_list_spec= +else + archiver_list_spec=$lt_cv_ar_at_file +fi + + + + + + + +if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}strip", so it can be a program name with args. +set dummy ${ac_tool_prefix}strip; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_STRIP+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$STRIP"; then + ac_cv_prog_STRIP="$STRIP" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_STRIP="${ac_tool_prefix}strip" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +STRIP=$ac_cv_prog_STRIP +if test -n "$STRIP"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $STRIP" >&5 +printf "%s\n" "$STRIP" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_STRIP"; then + ac_ct_STRIP=$STRIP + # Extract the first word of "strip", so it can be a program name with args. +set dummy strip; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_STRIP+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_STRIP"; then + ac_cv_prog_ac_ct_STRIP="$ac_ct_STRIP" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_STRIP="strip" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_STRIP=$ac_cv_prog_ac_ct_STRIP +if test -n "$ac_ct_STRIP"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_STRIP" >&5 +printf "%s\n" "$ac_ct_STRIP" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_ct_STRIP" = x; then + STRIP=":" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + STRIP=$ac_ct_STRIP + fi +else + STRIP="$ac_cv_prog_STRIP" +fi + +test -z "$STRIP" && STRIP=: + + + + + + +if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}ranlib", so it can be a program name with args. +set dummy ${ac_tool_prefix}ranlib; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_RANLIB+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$RANLIB"; then + ac_cv_prog_RANLIB="$RANLIB" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_RANLIB="${ac_tool_prefix}ranlib" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +RANLIB=$ac_cv_prog_RANLIB +if test -n "$RANLIB"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $RANLIB" >&5 +printf "%s\n" "$RANLIB" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_RANLIB"; then + ac_ct_RANLIB=$RANLIB + # Extract the first word of "ranlib", so it can be a program name with args. +set dummy ranlib; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_RANLIB+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_RANLIB"; then + ac_cv_prog_ac_ct_RANLIB="$ac_ct_RANLIB" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_RANLIB="ranlib" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_RANLIB=$ac_cv_prog_ac_ct_RANLIB +if test -n "$ac_ct_RANLIB"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_RANLIB" >&5 +printf "%s\n" "$ac_ct_RANLIB" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_ct_RANLIB" = x; then + RANLIB=":" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + RANLIB=$ac_ct_RANLIB + fi +else + RANLIB="$ac_cv_prog_RANLIB" +fi + +test -z "$RANLIB" && RANLIB=: + + + + + + +# Determine commands to create old-style static archives. +old_archive_cmds='$AR $AR_FLAGS $oldlib$oldobjs' +old_postinstall_cmds='chmod 644 $oldlib' +old_postuninstall_cmds= + +if test -n "$RANLIB"; then + case $host_os in + bitrig* | openbsd*) + old_postinstall_cmds="$old_postinstall_cmds~\$RANLIB -t \$tool_oldlib" + ;; + *) + old_postinstall_cmds="$old_postinstall_cmds~\$RANLIB \$tool_oldlib" + ;; + esac + old_archive_cmds="$old_archive_cmds~\$RANLIB \$tool_oldlib" +fi + +case $host_os in + darwin*) + lock_old_archive_extraction=yes ;; + *) + lock_old_archive_extraction=no ;; +esac + + + + + + + + + + + + + + + + + + + + + +for ac_prog in gawk mawk nawk awk +do + # Extract the first word of "$ac_prog", so it can be a program name with args. +set dummy $ac_prog; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_AWK+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$AWK"; then + ac_cv_prog_AWK="$AWK" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_AWK="$ac_prog" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +AWK=$ac_cv_prog_AWK +if test -n "$AWK"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $AWK" >&5 +printf "%s\n" "$AWK" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + test -n "$AWK" && break +done + + + + + + + + + + + + + + + + + + + +# If no C compiler was specified, use CC. +LTCC=${LTCC-"$CC"} + +# If no C compiler flags were specified, use CFLAGS. +LTCFLAGS=${LTCFLAGS-"$CFLAGS"} + +# Allow CC to be a program name with arguments. +compiler=$CC + + +# Check for command to grab the raw symbol name followed by C symbol from nm. +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking command to parse $NM output from $compiler object" >&5 +printf %s "checking command to parse $NM output from $compiler object... " >&6; } +if test ${lt_cv_sys_global_symbol_pipe+y} +then : + printf %s "(cached) " >&6 +else $as_nop + +# These are sane defaults that work on at least a few old systems. +# [They come from Ultrix. What could be older than Ultrix?!! ;)] + +# Character class describing NM global symbol codes. +symcode='[BCDEGRST]' + +# Regexp to match symbols that can be accessed directly from C. +sympat='\([_A-Za-z][_A-Za-z0-9]*\)' + +# Define system-specific variables. +case $host_os in +aix*) + symcode='[BCDT]' + ;; +cygwin* | mingw* | pw32* | cegcc*) + symcode='[ABCDGISTW]' + ;; +hpux*) + if test ia64 = "$host_cpu"; then + symcode='[ABCDEGRST]' + fi + ;; +irix* | nonstopux*) + symcode='[BCDEGRST]' + ;; +osf*) + symcode='[BCDEGQRST]' + ;; +solaris*) + symcode='[BDRT]' + ;; +sco3.2v5*) + symcode='[DT]' + ;; +sysv4.2uw2*) + symcode='[DT]' + ;; +sysv5* | sco5v6* | unixware* | OpenUNIX*) + symcode='[ABDT]' + ;; +sysv4) + symcode='[DFNSTU]' + ;; +esac + +# If we're using GNU nm, then use its standard symbol codes. +case `$NM -V 2>&1` in +*GNU* | *'with BFD'*) + symcode='[ABCDGIRSTW]' ;; +esac + +if test "$lt_cv_nm_interface" = "MS dumpbin"; then + # Gets list of data symbols to import. + lt_cv_sys_global_symbol_to_import="$SED -n -e 's/^I .* \(.*\)$/\1/p'" + # Adjust the below global symbol transforms to fixup imported variables. + lt_cdecl_hook=" -e 's/^I .* \(.*\)$/extern __declspec(dllimport) char \1;/p'" + lt_c_name_hook=" -e 's/^I .* \(.*\)$/ {\"\1\", (void *) 0},/p'" + lt_c_name_lib_hook="\ + -e 's/^I .* \(lib.*\)$/ {\"\1\", (void *) 0},/p'\ + -e 's/^I .* \(.*\)$/ {\"lib\1\", (void *) 0},/p'" +else + # Disable hooks by default. + lt_cv_sys_global_symbol_to_import= + lt_cdecl_hook= + lt_c_name_hook= + lt_c_name_lib_hook= +fi + +# Transform an extracted symbol line into a proper C declaration. +# Some systems (esp. on ia64) link data and code symbols differently, +# so use this general approach. +lt_cv_sys_global_symbol_to_cdecl="$SED -n"\ +$lt_cdecl_hook\ +" -e 's/^T .* \(.*\)$/extern int \1();/p'"\ +" -e 's/^$symcode$symcode* .* \(.*\)$/extern char \1;/p'" + +# Transform an extracted symbol line into symbol name and symbol address +lt_cv_sys_global_symbol_to_c_name_address="$SED -n"\ +$lt_c_name_hook\ +" -e 's/^: \(.*\) .*$/ {\"\1\", (void *) 0},/p'"\ +" -e 's/^$symcode$symcode* .* \(.*\)$/ {\"\1\", (void *) \&\1},/p'" + +# Transform an extracted symbol line into symbol name with lib prefix and +# symbol address. +lt_cv_sys_global_symbol_to_c_name_address_lib_prefix="$SED -n"\ +$lt_c_name_lib_hook\ +" -e 's/^: \(.*\) .*$/ {\"\1\", (void *) 0},/p'"\ +" -e 's/^$symcode$symcode* .* \(lib.*\)$/ {\"\1\", (void *) \&\1},/p'"\ +" -e 's/^$symcode$symcode* .* \(.*\)$/ {\"lib\1\", (void *) \&\1},/p'" + +# Handle CRLF in mingw tool chain +opt_cr= +case $build_os in +mingw*) + opt_cr=`$ECHO 'x\{0,1\}' | tr x '\015'` # option cr in regexp + ;; +esac + +# Try without a prefix underscore, then with it. +for ac_symprfx in "" "_"; do + + # Transform symcode, sympat, and symprfx into a raw symbol and a C symbol. + symxfrm="\\1 $ac_symprfx\\2 \\2" + + # Write the raw and C identifiers. + if test "$lt_cv_nm_interface" = "MS dumpbin"; then + # Fake it for dumpbin and say T for any non-static function, + # D for any global variable and I for any imported variable. + # Also find C++ and __fastcall symbols from MSVC++ or ICC, + # which start with @ or ?. + lt_cv_sys_global_symbol_pipe="$AWK '"\ +" {last_section=section; section=\$ 3};"\ +" /^COFF SYMBOL TABLE/{for(i in hide) delete hide[i]};"\ +" /Section length .*#relocs.*(pick any)/{hide[last_section]=1};"\ +" /^ *Symbol name *: /{split(\$ 0,sn,\":\"); si=substr(sn[2],2)};"\ +" /^ *Type *: code/{print \"T\",si,substr(si,length(prfx))};"\ +" /^ *Type *: data/{print \"I\",si,substr(si,length(prfx))};"\ +" \$ 0!~/External *\|/{next};"\ +" / 0+ UNDEF /{next}; / UNDEF \([^|]\)*()/{next};"\ +" {if(hide[section]) next};"\ +" {f=\"D\"}; \$ 0~/\(\).*\|/{f=\"T\"};"\ +" {split(\$ 0,a,/\||\r/); split(a[2],s)};"\ +" s[1]~/^[@?]/{print f,s[1],s[1]; next};"\ +" s[1]~prfx {split(s[1],t,\"@\"); print f,t[1],substr(t[1],length(prfx))}"\ +" ' prfx=^$ac_symprfx" + else + lt_cv_sys_global_symbol_pipe="$SED -n -e 's/^.*[ ]\($symcode$symcode*\)[ ][ ]*$ac_symprfx$sympat$opt_cr$/$symxfrm/p'" + fi + lt_cv_sys_global_symbol_pipe="$lt_cv_sys_global_symbol_pipe | $SED '/ __gnu_lto/d'" + + # Check to see that the pipe works correctly. + pipe_works=no + + rm -f conftest* + cat > conftest.$ac_ext <<_LT_EOF +#ifdef __cplusplus +extern "C" { +#endif +char nm_test_var; +void nm_test_func(void); +void nm_test_func(void){} +#ifdef __cplusplus +} +#endif +int main(){nm_test_var='a';nm_test_func();return(0);} +_LT_EOF + + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 + (eval $ac_compile) 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + # Now try to grab the symbols. + nlist=conftest.nm + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$NM conftest.$ac_objext \| "$lt_cv_sys_global_symbol_pipe" \> $nlist\""; } >&5 + (eval $NM conftest.$ac_objext \| "$lt_cv_sys_global_symbol_pipe" \> $nlist) 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } && test -s "$nlist"; then + # Try sorting and uniquifying the output. + if sort "$nlist" | uniq > "$nlist"T; then + mv -f "$nlist"T "$nlist" + else + rm -f "$nlist"T + fi + + # Make sure that we snagged all the symbols we need. + if $GREP ' nm_test_var$' "$nlist" >/dev/null; then + if $GREP ' nm_test_func$' "$nlist" >/dev/null; then + cat <<_LT_EOF > conftest.$ac_ext +/* Keep this code in sync between libtool.m4, ltmain, lt_system.h, and tests. */ +#if defined _WIN32 || defined __CYGWIN__ || defined _WIN32_WCE +/* DATA imports from DLLs on WIN32 can't be const, because runtime + relocations are performed -- see ld's documentation on pseudo-relocs. */ +# define LT_DLSYM_CONST +#elif defined __osf__ +/* This system does not cope well with relocations in const data. */ +# define LT_DLSYM_CONST +#else +# define LT_DLSYM_CONST const +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +_LT_EOF + # Now generate the symbol file. + eval "$lt_cv_sys_global_symbol_to_cdecl"' < "$nlist" | $GREP -v main >> conftest.$ac_ext' + + cat <<_LT_EOF >> conftest.$ac_ext + +/* The mapping between symbol names and symbols. */ +LT_DLSYM_CONST struct { + const char *name; + void *address; +} +lt__PROGRAM__LTX_preloaded_symbols[] = +{ + { "@PROGRAM@", (void *) 0 }, +_LT_EOF + $SED "s/^$symcode$symcode* .* \(.*\)$/ {\"\1\", (void *) \&\1},/" < "$nlist" | $GREP -v main >> conftest.$ac_ext + cat <<\_LT_EOF >> conftest.$ac_ext + {0, (void *) 0} +}; + +/* This works around a problem in FreeBSD linker */ +#ifdef FREEBSD_WORKAROUND +static const void *lt_preloaded_setup() { + return lt__PROGRAM__LTX_preloaded_symbols; +} +#endif + +#ifdef __cplusplus +} +#endif +_LT_EOF + # Now try linking the two files. + mv conftest.$ac_objext conftstm.$ac_objext + lt_globsym_save_LIBS=$LIBS + lt_globsym_save_CFLAGS=$CFLAGS + LIBS=conftstm.$ac_objext + CFLAGS="$CFLAGS$lt_prog_compiler_no_builtin_flag" + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_link\""; } >&5 + (eval $ac_link) 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } && test -s conftest$ac_exeext; then + pipe_works=yes + fi + LIBS=$lt_globsym_save_LIBS + CFLAGS=$lt_globsym_save_CFLAGS + else + echo "cannot find nm_test_func in $nlist" >&5 + fi + else + echo "cannot find nm_test_var in $nlist" >&5 + fi + else + echo "cannot run $lt_cv_sys_global_symbol_pipe" >&5 + fi + else + echo "$progname: failed program was:" >&5 + cat conftest.$ac_ext >&5 + fi + rm -rf conftest* conftst* + + # Do not use the global_symbol_pipe unless it works. + if test yes = "$pipe_works"; then + break + else + lt_cv_sys_global_symbol_pipe= + fi +done + +fi + +if test -z "$lt_cv_sys_global_symbol_pipe"; then + lt_cv_sys_global_symbol_to_cdecl= +fi +if test -z "$lt_cv_sys_global_symbol_pipe$lt_cv_sys_global_symbol_to_cdecl"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: failed" >&5 +printf "%s\n" "failed" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: ok" >&5 +printf "%s\n" "ok" >&6; } +fi + +# Response file support. +if test "$lt_cv_nm_interface" = "MS dumpbin"; then + nm_file_list_spec='@' +elif $NM --help 2>/dev/null | grep '[@]FILE' >/dev/null; then + nm_file_list_spec='@' +fi + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for sysroot" >&5 +printf %s "checking for sysroot... " >&6; } + +# Check whether --with-sysroot was given. +if test ${with_sysroot+y} +then : + withval=$with_sysroot; +else $as_nop + with_sysroot=no +fi + + +lt_sysroot= +case $with_sysroot in #( + yes) + if test yes = "$GCC"; then + lt_sysroot=`$CC --print-sysroot 2>/dev/null` + fi + ;; #( + /*) + lt_sysroot=`echo "$with_sysroot" | $SED -e "$sed_quote_subst"` + ;; #( + no|'') + ;; #( + *) + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $with_sysroot" >&5 +printf "%s\n" "$with_sysroot" >&6; } + as_fn_error $? "The sysroot must be an absolute path." "$LINENO" 5 + ;; +esac + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: ${lt_sysroot:-no}" >&5 +printf "%s\n" "${lt_sysroot:-no}" >&6; } + + + + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for a working dd" >&5 +printf %s "checking for a working dd... " >&6; } +if test ${ac_cv_path_lt_DD+y} +then : + printf %s "(cached) " >&6 +else $as_nop + printf 0123456789abcdef0123456789abcdef >conftest.i +cat conftest.i conftest.i >conftest2.i +: ${lt_DD:=$DD} +if test -z "$lt_DD"; then + ac_path_lt_DD_found=false + # Loop through the user's path and test for each of PROGNAME-LIST + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_prog in dd + do + for ac_exec_ext in '' $ac_executable_extensions; do + ac_path_lt_DD="$as_dir$ac_prog$ac_exec_ext" + as_fn_executable_p "$ac_path_lt_DD" || continue +if "$ac_path_lt_DD" bs=32 count=1 conftest.out 2>/dev/null; then + cmp -s conftest.i conftest.out \ + && ac_cv_path_lt_DD="$ac_path_lt_DD" ac_path_lt_DD_found=: +fi + $ac_path_lt_DD_found && break 3 + done + done + done +IFS=$as_save_IFS + if test -z "$ac_cv_path_lt_DD"; then + : + fi +else + ac_cv_path_lt_DD=$lt_DD +fi + +rm -f conftest.i conftest2.i conftest.out +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_lt_DD" >&5 +printf "%s\n" "$ac_cv_path_lt_DD" >&6; } + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking how to truncate binary pipes" >&5 +printf %s "checking how to truncate binary pipes... " >&6; } +if test ${lt_cv_truncate_bin+y} +then : + printf %s "(cached) " >&6 +else $as_nop + printf 0123456789abcdef0123456789abcdef >conftest.i +cat conftest.i conftest.i >conftest2.i +lt_cv_truncate_bin= +if "$ac_cv_path_lt_DD" bs=32 count=1 conftest.out 2>/dev/null; then + cmp -s conftest.i conftest.out \ + && lt_cv_truncate_bin="$ac_cv_path_lt_DD bs=4096 count=1" +fi +rm -f conftest.i conftest2.i conftest.out +test -z "$lt_cv_truncate_bin" && lt_cv_truncate_bin="$SED -e 4q" +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_truncate_bin" >&5 +printf "%s\n" "$lt_cv_truncate_bin" >&6; } + + + + + + + +# Calculate cc_basename. Skip known compiler wrappers and cross-prefix. +func_cc_basename () +{ + for cc_temp in $*""; do + case $cc_temp in + compile | *[\\/]compile | ccache | *[\\/]ccache ) ;; + distcc | *[\\/]distcc | purify | *[\\/]purify ) ;; + \-*) ;; + *) break;; + esac + done + func_cc_basename_result=`$ECHO "$cc_temp" | $SED "s%.*/%%; s%^$host_alias-%%"` +} + +# Check whether --enable-libtool-lock was given. +if test ${enable_libtool_lock+y} +then : + enableval=$enable_libtool_lock; +fi + +test no = "$enable_libtool_lock" || enable_libtool_lock=yes + +# Some flags need to be propagated to the compiler or linker for good +# libtool support. +case $host in +ia64-*-hpux*) + # Find out what ABI is being produced by ac_compile, and set mode + # options accordingly. + echo 'int i;' > conftest.$ac_ext + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 + (eval $ac_compile) 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + case `$FILECMD conftest.$ac_objext` in + *ELF-32*) + HPUX_IA64_MODE=32 + ;; + *ELF-64*) + HPUX_IA64_MODE=64 + ;; + esac + fi + rm -rf conftest* + ;; +*-*-irix6*) + # Find out what ABI is being produced by ac_compile, and set linker + # options accordingly. + echo '#line '$LINENO' "configure"' > conftest.$ac_ext + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 + (eval $ac_compile) 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + if test yes = "$lt_cv_prog_gnu_ld"; then + case `$FILECMD conftest.$ac_objext` in + *32-bit*) + LD="${LD-ld} -melf32bsmip" + ;; + *N32*) + LD="${LD-ld} -melf32bmipn32" + ;; + *64-bit*) + LD="${LD-ld} -melf64bmip" + ;; + esac + else + case `$FILECMD conftest.$ac_objext` in + *32-bit*) + LD="${LD-ld} -32" + ;; + *N32*) + LD="${LD-ld} -n32" + ;; + *64-bit*) + LD="${LD-ld} -64" + ;; + esac + fi + fi + rm -rf conftest* + ;; + +mips64*-*linux*) + # Find out what ABI is being produced by ac_compile, and set linker + # options accordingly. + echo '#line '$LINENO' "configure"' > conftest.$ac_ext + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 + (eval $ac_compile) 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + emul=elf + case `$FILECMD conftest.$ac_objext` in + *32-bit*) + emul="${emul}32" + ;; + *64-bit*) + emul="${emul}64" + ;; + esac + case `$FILECMD conftest.$ac_objext` in + *MSB*) + emul="${emul}btsmip" + ;; + *LSB*) + emul="${emul}ltsmip" + ;; + esac + case `$FILECMD conftest.$ac_objext` in + *N32*) + emul="${emul}n32" + ;; + esac + LD="${LD-ld} -m $emul" + fi + rm -rf conftest* + ;; + +x86_64-*kfreebsd*-gnu|x86_64-*linux*|powerpc*-*linux*| \ +s390*-*linux*|s390*-*tpf*|sparc*-*linux*) + # Find out what ABI is being produced by ac_compile, and set linker + # options accordingly. Note that the listed cases only cover the + # situations where additional linker options are needed (such as when + # doing 32-bit compilation for a host where ld defaults to 64-bit, or + # vice versa); the common cases where no linker options are needed do + # not appear in the list. + echo 'int i;' > conftest.$ac_ext + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 + (eval $ac_compile) 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + case `$FILECMD conftest.o` in + *32-bit*) + case $host in + x86_64-*kfreebsd*-gnu) + LD="${LD-ld} -m elf_i386_fbsd" + ;; + x86_64-*linux*) + case `$FILECMD conftest.o` in + *x86-64*) + LD="${LD-ld} -m elf32_x86_64" + ;; + *) + LD="${LD-ld} -m elf_i386" + ;; + esac + ;; + powerpc64le-*linux*) + LD="${LD-ld} -m elf32lppclinux" + ;; + powerpc64-*linux*) + LD="${LD-ld} -m elf32ppclinux" + ;; + s390x-*linux*) + LD="${LD-ld} -m elf_s390" + ;; + sparc64-*linux*) + LD="${LD-ld} -m elf32_sparc" + ;; + esac + ;; + *64-bit*) + case $host in + x86_64-*kfreebsd*-gnu) + LD="${LD-ld} -m elf_x86_64_fbsd" + ;; + x86_64-*linux*) + LD="${LD-ld} -m elf_x86_64" + ;; + powerpcle-*linux*) + LD="${LD-ld} -m elf64lppc" + ;; + powerpc-*linux*) + LD="${LD-ld} -m elf64ppc" + ;; + s390*-*linux*|s390*-*tpf*) + LD="${LD-ld} -m elf64_s390" + ;; + sparc*-*linux*) + LD="${LD-ld} -m elf64_sparc" + ;; + esac + ;; + esac + fi + rm -rf conftest* + ;; + +*-*-sco3.2v5*) + # On SCO OpenServer 5, we need -belf to get full-featured binaries. + SAVE_CFLAGS=$CFLAGS + CFLAGS="$CFLAGS -belf" + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether the C compiler needs -belf" >&5 +printf %s "checking whether the C compiler needs -belf... " >&6; } +if test ${lt_cv_cc_needs_belf+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu + + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +int +main (void) +{ + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + lt_cv_cc_needs_belf=yes +else $as_nop + lt_cv_cc_needs_belf=no +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext + ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_cc_needs_belf" >&5 +printf "%s\n" "$lt_cv_cc_needs_belf" >&6; } + if test yes != "$lt_cv_cc_needs_belf"; then + # this is probably gcc 2.8.0, egcs 1.0 or newer; no need for -belf + CFLAGS=$SAVE_CFLAGS + fi + ;; +*-*solaris*) + # Find out what ABI is being produced by ac_compile, and set linker + # options accordingly. + echo 'int i;' > conftest.$ac_ext + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 + (eval $ac_compile) 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + case `$FILECMD conftest.o` in + *64-bit*) + case $lt_cv_prog_gnu_ld in + yes*) + case $host in + i?86-*-solaris*|x86_64-*-solaris*) + LD="${LD-ld} -m elf_x86_64" + ;; + sparc*-*-solaris*) + LD="${LD-ld} -m elf64_sparc" + ;; + esac + # GNU ld 2.21 introduced _sol2 emulations. Use them if available. + if ${LD-ld} -V | grep _sol2 >/dev/null 2>&1; then + LD=${LD-ld}_sol2 + fi + ;; + *) + if ${LD-ld} -64 -r -o conftest2.o conftest.o >/dev/null 2>&1; then + LD="${LD-ld} -64" + fi + ;; + esac + ;; + esac + fi + rm -rf conftest* + ;; +esac + +need_locks=$enable_libtool_lock + +if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}mt", so it can be a program name with args. +set dummy ${ac_tool_prefix}mt; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_MANIFEST_TOOL+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$MANIFEST_TOOL"; then + ac_cv_prog_MANIFEST_TOOL="$MANIFEST_TOOL" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_MANIFEST_TOOL="${ac_tool_prefix}mt" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +MANIFEST_TOOL=$ac_cv_prog_MANIFEST_TOOL +if test -n "$MANIFEST_TOOL"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $MANIFEST_TOOL" >&5 +printf "%s\n" "$MANIFEST_TOOL" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_MANIFEST_TOOL"; then + ac_ct_MANIFEST_TOOL=$MANIFEST_TOOL + # Extract the first word of "mt", so it can be a program name with args. +set dummy mt; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_MANIFEST_TOOL+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_MANIFEST_TOOL"; then + ac_cv_prog_ac_ct_MANIFEST_TOOL="$ac_ct_MANIFEST_TOOL" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_MANIFEST_TOOL="mt" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_MANIFEST_TOOL=$ac_cv_prog_ac_ct_MANIFEST_TOOL +if test -n "$ac_ct_MANIFEST_TOOL"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_MANIFEST_TOOL" >&5 +printf "%s\n" "$ac_ct_MANIFEST_TOOL" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_ct_MANIFEST_TOOL" = x; then + MANIFEST_TOOL=":" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + MANIFEST_TOOL=$ac_ct_MANIFEST_TOOL + fi +else + MANIFEST_TOOL="$ac_cv_prog_MANIFEST_TOOL" +fi + +test -z "$MANIFEST_TOOL" && MANIFEST_TOOL=mt +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking if $MANIFEST_TOOL is a manifest tool" >&5 +printf %s "checking if $MANIFEST_TOOL is a manifest tool... " >&6; } +if test ${lt_cv_path_mainfest_tool+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_path_mainfest_tool=no + echo "$as_me:$LINENO: $MANIFEST_TOOL '-?'" >&5 + $MANIFEST_TOOL '-?' 2>conftest.err > conftest.out + cat conftest.err >&5 + if $GREP 'Manifest Tool' conftest.out > /dev/null; then + lt_cv_path_mainfest_tool=yes + fi + rm -f conftest* +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_path_mainfest_tool" >&5 +printf "%s\n" "$lt_cv_path_mainfest_tool" >&6; } +if test yes != "$lt_cv_path_mainfest_tool"; then + MANIFEST_TOOL=: +fi + + + + + + + case $host_os in + rhapsody* | darwin*) + if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}dsymutil", so it can be a program name with args. +set dummy ${ac_tool_prefix}dsymutil; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_DSYMUTIL+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$DSYMUTIL"; then + ac_cv_prog_DSYMUTIL="$DSYMUTIL" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_DSYMUTIL="${ac_tool_prefix}dsymutil" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +DSYMUTIL=$ac_cv_prog_DSYMUTIL +if test -n "$DSYMUTIL"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $DSYMUTIL" >&5 +printf "%s\n" "$DSYMUTIL" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_DSYMUTIL"; then + ac_ct_DSYMUTIL=$DSYMUTIL + # Extract the first word of "dsymutil", so it can be a program name with args. +set dummy dsymutil; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_DSYMUTIL+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_DSYMUTIL"; then + ac_cv_prog_ac_ct_DSYMUTIL="$ac_ct_DSYMUTIL" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_DSYMUTIL="dsymutil" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_DSYMUTIL=$ac_cv_prog_ac_ct_DSYMUTIL +if test -n "$ac_ct_DSYMUTIL"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_DSYMUTIL" >&5 +printf "%s\n" "$ac_ct_DSYMUTIL" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_ct_DSYMUTIL" = x; then + DSYMUTIL=":" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + DSYMUTIL=$ac_ct_DSYMUTIL + fi +else + DSYMUTIL="$ac_cv_prog_DSYMUTIL" +fi + + if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}nmedit", so it can be a program name with args. +set dummy ${ac_tool_prefix}nmedit; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_NMEDIT+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$NMEDIT"; then + ac_cv_prog_NMEDIT="$NMEDIT" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_NMEDIT="${ac_tool_prefix}nmedit" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +NMEDIT=$ac_cv_prog_NMEDIT +if test -n "$NMEDIT"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $NMEDIT" >&5 +printf "%s\n" "$NMEDIT" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_NMEDIT"; then + ac_ct_NMEDIT=$NMEDIT + # Extract the first word of "nmedit", so it can be a program name with args. +set dummy nmedit; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_NMEDIT+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_NMEDIT"; then + ac_cv_prog_ac_ct_NMEDIT="$ac_ct_NMEDIT" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_NMEDIT="nmedit" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_NMEDIT=$ac_cv_prog_ac_ct_NMEDIT +if test -n "$ac_ct_NMEDIT"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_NMEDIT" >&5 +printf "%s\n" "$ac_ct_NMEDIT" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_ct_NMEDIT" = x; then + NMEDIT=":" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + NMEDIT=$ac_ct_NMEDIT + fi +else + NMEDIT="$ac_cv_prog_NMEDIT" +fi + + if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}lipo", so it can be a program name with args. +set dummy ${ac_tool_prefix}lipo; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_LIPO+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$LIPO"; then + ac_cv_prog_LIPO="$LIPO" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_LIPO="${ac_tool_prefix}lipo" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +LIPO=$ac_cv_prog_LIPO +if test -n "$LIPO"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $LIPO" >&5 +printf "%s\n" "$LIPO" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_LIPO"; then + ac_ct_LIPO=$LIPO + # Extract the first word of "lipo", so it can be a program name with args. +set dummy lipo; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_LIPO+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_LIPO"; then + ac_cv_prog_ac_ct_LIPO="$ac_ct_LIPO" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_LIPO="lipo" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_LIPO=$ac_cv_prog_ac_ct_LIPO +if test -n "$ac_ct_LIPO"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_LIPO" >&5 +printf "%s\n" "$ac_ct_LIPO" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_ct_LIPO" = x; then + LIPO=":" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + LIPO=$ac_ct_LIPO + fi +else + LIPO="$ac_cv_prog_LIPO" +fi + + if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}otool", so it can be a program name with args. +set dummy ${ac_tool_prefix}otool; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_OTOOL+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$OTOOL"; then + ac_cv_prog_OTOOL="$OTOOL" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_OTOOL="${ac_tool_prefix}otool" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +OTOOL=$ac_cv_prog_OTOOL +if test -n "$OTOOL"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $OTOOL" >&5 +printf "%s\n" "$OTOOL" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_OTOOL"; then + ac_ct_OTOOL=$OTOOL + # Extract the first word of "otool", so it can be a program name with args. +set dummy otool; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_OTOOL+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_OTOOL"; then + ac_cv_prog_ac_ct_OTOOL="$ac_ct_OTOOL" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_OTOOL="otool" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_OTOOL=$ac_cv_prog_ac_ct_OTOOL +if test -n "$ac_ct_OTOOL"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_OTOOL" >&5 +printf "%s\n" "$ac_ct_OTOOL" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_ct_OTOOL" = x; then + OTOOL=":" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + OTOOL=$ac_ct_OTOOL + fi +else + OTOOL="$ac_cv_prog_OTOOL" +fi + + if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}otool64", so it can be a program name with args. +set dummy ${ac_tool_prefix}otool64; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_OTOOL64+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$OTOOL64"; then + ac_cv_prog_OTOOL64="$OTOOL64" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_OTOOL64="${ac_tool_prefix}otool64" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +OTOOL64=$ac_cv_prog_OTOOL64 +if test -n "$OTOOL64"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $OTOOL64" >&5 +printf "%s\n" "$OTOOL64" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_OTOOL64"; then + ac_ct_OTOOL64=$OTOOL64 + # Extract the first word of "otool64", so it can be a program name with args. +set dummy otool64; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_OTOOL64+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_OTOOL64"; then + ac_cv_prog_ac_ct_OTOOL64="$ac_ct_OTOOL64" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_OTOOL64="otool64" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_OTOOL64=$ac_cv_prog_ac_ct_OTOOL64 +if test -n "$ac_ct_OTOOL64"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_OTOOL64" >&5 +printf "%s\n" "$ac_ct_OTOOL64" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_ct_OTOOL64" = x; then + OTOOL64=":" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + OTOOL64=$ac_ct_OTOOL64 + fi +else + OTOOL64="$ac_cv_prog_OTOOL64" +fi + + + + + + + + + + + + + + + + + + + + + + + + + + + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for -single_module linker flag" >&5 +printf %s "checking for -single_module linker flag... " >&6; } +if test ${lt_cv_apple_cc_single_mod+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_apple_cc_single_mod=no + if test -z "$LT_MULTI_MODULE"; then + # By default we will add the -single_module flag. You can override + # by either setting the environment variable LT_MULTI_MODULE + # non-empty at configure time, or by adding -multi_module to the + # link flags. + rm -rf libconftest.dylib* + echo "int foo(void){return 1;}" > conftest.c + echo "$LTCC $LTCFLAGS $LDFLAGS -o libconftest.dylib \ +-dynamiclib -Wl,-single_module conftest.c" >&5 + $LTCC $LTCFLAGS $LDFLAGS -o libconftest.dylib \ + -dynamiclib -Wl,-single_module conftest.c 2>conftest.err + _lt_result=$? + # If there is a non-empty error log, and "single_module" + # appears in it, assume the flag caused a linker warning + if test -s conftest.err && $GREP single_module conftest.err; then + cat conftest.err >&5 + # Otherwise, if the output was created with a 0 exit code from + # the compiler, it worked. + elif test -f libconftest.dylib && test 0 = "$_lt_result"; then + lt_cv_apple_cc_single_mod=yes + else + cat conftest.err >&5 + fi + rm -rf libconftest.dylib* + rm -f conftest.* + fi +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_apple_cc_single_mod" >&5 +printf "%s\n" "$lt_cv_apple_cc_single_mod" >&6; } + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for -exported_symbols_list linker flag" >&5 +printf %s "checking for -exported_symbols_list linker flag... " >&6; } +if test ${lt_cv_ld_exported_symbols_list+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_ld_exported_symbols_list=no + save_LDFLAGS=$LDFLAGS + echo "_main" > conftest.sym + LDFLAGS="$LDFLAGS -Wl,-exported_symbols_list,conftest.sym" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +int +main (void) +{ + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + lt_cv_ld_exported_symbols_list=yes +else $as_nop + lt_cv_ld_exported_symbols_list=no +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext + LDFLAGS=$save_LDFLAGS + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_ld_exported_symbols_list" >&5 +printf "%s\n" "$lt_cv_ld_exported_symbols_list" >&6; } + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for -force_load linker flag" >&5 +printf %s "checking for -force_load linker flag... " >&6; } +if test ${lt_cv_ld_force_load+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_ld_force_load=no + cat > conftest.c << _LT_EOF +int forced_loaded() { return 2;} +_LT_EOF + echo "$LTCC $LTCFLAGS -c -o conftest.o conftest.c" >&5 + $LTCC $LTCFLAGS -c -o conftest.o conftest.c 2>&5 + echo "$AR $AR_FLAGS libconftest.a conftest.o" >&5 + $AR $AR_FLAGS libconftest.a conftest.o 2>&5 + echo "$RANLIB libconftest.a" >&5 + $RANLIB libconftest.a 2>&5 + cat > conftest.c << _LT_EOF +int main() { return 0;} +_LT_EOF + echo "$LTCC $LTCFLAGS $LDFLAGS -o conftest conftest.c -Wl,-force_load,./libconftest.a" >&5 + $LTCC $LTCFLAGS $LDFLAGS -o conftest conftest.c -Wl,-force_load,./libconftest.a 2>conftest.err + _lt_result=$? + if test -s conftest.err && $GREP force_load conftest.err; then + cat conftest.err >&5 + elif test -f conftest && test 0 = "$_lt_result" && $GREP forced_load conftest >/dev/null 2>&1; then + lt_cv_ld_force_load=yes + else + cat conftest.err >&5 + fi + rm -f conftest.err libconftest.a conftest conftest.c + rm -rf conftest.dSYM + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_ld_force_load" >&5 +printf "%s\n" "$lt_cv_ld_force_load" >&6; } + case $host_os in + rhapsody* | darwin1.[012]) + _lt_dar_allow_undefined='$wl-undefined ${wl}suppress' ;; + darwin1.*) + _lt_dar_allow_undefined='$wl-flat_namespace $wl-undefined ${wl}suppress' ;; + darwin*) + case $MACOSX_DEPLOYMENT_TARGET,$host in + 10.[012],*|,*powerpc*-darwin[5-8]*) + _lt_dar_allow_undefined='$wl-flat_namespace $wl-undefined ${wl}suppress' ;; + *) + _lt_dar_allow_undefined='$wl-undefined ${wl}dynamic_lookup' ;; + esac + ;; + esac + if test yes = "$lt_cv_apple_cc_single_mod"; then + _lt_dar_single_mod='$single_module' + fi + if test yes = "$lt_cv_ld_exported_symbols_list"; then + _lt_dar_export_syms=' $wl-exported_symbols_list,$output_objdir/$libname-symbols.expsym' + else + _lt_dar_export_syms='~$NMEDIT -s $output_objdir/$libname-symbols.expsym $lib' + fi + if test : != "$DSYMUTIL" && test no = "$lt_cv_ld_force_load"; then + _lt_dsymutil='~$DSYMUTIL $lib || :' + else + _lt_dsymutil= + fi + ;; + esac + +# func_munge_path_list VARIABLE PATH +# ----------------------------------- +# VARIABLE is name of variable containing _space_ separated list of +# directories to be munged by the contents of PATH, which is string +# having a format: +# "DIR[:DIR]:" +# string "DIR[ DIR]" will be prepended to VARIABLE +# ":DIR[:DIR]" +# string "DIR[ DIR]" will be appended to VARIABLE +# "DIRP[:DIRP]::[DIRA:]DIRA" +# string "DIRP[ DIRP]" will be prepended to VARIABLE and string +# "DIRA[ DIRA]" will be appended to VARIABLE +# "DIR[:DIR]" +# VARIABLE will be replaced by "DIR[ DIR]" +func_munge_path_list () +{ + case x$2 in + x) + ;; + *:) + eval $1=\"`$ECHO $2 | $SED 's/:/ /g'` \$$1\" + ;; + x:*) + eval $1=\"\$$1 `$ECHO $2 | $SED 's/:/ /g'`\" + ;; + *::*) + eval $1=\"\$$1\ `$ECHO $2 | $SED -e 's/.*:://' -e 's/:/ /g'`\" + eval $1=\"`$ECHO $2 | $SED -e 's/::.*//' -e 's/:/ /g'`\ \$$1\" + ;; + *) + eval $1=\"`$ECHO $2 | $SED 's/:/ /g'`\" + ;; + esac +} + +ac_header= ac_cache= +for ac_item in $ac_header_c_list +do + if test $ac_cache; then + ac_fn_c_check_header_compile "$LINENO" $ac_header ac_cv_header_$ac_cache "$ac_includes_default" + if eval test \"x\$ac_cv_header_$ac_cache\" = xyes; then + printf "%s\n" "#define $ac_item 1" >> confdefs.h + fi + ac_header= ac_cache= + elif test $ac_header; then + ac_cache=$ac_item + else + ac_header=$ac_item + fi +done + + + + + + + + +if test $ac_cv_header_stdlib_h = yes && test $ac_cv_header_string_h = yes +then : + +printf "%s\n" "#define STDC_HEADERS 1" >>confdefs.h + +fi +ac_fn_c_check_header_compile "$LINENO" "dlfcn.h" "ac_cv_header_dlfcn_h" "$ac_includes_default +" +if test "x$ac_cv_header_dlfcn_h" = xyes +then : + printf "%s\n" "#define HAVE_DLFCN_H 1" >>confdefs.h + +fi + + + + + +# Set options +enable_win32_dll=yes + +case $host in +*-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-cegcc*) + if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}as", so it can be a program name with args. +set dummy ${ac_tool_prefix}as; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_AS+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$AS"; then + ac_cv_prog_AS="$AS" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_AS="${ac_tool_prefix}as" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +AS=$ac_cv_prog_AS +if test -n "$AS"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $AS" >&5 +printf "%s\n" "$AS" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_AS"; then + ac_ct_AS=$AS + # Extract the first word of "as", so it can be a program name with args. +set dummy as; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_AS+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_AS"; then + ac_cv_prog_ac_ct_AS="$ac_ct_AS" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_AS="as" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_AS=$ac_cv_prog_ac_ct_AS +if test -n "$ac_ct_AS"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_AS" >&5 +printf "%s\n" "$ac_ct_AS" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_ct_AS" = x; then + AS="false" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + AS=$ac_ct_AS + fi +else + AS="$ac_cv_prog_AS" +fi + + if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}dlltool", so it can be a program name with args. +set dummy ${ac_tool_prefix}dlltool; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_DLLTOOL+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$DLLTOOL"; then + ac_cv_prog_DLLTOOL="$DLLTOOL" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_DLLTOOL="${ac_tool_prefix}dlltool" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +DLLTOOL=$ac_cv_prog_DLLTOOL +if test -n "$DLLTOOL"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $DLLTOOL" >&5 +printf "%s\n" "$DLLTOOL" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_DLLTOOL"; then + ac_ct_DLLTOOL=$DLLTOOL + # Extract the first word of "dlltool", so it can be a program name with args. +set dummy dlltool; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_DLLTOOL+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_DLLTOOL"; then + ac_cv_prog_ac_ct_DLLTOOL="$ac_ct_DLLTOOL" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_DLLTOOL="dlltool" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_DLLTOOL=$ac_cv_prog_ac_ct_DLLTOOL +if test -n "$ac_ct_DLLTOOL"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_DLLTOOL" >&5 +printf "%s\n" "$ac_ct_DLLTOOL" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_ct_DLLTOOL" = x; then + DLLTOOL="false" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + DLLTOOL=$ac_ct_DLLTOOL + fi +else + DLLTOOL="$ac_cv_prog_DLLTOOL" +fi + + if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}objdump", so it can be a program name with args. +set dummy ${ac_tool_prefix}objdump; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_OBJDUMP+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$OBJDUMP"; then + ac_cv_prog_OBJDUMP="$OBJDUMP" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_OBJDUMP="${ac_tool_prefix}objdump" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +OBJDUMP=$ac_cv_prog_OBJDUMP +if test -n "$OBJDUMP"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $OBJDUMP" >&5 +printf "%s\n" "$OBJDUMP" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_OBJDUMP"; then + ac_ct_OBJDUMP=$OBJDUMP + # Extract the first word of "objdump", so it can be a program name with args. +set dummy objdump; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_OBJDUMP+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_OBJDUMP"; then + ac_cv_prog_ac_ct_OBJDUMP="$ac_ct_OBJDUMP" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_OBJDUMP="objdump" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_OBJDUMP=$ac_cv_prog_ac_ct_OBJDUMP +if test -n "$ac_ct_OBJDUMP"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_OBJDUMP" >&5 +printf "%s\n" "$ac_ct_OBJDUMP" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_ct_OBJDUMP" = x; then + OBJDUMP="false" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + OBJDUMP=$ac_ct_OBJDUMP + fi +else + OBJDUMP="$ac_cv_prog_OBJDUMP" +fi + + ;; +esac + +test -z "$AS" && AS=as + + + + + +test -z "$DLLTOOL" && DLLTOOL=dlltool + + + + + +test -z "$OBJDUMP" && OBJDUMP=objdump + + + + + + + + enable_dlopen=no + + + + # Check whether --enable-shared was given. +if test ${enable_shared+y} +then : + enableval=$enable_shared; p=${PACKAGE-default} + case $enableval in + yes) enable_shared=yes ;; + no) enable_shared=no ;; + *) + enable_shared=no + # Look at the argument we got. We use all the common list separators. + lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR, + for pkg in $enableval; do + IFS=$lt_save_ifs + if test "X$pkg" = "X$p"; then + enable_shared=yes + fi + done + IFS=$lt_save_ifs + ;; + esac +else $as_nop + enable_shared=yes +fi + + + + + + + + + + # Check whether --enable-static was given. +if test ${enable_static+y} +then : + enableval=$enable_static; p=${PACKAGE-default} + case $enableval in + yes) enable_static=yes ;; + no) enable_static=no ;; + *) + enable_static=no + # Look at the argument we got. We use all the common list separators. + lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR, + for pkg in $enableval; do + IFS=$lt_save_ifs + if test "X$pkg" = "X$p"; then + enable_static=yes + fi + done + IFS=$lt_save_ifs + ;; + esac +else $as_nop + enable_static=yes +fi + + + + + + + + + + +# Check whether --with-pic was given. +if test ${with_pic+y} +then : + withval=$with_pic; lt_p=${PACKAGE-default} + case $withval in + yes|no) pic_mode=$withval ;; + *) + pic_mode=default + # Look at the argument we got. We use all the common list separators. + lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR, + for lt_pkg in $withval; do + IFS=$lt_save_ifs + if test "X$lt_pkg" = "X$lt_p"; then + pic_mode=yes + fi + done + IFS=$lt_save_ifs + ;; + esac +else $as_nop + pic_mode=default +fi + + + + + + + + + # Check whether --enable-fast-install was given. +if test ${enable_fast_install+y} +then : + enableval=$enable_fast_install; p=${PACKAGE-default} + case $enableval in + yes) enable_fast_install=yes ;; + no) enable_fast_install=no ;; + *) + enable_fast_install=no + # Look at the argument we got. We use all the common list separators. + lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR, + for pkg in $enableval; do + IFS=$lt_save_ifs + if test "X$pkg" = "X$p"; then + enable_fast_install=yes + fi + done + IFS=$lt_save_ifs + ;; + esac +else $as_nop + enable_fast_install=yes +fi + + + + + + + + + shared_archive_member_spec= +case $host,$enable_shared in +power*-*-aix[5-9]*,yes) + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking which variant of shared library versioning to provide" >&5 +printf %s "checking which variant of shared library versioning to provide... " >&6; } + +# Check whether --with-aix-soname was given. +if test ${with_aix_soname+y} +then : + withval=$with_aix_soname; case $withval in + aix|svr4|both) + ;; + *) + as_fn_error $? "Unknown argument to --with-aix-soname" "$LINENO" 5 + ;; + esac + lt_cv_with_aix_soname=$with_aix_soname +else $as_nop + if test ${lt_cv_with_aix_soname+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_with_aix_soname=aix +fi + + with_aix_soname=$lt_cv_with_aix_soname +fi + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $with_aix_soname" >&5 +printf "%s\n" "$with_aix_soname" >&6; } + if test aix != "$with_aix_soname"; then + # For the AIX way of multilib, we name the shared archive member + # based on the bitwidth used, traditionally 'shr.o' or 'shr_64.o', + # and 'shr.imp' or 'shr_64.imp', respectively, for the Import File. + # Even when GNU compilers ignore OBJECT_MODE but need '-maix64' flag, + # the AIX toolchain works better with OBJECT_MODE set (default 32). + if test 64 = "${OBJECT_MODE-32}"; then + shared_archive_member_spec=shr_64 + else + shared_archive_member_spec=shr + fi + fi + ;; +*) + with_aix_soname=aix + ;; +esac + + + + + + + + + + +# This can be used to rebuild libtool when needed +LIBTOOL_DEPS=$ltmain + +# Always use our own libtool. +LIBTOOL='$(SHELL) $(top_builddir)/libtool' + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +test -z "$LN_S" && LN_S="ln -s" + + + + + + + + + + + + + + +if test -n "${ZSH_VERSION+set}"; then + setopt NO_GLOB_SUBST +fi + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for objdir" >&5 +printf %s "checking for objdir... " >&6; } +if test ${lt_cv_objdir+y} +then : + printf %s "(cached) " >&6 +else $as_nop + rm -f .libs 2>/dev/null +mkdir .libs 2>/dev/null +if test -d .libs; then + lt_cv_objdir=.libs +else + # MS-DOS does not allow filenames that begin with a dot. + lt_cv_objdir=_libs +fi +rmdir .libs 2>/dev/null +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_objdir" >&5 +printf "%s\n" "$lt_cv_objdir" >&6; } +objdir=$lt_cv_objdir + + + + + +printf "%s\n" "#define LT_OBJDIR \"$lt_cv_objdir/\"" >>confdefs.h + + + + +case $host_os in +aix3*) + # AIX sometimes has problems with the GCC collect2 program. For some + # reason, if we set the COLLECT_NAMES environment variable, the problems + # vanish in a puff of smoke. + if test set != "${COLLECT_NAMES+set}"; then + COLLECT_NAMES= + export COLLECT_NAMES + fi + ;; +esac + +# Global variables: +ofile=libtool +can_build_shared=yes + +# All known linkers require a '.a' archive for static linking (except MSVC and +# ICC, which need '.lib'). +libext=a + +with_gnu_ld=$lt_cv_prog_gnu_ld + +old_CC=$CC +old_CFLAGS=$CFLAGS + +# Set sane defaults for various variables +test -z "$CC" && CC=cc +test -z "$LTCC" && LTCC=$CC +test -z "$LTCFLAGS" && LTCFLAGS=$CFLAGS +test -z "$LD" && LD=ld +test -z "$ac_objext" && ac_objext=o + +func_cc_basename $compiler +cc_basename=$func_cc_basename_result + + +# Only perform the check for file, if the check method requires it +test -z "$MAGIC_CMD" && MAGIC_CMD=file +case $deplibs_check_method in +file_magic*) + if test "$file_magic_cmd" = '$MAGIC_CMD'; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for ${ac_tool_prefix}file" >&5 +printf %s "checking for ${ac_tool_prefix}file... " >&6; } +if test ${lt_cv_path_MAGIC_CMD+y} +then : + printf %s "(cached) " >&6 +else $as_nop + case $MAGIC_CMD in +[\\/*] | ?:[\\/]*) + lt_cv_path_MAGIC_CMD=$MAGIC_CMD # Let the user override the test with a path. + ;; +*) + lt_save_MAGIC_CMD=$MAGIC_CMD + lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR + ac_dummy="/usr/bin$PATH_SEPARATOR$PATH" + for ac_dir in $ac_dummy; do + IFS=$lt_save_ifs + test -z "$ac_dir" && ac_dir=. + if test -f "$ac_dir/${ac_tool_prefix}file"; then + lt_cv_path_MAGIC_CMD=$ac_dir/"${ac_tool_prefix}file" + if test -n "$file_magic_test_file"; then + case $deplibs_check_method in + "file_magic "*) + file_magic_regex=`expr "$deplibs_check_method" : "file_magic \(.*\)"` + MAGIC_CMD=$lt_cv_path_MAGIC_CMD + if eval $file_magic_cmd \$file_magic_test_file 2> /dev/null | + $EGREP "$file_magic_regex" > /dev/null; then + : + else + cat <<_LT_EOF 1>&2 + +*** Warning: the command libtool uses to detect shared libraries, +*** $file_magic_cmd, produces output that libtool cannot recognize. +*** The result is that libtool may fail to recognize shared libraries +*** as such. This will affect the creation of libtool libraries that +*** depend on shared libraries, but programs linked with such libtool +*** libraries will work regardless of this problem. Nevertheless, you +*** may want to report the problem to your system manager and/or to +*** bug-libtool@gnu.org + +_LT_EOF + fi ;; + esac + fi + break + fi + done + IFS=$lt_save_ifs + MAGIC_CMD=$lt_save_MAGIC_CMD + ;; +esac +fi + +MAGIC_CMD=$lt_cv_path_MAGIC_CMD +if test -n "$MAGIC_CMD"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $MAGIC_CMD" >&5 +printf "%s\n" "$MAGIC_CMD" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + + + +if test -z "$lt_cv_path_MAGIC_CMD"; then + if test -n "$ac_tool_prefix"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for file" >&5 +printf %s "checking for file... " >&6; } +if test ${lt_cv_path_MAGIC_CMD+y} +then : + printf %s "(cached) " >&6 +else $as_nop + case $MAGIC_CMD in +[\\/*] | ?:[\\/]*) + lt_cv_path_MAGIC_CMD=$MAGIC_CMD # Let the user override the test with a path. + ;; +*) + lt_save_MAGIC_CMD=$MAGIC_CMD + lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR + ac_dummy="/usr/bin$PATH_SEPARATOR$PATH" + for ac_dir in $ac_dummy; do + IFS=$lt_save_ifs + test -z "$ac_dir" && ac_dir=. + if test -f "$ac_dir/file"; then + lt_cv_path_MAGIC_CMD=$ac_dir/"file" + if test -n "$file_magic_test_file"; then + case $deplibs_check_method in + "file_magic "*) + file_magic_regex=`expr "$deplibs_check_method" : "file_magic \(.*\)"` + MAGIC_CMD=$lt_cv_path_MAGIC_CMD + if eval $file_magic_cmd \$file_magic_test_file 2> /dev/null | + $EGREP "$file_magic_regex" > /dev/null; then + : + else + cat <<_LT_EOF 1>&2 + +*** Warning: the command libtool uses to detect shared libraries, +*** $file_magic_cmd, produces output that libtool cannot recognize. +*** The result is that libtool may fail to recognize shared libraries +*** as such. This will affect the creation of libtool libraries that +*** depend on shared libraries, but programs linked with such libtool +*** libraries will work regardless of this problem. Nevertheless, you +*** may want to report the problem to your system manager and/or to +*** bug-libtool@gnu.org + +_LT_EOF + fi ;; + esac + fi + break + fi + done + IFS=$lt_save_ifs + MAGIC_CMD=$lt_save_MAGIC_CMD + ;; +esac +fi + +MAGIC_CMD=$lt_cv_path_MAGIC_CMD +if test -n "$MAGIC_CMD"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $MAGIC_CMD" >&5 +printf "%s\n" "$MAGIC_CMD" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + else + MAGIC_CMD=: + fi +fi + + fi + ;; +esac + +# Use C for the default configuration in the libtool script + +lt_save_CC=$CC +ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu + + +# Source file extension for C test sources. +ac_ext=c + +# Object file extension for compiled C test sources. +objext=o +objext=$objext + +# Code to be used in simple compile tests +lt_simple_compile_test_code="int some_variable = 0;" + +# Code to be used in simple link tests +lt_simple_link_test_code='int main(){return(0);}' + + + + + + + +# If no C compiler was specified, use CC. +LTCC=${LTCC-"$CC"} + +# If no C compiler flags were specified, use CFLAGS. +LTCFLAGS=${LTCFLAGS-"$CFLAGS"} + +# Allow CC to be a program name with arguments. +compiler=$CC + +# Save the default compiler, since it gets overwritten when the other +# tags are being tested, and _LT_TAGVAR(compiler, []) is a NOP. +compiler_DEFAULT=$CC + +# save warnings/boilerplate of simple test code +ac_outfile=conftest.$ac_objext +echo "$lt_simple_compile_test_code" >conftest.$ac_ext +eval "$ac_compile" 2>&1 >/dev/null | $SED '/^$/d; /^ *+/d' >conftest.err +_lt_compiler_boilerplate=`cat conftest.err` +$RM conftest* + +ac_outfile=conftest.$ac_objext +echo "$lt_simple_link_test_code" >conftest.$ac_ext +eval "$ac_link" 2>&1 >/dev/null | $SED '/^$/d; /^ *+/d' >conftest.err +_lt_linker_boilerplate=`cat conftest.err` +$RM -r conftest* + + +if test -n "$compiler"; then + +lt_prog_compiler_no_builtin_flag= + +if test yes = "$GCC"; then + case $cc_basename in + nvcc*) + lt_prog_compiler_no_builtin_flag=' -Xcompiler -fno-builtin' ;; + *) + lt_prog_compiler_no_builtin_flag=' -fno-builtin' ;; + esac + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking if $compiler supports -fno-rtti -fno-exceptions" >&5 +printf %s "checking if $compiler supports -fno-rtti -fno-exceptions... " >&6; } +if test ${lt_cv_prog_compiler_rtti_exceptions+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_prog_compiler_rtti_exceptions=no + ac_outfile=conftest.$ac_objext + echo "$lt_simple_compile_test_code" > conftest.$ac_ext + lt_compiler_flag="-fno-rtti -fno-exceptions" ## exclude from sc_useless_quotes_in_assignment + # Insert the option either (1) after the last *FLAGS variable, or + # (2) before a word containing "conftest.", or (3) at the end. + # Note that $ac_compile itself does not contain backslashes and begins + # with a dollar sign (not a hyphen), so the echo should work correctly. + # The option is referenced via a variable to avoid confusing sed. + lt_compile=`echo "$ac_compile" | $SED \ + -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ + -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ + -e 's:$: $lt_compiler_flag:'` + (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&5) + (eval "$lt_compile" 2>conftest.err) + ac_status=$? + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + if (exit $ac_status) && test -s "$ac_outfile"; then + # The compiler can only warn and ignore the option if not recognized + # So say no if there are warnings other than the usual output. + $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' >conftest.exp + $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 + if test ! -s conftest.er2 || diff conftest.exp conftest.er2 >/dev/null; then + lt_cv_prog_compiler_rtti_exceptions=yes + fi + fi + $RM conftest* + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_rtti_exceptions" >&5 +printf "%s\n" "$lt_cv_prog_compiler_rtti_exceptions" >&6; } + +if test yes = "$lt_cv_prog_compiler_rtti_exceptions"; then + lt_prog_compiler_no_builtin_flag="$lt_prog_compiler_no_builtin_flag -fno-rtti -fno-exceptions" +else + : +fi + +fi + + + + + + + lt_prog_compiler_wl= +lt_prog_compiler_pic= +lt_prog_compiler_static= + + + if test yes = "$GCC"; then + lt_prog_compiler_wl='-Wl,' + lt_prog_compiler_static='-static' + + case $host_os in + aix*) + # All AIX code is PIC. + if test ia64 = "$host_cpu"; then + # AIX 5 now supports IA64 processor + lt_prog_compiler_static='-Bstatic' + fi + lt_prog_compiler_pic='-fPIC' + ;; + + amigaos*) + case $host_cpu in + powerpc) + # see comment about AmigaOS4 .so support + lt_prog_compiler_pic='-fPIC' + ;; + m68k) + # FIXME: we need at least 68020 code to build shared libraries, but + # adding the '-m68020' flag to GCC prevents building anything better, + # like '-m68040'. + lt_prog_compiler_pic='-m68020 -resident32 -malways-restore-a4' + ;; + esac + ;; + + beos* | irix5* | irix6* | nonstopux* | osf3* | osf4* | osf5*) + # PIC is the default for these OSes. + ;; + + mingw* | cygwin* | pw32* | os2* | cegcc*) + # This hack is so that the source file can tell whether it is being + # built for inclusion in a dll (and should export symbols for example). + # Although the cygwin gcc ignores -fPIC, still need this for old-style + # (--disable-auto-import) libraries + lt_prog_compiler_pic='-DDLL_EXPORT' + case $host_os in + os2*) + lt_prog_compiler_static='$wl-static' + ;; + esac + ;; + + darwin* | rhapsody*) + # PIC is the default on this platform + # Common symbols not allowed in MH_DYLIB files + lt_prog_compiler_pic='-fno-common' + ;; + + haiku*) + # PIC is the default for Haiku. + # The "-static" flag exists, but is broken. + lt_prog_compiler_static= + ;; + + hpux*) + # PIC is the default for 64-bit PA HP-UX, but not for 32-bit + # PA HP-UX. On IA64 HP-UX, PIC is the default but the pic flag + # sets the default TLS model and affects inlining. + case $host_cpu in + hppa*64*) + # +Z the default + ;; + *) + lt_prog_compiler_pic='-fPIC' + ;; + esac + ;; + + interix[3-9]*) + # Interix 3.x gcc -fpic/-fPIC options generate broken code. + # Instead, we relocate shared libraries at runtime. + ;; + + msdosdjgpp*) + # Just because we use GCC doesn't mean we suddenly get shared libraries + # on systems that don't support them. + lt_prog_compiler_can_build_shared=no + enable_shared=no + ;; + + *nto* | *qnx*) + # QNX uses GNU C++, but need to define -shared option too, otherwise + # it will coredump. + lt_prog_compiler_pic='-fPIC -shared' + ;; + + sysv4*MP*) + if test -d /usr/nec; then + lt_prog_compiler_pic=-Kconform_pic + fi + ;; + + *) + lt_prog_compiler_pic='-fPIC' + ;; + esac + + case $cc_basename in + nvcc*) # Cuda Compiler Driver 2.2 + lt_prog_compiler_wl='-Xlinker ' + if test -n "$lt_prog_compiler_pic"; then + lt_prog_compiler_pic="-Xcompiler $lt_prog_compiler_pic" + fi + ;; + esac + else + # PORTME Check for flag to pass linker flags through the system compiler. + case $host_os in + aix*) + lt_prog_compiler_wl='-Wl,' + if test ia64 = "$host_cpu"; then + # AIX 5 now supports IA64 processor + lt_prog_compiler_static='-Bstatic' + else + lt_prog_compiler_static='-bnso -bI:/lib/syscalls.exp' + fi + ;; + + darwin* | rhapsody*) + # PIC is the default on this platform + # Common symbols not allowed in MH_DYLIB files + lt_prog_compiler_pic='-fno-common' + case $cc_basename in + nagfor*) + # NAG Fortran compiler + lt_prog_compiler_wl='-Wl,-Wl,,' + lt_prog_compiler_pic='-PIC' + lt_prog_compiler_static='-Bstatic' + ;; + esac + ;; + + mingw* | cygwin* | pw32* | os2* | cegcc*) + # This hack is so that the source file can tell whether it is being + # built for inclusion in a dll (and should export symbols for example). + lt_prog_compiler_pic='-DDLL_EXPORT' + case $host_os in + os2*) + lt_prog_compiler_static='$wl-static' + ;; + esac + ;; + + hpux9* | hpux10* | hpux11*) + lt_prog_compiler_wl='-Wl,' + # PIC is the default for IA64 HP-UX and 64-bit HP-UX, but + # not for PA HP-UX. + case $host_cpu in + hppa*64*|ia64*) + # +Z the default + ;; + *) + lt_prog_compiler_pic='+Z' + ;; + esac + # Is there a better lt_prog_compiler_static that works with the bundled CC? + lt_prog_compiler_static='$wl-a ${wl}archive' + ;; + + irix5* | irix6* | nonstopux*) + lt_prog_compiler_wl='-Wl,' + # PIC (with -KPIC) is the default. + lt_prog_compiler_static='-non_shared' + ;; + + linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) + case $cc_basename in + # old Intel for x86_64, which still supported -KPIC. + ecc*) + lt_prog_compiler_wl='-Wl,' + lt_prog_compiler_pic='-KPIC' + lt_prog_compiler_static='-static' + ;; + # icc used to be incompatible with GCC. + # ICC 10 doesn't accept -KPIC any more. + icc* | ifort*) + lt_prog_compiler_wl='-Wl,' + lt_prog_compiler_pic='-fPIC' + lt_prog_compiler_static='-static' + ;; + # Lahey Fortran 8.1. + lf95*) + lt_prog_compiler_wl='-Wl,' + lt_prog_compiler_pic='--shared' + lt_prog_compiler_static='--static' + ;; + nagfor*) + # NAG Fortran compiler + lt_prog_compiler_wl='-Wl,-Wl,,' + lt_prog_compiler_pic='-PIC' + lt_prog_compiler_static='-Bstatic' + ;; + tcc*) + # Fabrice Bellard et al's Tiny C Compiler + lt_prog_compiler_wl='-Wl,' + lt_prog_compiler_pic='-fPIC' + lt_prog_compiler_static='-static' + ;; + pgcc* | pgf77* | pgf90* | pgf95* | pgfortran*) + # Portland Group compilers (*not* the Pentium gcc compiler, + # which looks to be a dead project) + lt_prog_compiler_wl='-Wl,' + lt_prog_compiler_pic='-fpic' + lt_prog_compiler_static='-Bstatic' + ;; + ccc*) + lt_prog_compiler_wl='-Wl,' + # All Alpha code is PIC. + lt_prog_compiler_static='-non_shared' + ;; + xl* | bgxl* | bgf* | mpixl*) + # IBM XL C 8.0/Fortran 10.1, 11.1 on PPC and BlueGene + lt_prog_compiler_wl='-Wl,' + lt_prog_compiler_pic='-qpic' + lt_prog_compiler_static='-qstaticlink' + ;; + *) + case `$CC -V 2>&1 | $SED 5q` in + *Sun\ Ceres\ Fortran* | *Sun*Fortran*\ [1-7].* | *Sun*Fortran*\ 8.[0-3]*) + # Sun Fortran 8.3 passes all unrecognized flags to the linker + lt_prog_compiler_pic='-KPIC' + lt_prog_compiler_static='-Bstatic' + lt_prog_compiler_wl='' + ;; + *Sun\ F* | *Sun*Fortran*) + lt_prog_compiler_pic='-KPIC' + lt_prog_compiler_static='-Bstatic' + lt_prog_compiler_wl='-Qoption ld ' + ;; + *Sun\ C*) + # Sun C 5.9 + lt_prog_compiler_pic='-KPIC' + lt_prog_compiler_static='-Bstatic' + lt_prog_compiler_wl='-Wl,' + ;; + *Intel*\ [CF]*Compiler*) + lt_prog_compiler_wl='-Wl,' + lt_prog_compiler_pic='-fPIC' + lt_prog_compiler_static='-static' + ;; + *Portland\ Group*) + lt_prog_compiler_wl='-Wl,' + lt_prog_compiler_pic='-fpic' + lt_prog_compiler_static='-Bstatic' + ;; + esac + ;; + esac + ;; + + newsos6) + lt_prog_compiler_pic='-KPIC' + lt_prog_compiler_static='-Bstatic' + ;; + + *nto* | *qnx*) + # QNX uses GNU C++, but need to define -shared option too, otherwise + # it will coredump. + lt_prog_compiler_pic='-fPIC -shared' + ;; + + osf3* | osf4* | osf5*) + lt_prog_compiler_wl='-Wl,' + # All OSF/1 code is PIC. + lt_prog_compiler_static='-non_shared' + ;; + + rdos*) + lt_prog_compiler_static='-non_shared' + ;; + + solaris*) + lt_prog_compiler_pic='-KPIC' + lt_prog_compiler_static='-Bstatic' + case $cc_basename in + f77* | f90* | f95* | sunf77* | sunf90* | sunf95*) + lt_prog_compiler_wl='-Qoption ld ';; + *) + lt_prog_compiler_wl='-Wl,';; + esac + ;; + + sunos4*) + lt_prog_compiler_wl='-Qoption ld ' + lt_prog_compiler_pic='-PIC' + lt_prog_compiler_static='-Bstatic' + ;; + + sysv4 | sysv4.2uw2* | sysv4.3*) + lt_prog_compiler_wl='-Wl,' + lt_prog_compiler_pic='-KPIC' + lt_prog_compiler_static='-Bstatic' + ;; + + sysv4*MP*) + if test -d /usr/nec; then + lt_prog_compiler_pic='-Kconform_pic' + lt_prog_compiler_static='-Bstatic' + fi + ;; + + sysv5* | unixware* | sco3.2v5* | sco5v6* | OpenUNIX*) + lt_prog_compiler_wl='-Wl,' + lt_prog_compiler_pic='-KPIC' + lt_prog_compiler_static='-Bstatic' + ;; + + unicos*) + lt_prog_compiler_wl='-Wl,' + lt_prog_compiler_can_build_shared=no + ;; + + uts4*) + lt_prog_compiler_pic='-pic' + lt_prog_compiler_static='-Bstatic' + ;; + + *) + lt_prog_compiler_can_build_shared=no + ;; + esac + fi + +case $host_os in + # For platforms that do not support PIC, -DPIC is meaningless: + *djgpp*) + lt_prog_compiler_pic= + ;; + *) + lt_prog_compiler_pic="$lt_prog_compiler_pic -DPIC" + ;; +esac + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $compiler option to produce PIC" >&5 +printf %s "checking for $compiler option to produce PIC... " >&6; } +if test ${lt_cv_prog_compiler_pic+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_prog_compiler_pic=$lt_prog_compiler_pic +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_pic" >&5 +printf "%s\n" "$lt_cv_prog_compiler_pic" >&6; } +lt_prog_compiler_pic=$lt_cv_prog_compiler_pic + +# +# Check to make sure the PIC flag actually works. +# +if test -n "$lt_prog_compiler_pic"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking if $compiler PIC flag $lt_prog_compiler_pic works" >&5 +printf %s "checking if $compiler PIC flag $lt_prog_compiler_pic works... " >&6; } +if test ${lt_cv_prog_compiler_pic_works+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_prog_compiler_pic_works=no + ac_outfile=conftest.$ac_objext + echo "$lt_simple_compile_test_code" > conftest.$ac_ext + lt_compiler_flag="$lt_prog_compiler_pic -DPIC" ## exclude from sc_useless_quotes_in_assignment + # Insert the option either (1) after the last *FLAGS variable, or + # (2) before a word containing "conftest.", or (3) at the end. + # Note that $ac_compile itself does not contain backslashes and begins + # with a dollar sign (not a hyphen), so the echo should work correctly. + # The option is referenced via a variable to avoid confusing sed. + lt_compile=`echo "$ac_compile" | $SED \ + -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ + -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ + -e 's:$: $lt_compiler_flag:'` + (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&5) + (eval "$lt_compile" 2>conftest.err) + ac_status=$? + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + if (exit $ac_status) && test -s "$ac_outfile"; then + # The compiler can only warn and ignore the option if not recognized + # So say no if there are warnings other than the usual output. + $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' >conftest.exp + $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 + if test ! -s conftest.er2 || diff conftest.exp conftest.er2 >/dev/null; then + lt_cv_prog_compiler_pic_works=yes + fi + fi + $RM conftest* + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_pic_works" >&5 +printf "%s\n" "$lt_cv_prog_compiler_pic_works" >&6; } + +if test yes = "$lt_cv_prog_compiler_pic_works"; then + case $lt_prog_compiler_pic in + "" | " "*) ;; + *) lt_prog_compiler_pic=" $lt_prog_compiler_pic" ;; + esac +else + lt_prog_compiler_pic= + lt_prog_compiler_can_build_shared=no +fi + +fi + + + + + + + + + + + +# +# Check to make sure the static flag actually works. +# +wl=$lt_prog_compiler_wl eval lt_tmp_static_flag=\"$lt_prog_compiler_static\" +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking if $compiler static flag $lt_tmp_static_flag works" >&5 +printf %s "checking if $compiler static flag $lt_tmp_static_flag works... " >&6; } +if test ${lt_cv_prog_compiler_static_works+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_prog_compiler_static_works=no + save_LDFLAGS=$LDFLAGS + LDFLAGS="$LDFLAGS $lt_tmp_static_flag" + echo "$lt_simple_link_test_code" > conftest.$ac_ext + if (eval $ac_link 2>conftest.err) && test -s conftest$ac_exeext; then + # The linker can only warn and ignore the option if not recognized + # So say no if there are warnings + if test -s conftest.err; then + # Append any errors to the config.log. + cat conftest.err 1>&5 + $ECHO "$_lt_linker_boilerplate" | $SED '/^$/d' > conftest.exp + $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 + if diff conftest.exp conftest.er2 >/dev/null; then + lt_cv_prog_compiler_static_works=yes + fi + else + lt_cv_prog_compiler_static_works=yes + fi + fi + $RM -r conftest* + LDFLAGS=$save_LDFLAGS + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_static_works" >&5 +printf "%s\n" "$lt_cv_prog_compiler_static_works" >&6; } + +if test yes = "$lt_cv_prog_compiler_static_works"; then + : +else + lt_prog_compiler_static= +fi + + + + + + + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking if $compiler supports -c -o file.$ac_objext" >&5 +printf %s "checking if $compiler supports -c -o file.$ac_objext... " >&6; } +if test ${lt_cv_prog_compiler_c_o+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_prog_compiler_c_o=no + $RM -r conftest 2>/dev/null + mkdir conftest + cd conftest + mkdir out + echo "$lt_simple_compile_test_code" > conftest.$ac_ext + + lt_compiler_flag="-o out/conftest2.$ac_objext" + # Insert the option either (1) after the last *FLAGS variable, or + # (2) before a word containing "conftest.", or (3) at the end. + # Note that $ac_compile itself does not contain backslashes and begins + # with a dollar sign (not a hyphen), so the echo should work correctly. + lt_compile=`echo "$ac_compile" | $SED \ + -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ + -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ + -e 's:$: $lt_compiler_flag:'` + (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&5) + (eval "$lt_compile" 2>out/conftest.err) + ac_status=$? + cat out/conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + if (exit $ac_status) && test -s out/conftest2.$ac_objext + then + # The compiler can only warn and ignore the option if not recognized + # So say no if there are warnings + $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' > out/conftest.exp + $SED '/^$/d; /^ *+/d' out/conftest.err >out/conftest.er2 + if test ! -s out/conftest.er2 || diff out/conftest.exp out/conftest.er2 >/dev/null; then + lt_cv_prog_compiler_c_o=yes + fi + fi + chmod u+w . 2>&5 + $RM conftest* + # SGI C++ compiler will create directory out/ii_files/ for + # template instantiation + test -d out/ii_files && $RM out/ii_files/* && rmdir out/ii_files + $RM out/* && rmdir out + cd .. + $RM -r conftest + $RM conftest* + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_c_o" >&5 +printf "%s\n" "$lt_cv_prog_compiler_c_o" >&6; } + + + + + + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking if $compiler supports -c -o file.$ac_objext" >&5 +printf %s "checking if $compiler supports -c -o file.$ac_objext... " >&6; } +if test ${lt_cv_prog_compiler_c_o+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_prog_compiler_c_o=no + $RM -r conftest 2>/dev/null + mkdir conftest + cd conftest + mkdir out + echo "$lt_simple_compile_test_code" > conftest.$ac_ext + + lt_compiler_flag="-o out/conftest2.$ac_objext" + # Insert the option either (1) after the last *FLAGS variable, or + # (2) before a word containing "conftest.", or (3) at the end. + # Note that $ac_compile itself does not contain backslashes and begins + # with a dollar sign (not a hyphen), so the echo should work correctly. + lt_compile=`echo "$ac_compile" | $SED \ + -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ + -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ + -e 's:$: $lt_compiler_flag:'` + (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&5) + (eval "$lt_compile" 2>out/conftest.err) + ac_status=$? + cat out/conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + if (exit $ac_status) && test -s out/conftest2.$ac_objext + then + # The compiler can only warn and ignore the option if not recognized + # So say no if there are warnings + $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' > out/conftest.exp + $SED '/^$/d; /^ *+/d' out/conftest.err >out/conftest.er2 + if test ! -s out/conftest.er2 || diff out/conftest.exp out/conftest.er2 >/dev/null; then + lt_cv_prog_compiler_c_o=yes + fi + fi + chmod u+w . 2>&5 + $RM conftest* + # SGI C++ compiler will create directory out/ii_files/ for + # template instantiation + test -d out/ii_files && $RM out/ii_files/* && rmdir out/ii_files + $RM out/* && rmdir out + cd .. + $RM -r conftest + $RM conftest* + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_c_o" >&5 +printf "%s\n" "$lt_cv_prog_compiler_c_o" >&6; } + + + + +hard_links=nottested +if test no = "$lt_cv_prog_compiler_c_o" && test no != "$need_locks"; then + # do not overwrite the value of need_locks provided by the user + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking if we can lock with hard links" >&5 +printf %s "checking if we can lock with hard links... " >&6; } + hard_links=yes + $RM conftest* + ln conftest.a conftest.b 2>/dev/null && hard_links=no + touch conftest.a + ln conftest.a conftest.b 2>&5 || hard_links=no + ln conftest.a conftest.b 2>/dev/null && hard_links=no + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $hard_links" >&5 +printf "%s\n" "$hard_links" >&6; } + if test no = "$hard_links"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: '$CC' does not support '-c -o', so 'make -j' may be unsafe" >&5 +printf "%s\n" "$as_me: WARNING: '$CC' does not support '-c -o', so 'make -j' may be unsafe" >&2;} + need_locks=warn + fi +else + need_locks=no +fi + + + + + + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether the $compiler linker ($LD) supports shared libraries" >&5 +printf %s "checking whether the $compiler linker ($LD) supports shared libraries... " >&6; } + + runpath_var= + allow_undefined_flag= + always_export_symbols=no + archive_cmds= + archive_expsym_cmds= + compiler_needs_object=no + enable_shared_with_static_runtimes=no + export_dynamic_flag_spec= + export_symbols_cmds='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\''s/.* //'\'' | sort | uniq > $export_symbols' + hardcode_automatic=no + hardcode_direct=no + hardcode_direct_absolute=no + hardcode_libdir_flag_spec= + hardcode_libdir_separator= + hardcode_minus_L=no + hardcode_shlibpath_var=unsupported + inherit_rpath=no + link_all_deplibs=unknown + module_cmds= + module_expsym_cmds= + old_archive_from_new_cmds= + old_archive_from_expsyms_cmds= + thread_safe_flag_spec= + whole_archive_flag_spec= + # include_expsyms should be a list of space-separated symbols to be *always* + # included in the symbol list + include_expsyms= + # exclude_expsyms can be an extended regexp of symbols to exclude + # it will be wrapped by ' (' and ')$', so one must not match beginning or + # end of line. Example: 'a|bc|.*d.*' will exclude the symbols 'a' and 'bc', + # as well as any symbol that contains 'd'. + exclude_expsyms='_GLOBAL_OFFSET_TABLE_|_GLOBAL__F[ID]_.*' + # Although _GLOBAL_OFFSET_TABLE_ is a valid symbol C name, most a.out + # platforms (ab)use it in PIC code, but their linkers get confused if + # the symbol is explicitly referenced. Since portable code cannot + # rely on this symbol name, it's probably fine to never include it in + # preloaded symbol tables. + # Exclude shared library initialization/finalization symbols. + extract_expsyms_cmds= + + case $host_os in + cygwin* | mingw* | pw32* | cegcc*) + # FIXME: the MSVC++ and ICC port hasn't been tested in a loooong time + # When not using gcc, we currently assume that we are using + # Microsoft Visual C++ or Intel C++ Compiler. + if test yes != "$GCC"; then + with_gnu_ld=no + fi + ;; + interix*) + # we just hope/assume this is gcc and not c89 (= MSVC++ or ICC) + with_gnu_ld=yes + ;; + openbsd* | bitrig*) + with_gnu_ld=no + ;; + esac + + ld_shlibs=yes + + # On some targets, GNU ld is compatible enough with the native linker + # that we're better off using the native interface for both. + lt_use_gnu_ld_interface=no + if test yes = "$with_gnu_ld"; then + case $host_os in + aix*) + # The AIX port of GNU ld has always aspired to compatibility + # with the native linker. However, as the warning in the GNU ld + # block says, versions before 2.19.5* couldn't really create working + # shared libraries, regardless of the interface used. + case `$LD -v 2>&1` in + *\ \(GNU\ Binutils\)\ 2.19.5*) ;; + *\ \(GNU\ Binutils\)\ 2.[2-9]*) ;; + *\ \(GNU\ Binutils\)\ [3-9]*) ;; + *) + lt_use_gnu_ld_interface=yes + ;; + esac + ;; + *) + lt_use_gnu_ld_interface=yes + ;; + esac + fi + + if test yes = "$lt_use_gnu_ld_interface"; then + # If archive_cmds runs LD, not CC, wlarc should be empty + wlarc='$wl' + + # Set some defaults for GNU ld with shared library support. These + # are reset later if shared libraries are not supported. Putting them + # here allows them to be overridden if necessary. + runpath_var=LD_RUN_PATH + hardcode_libdir_flag_spec='$wl-rpath $wl$libdir' + export_dynamic_flag_spec='$wl--export-dynamic' + # ancient GNU ld didn't support --whole-archive et. al. + if $LD --help 2>&1 | $GREP 'no-whole-archive' > /dev/null; then + whole_archive_flag_spec=$wlarc'--whole-archive$convenience '$wlarc'--no-whole-archive' + else + whole_archive_flag_spec= + fi + supports_anon_versioning=no + case `$LD -v | $SED -e 's/([^)]\+)\s\+//' 2>&1` in + *GNU\ gold*) supports_anon_versioning=yes ;; + *\ [01].* | *\ 2.[0-9].* | *\ 2.10.*) ;; # catch versions < 2.11 + *\ 2.11.93.0.2\ *) supports_anon_versioning=yes ;; # RH7.3 ... + *\ 2.11.92.0.12\ *) supports_anon_versioning=yes ;; # Mandrake 8.2 ... + *\ 2.11.*) ;; # other 2.11 versions + *) supports_anon_versioning=yes ;; + esac + + # See if GNU ld supports shared libraries. + case $host_os in + aix[3-9]*) + # On AIX/PPC, the GNU linker is very broken + if test ia64 != "$host_cpu"; then + ld_shlibs=no + cat <<_LT_EOF 1>&2 + +*** Warning: the GNU linker, at least up to release 2.19, is reported +*** to be unable to reliably create shared libraries on AIX. +*** Therefore, libtool is disabling shared libraries support. If you +*** really care for shared libraries, you may want to install binutils +*** 2.20 or above, or modify your PATH so that a non-GNU linker is found. +*** You will then need to restart the configuration process. + +_LT_EOF + fi + ;; + + amigaos*) + case $host_cpu in + powerpc) + # see comment about AmigaOS4 .so support + archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + archive_expsym_cmds='' + ;; + m68k) + archive_cmds='$RM $output_objdir/a2ixlibrary.data~$ECHO "#define NAME $libname" > $output_objdir/a2ixlibrary.data~$ECHO "#define LIBRARY_ID 1" >> $output_objdir/a2ixlibrary.data~$ECHO "#define VERSION $major" >> $output_objdir/a2ixlibrary.data~$ECHO "#define REVISION $revision" >> $output_objdir/a2ixlibrary.data~$AR $AR_FLAGS $lib $libobjs~$RANLIB $lib~(cd $output_objdir && a2ixlibrary -32)' + hardcode_libdir_flag_spec='-L$libdir' + hardcode_minus_L=yes + ;; + esac + ;; + + beos*) + if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then + allow_undefined_flag=unsupported + # Joseph Beckenbach says some releases of gcc + # support --undefined. This deserves some investigation. FIXME + archive_cmds='$CC -nostart $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + else + ld_shlibs=no + fi + ;; + + cygwin* | mingw* | pw32* | cegcc*) + # _LT_TAGVAR(hardcode_libdir_flag_spec, ) is actually meaningless, + # as there is no search path for DLLs. + hardcode_libdir_flag_spec='-L$libdir' + export_dynamic_flag_spec='$wl--export-all-symbols' + allow_undefined_flag=unsupported + always_export_symbols=no + enable_shared_with_static_runtimes=yes + export_symbols_cmds='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[BCDGRS][ ]/s/.*[ ]\([^ ]*\)/\1 DATA/;s/^.*[ ]__nm__\([^ ]*\)[ ][^ ]*/\1 DATA/;/^I[ ]/d;/^[AITW][ ]/s/.* //'\'' | sort | uniq > $export_symbols' + exclude_expsyms='[_]+GLOBAL_OFFSET_TABLE_|[_]+GLOBAL__[FID]_.*|[_]+head_[A-Za-z0-9_]+_dll|[A-Za-z0-9_]+_dll_iname' + + if $LD --help 2>&1 | $GREP 'auto-import' > /dev/null; then + archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' + # If the export-symbols file already is a .def file, use it as + # is; otherwise, prepend EXPORTS... + archive_expsym_cmds='if test DEF = "`$SED -n -e '\''s/^[ ]*//'\'' -e '\''/^\(;.*\)*$/d'\'' -e '\''s/^\(EXPORTS\|LIBRARY\)\([ ].*\)*$/DEF/p'\'' -e q $export_symbols`" ; then + cp $export_symbols $output_objdir/$soname.def; + else + echo EXPORTS > $output_objdir/$soname.def; + cat $export_symbols >> $output_objdir/$soname.def; + fi~ + $CC -shared $output_objdir/$soname.def $libobjs $deplibs $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' + else + ld_shlibs=no + fi + ;; + + haiku*) + archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + link_all_deplibs=yes + ;; + + os2*) + hardcode_libdir_flag_spec='-L$libdir' + hardcode_minus_L=yes + allow_undefined_flag=unsupported + shrext_cmds=.dll + archive_cmds='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ + $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ + $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ + $ECHO EXPORTS >> $output_objdir/$libname.def~ + emxexp $libobjs | $SED /"_DLL_InitTerm"/d >> $output_objdir/$libname.def~ + $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ + emximp -o $lib $output_objdir/$libname.def' + archive_expsym_cmds='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ + $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ + $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ + $ECHO EXPORTS >> $output_objdir/$libname.def~ + prefix_cmds="$SED"~ + if test EXPORTS = "`$SED 1q $export_symbols`"; then + prefix_cmds="$prefix_cmds -e 1d"; + fi~ + prefix_cmds="$prefix_cmds -e \"s/^\(.*\)$/_\1/g\""~ + cat $export_symbols | $prefix_cmds >> $output_objdir/$libname.def~ + $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ + emximp -o $lib $output_objdir/$libname.def' + old_archive_From_new_cmds='emximp -o $output_objdir/${libname}_dll.a $output_objdir/$libname.def' + enable_shared_with_static_runtimes=yes + file_list_spec='@' + ;; + + interix[3-9]*) + hardcode_direct=no + hardcode_shlibpath_var=no + hardcode_libdir_flag_spec='$wl-rpath,$libdir' + export_dynamic_flag_spec='$wl-E' + # Hack: On Interix 3.x, we cannot compile PIC because of a broken gcc. + # Instead, shared libraries are loaded at an image base (0x10000000 by + # default) and relocated if they conflict, which is a slow very memory + # consuming and fragmenting process. To avoid this, we pick a random, + # 256 KiB-aligned image base between 0x50000000 and 0x6FFC0000 at link + # time. Moving up from 0x10000000 also allows more sbrk(2) space. + archive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \* 262144 + 1342177280` -o $lib' + archive_expsym_cmds='$SED "s|^|_|" $export_symbols >$output_objdir/$soname.expsym~$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--retain-symbols-file,$output_objdir/$soname.expsym $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \* 262144 + 1342177280` -o $lib' + ;; + + gnu* | linux* | tpf* | k*bsd*-gnu | kopensolaris*-gnu) + tmp_diet=no + if test linux-dietlibc = "$host_os"; then + case $cc_basename in + diet\ *) tmp_diet=yes;; # linux-dietlibc with static linking (!diet-dyn) + esac + fi + if $LD --help 2>&1 | $EGREP ': supported targets:.* elf' > /dev/null \ + && test no = "$tmp_diet" + then + tmp_addflag=' $pic_flag' + tmp_sharedflag='-shared' + case $cc_basename,$host_cpu in + pgcc*) # Portland Group C compiler + whole_archive_flag_spec='$wl--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' + tmp_addflag=' $pic_flag' + ;; + pgf77* | pgf90* | pgf95* | pgfortran*) + # Portland Group f77 and f90 compilers + whole_archive_flag_spec='$wl--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' + tmp_addflag=' $pic_flag -Mnomain' ;; + ecc*,ia64* | icc*,ia64*) # Intel C compiler on ia64 + tmp_addflag=' -i_dynamic' ;; + efc*,ia64* | ifort*,ia64*) # Intel Fortran compiler on ia64 + tmp_addflag=' -i_dynamic -nofor_main' ;; + ifc* | ifort*) # Intel Fortran compiler + tmp_addflag=' -nofor_main' ;; + lf95*) # Lahey Fortran 8.1 + whole_archive_flag_spec= + tmp_sharedflag='--shared' ;; + nagfor*) # NAGFOR 5.3 + tmp_sharedflag='-Wl,-shared' ;; + xl[cC]* | bgxl[cC]* | mpixl[cC]*) # IBM XL C 8.0 on PPC (deal with xlf below) + tmp_sharedflag='-qmkshrobj' + tmp_addflag= ;; + nvcc*) # Cuda Compiler Driver 2.2 + whole_archive_flag_spec='$wl--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' + compiler_needs_object=yes + ;; + esac + case `$CC -V 2>&1 | $SED 5q` in + *Sun\ C*) # Sun C 5.9 + whole_archive_flag_spec='$wl--whole-archive`new_convenience=; for conv in $convenience\"\"; do test -z \"$conv\" || new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' + compiler_needs_object=yes + tmp_sharedflag='-G' ;; + *Sun\ F*) # Sun Fortran 8.3 + tmp_sharedflag='-G' ;; + esac + archive_cmds='$CC '"$tmp_sharedflag""$tmp_addflag"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + + if test yes = "$supports_anon_versioning"; then + archive_expsym_cmds='echo "{ global:" > $output_objdir/$libname.ver~ + cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $output_objdir/$libname.ver~ + echo "local: *; };" >> $output_objdir/$libname.ver~ + $CC '"$tmp_sharedflag""$tmp_addflag"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-version-script $wl$output_objdir/$libname.ver -o $lib' + fi + + case $cc_basename in + tcc*) + export_dynamic_flag_spec='-rdynamic' + ;; + xlf* | bgf* | bgxlf* | mpixlf*) + # IBM XL Fortran 10.1 on PPC cannot create shared libs itself + whole_archive_flag_spec='--whole-archive$convenience --no-whole-archive' + hardcode_libdir_flag_spec='$wl-rpath $wl$libdir' + archive_cmds='$LD -shared $libobjs $deplibs $linker_flags -soname $soname -o $lib' + if test yes = "$supports_anon_versioning"; then + archive_expsym_cmds='echo "{ global:" > $output_objdir/$libname.ver~ + cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $output_objdir/$libname.ver~ + echo "local: *; };" >> $output_objdir/$libname.ver~ + $LD -shared $libobjs $deplibs $linker_flags -soname $soname -version-script $output_objdir/$libname.ver -o $lib' + fi + ;; + esac + else + ld_shlibs=no + fi + ;; + + netbsd*) + if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then + archive_cmds='$LD -Bshareable $libobjs $deplibs $linker_flags -o $lib' + wlarc= + else + archive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + archive_expsym_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' + fi + ;; + + solaris*) + if $LD -v 2>&1 | $GREP 'BFD 2\.8' > /dev/null; then + ld_shlibs=no + cat <<_LT_EOF 1>&2 + +*** Warning: The releases 2.8.* of the GNU linker cannot reliably +*** create shared libraries on Solaris systems. Therefore, libtool +*** is disabling shared libraries support. We urge you to upgrade GNU +*** binutils to release 2.9.1 or newer. Another option is to modify +*** your PATH or compiler configuration so that the native linker is +*** used, and then restart. + +_LT_EOF + elif $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then + archive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + archive_expsym_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' + else + ld_shlibs=no + fi + ;; + + sysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX*) + case `$LD -v 2>&1` in + *\ [01].* | *\ 2.[0-9].* | *\ 2.1[0-5].*) + ld_shlibs=no + cat <<_LT_EOF 1>&2 + +*** Warning: Releases of the GNU linker prior to 2.16.91.0.3 cannot +*** reliably create shared libraries on SCO systems. Therefore, libtool +*** is disabling shared libraries support. We urge you to upgrade GNU +*** binutils to release 2.16.91.0.3 or newer. Another option is to modify +*** your PATH or compiler configuration so that the native linker is +*** used, and then restart. + +_LT_EOF + ;; + *) + # For security reasons, it is highly recommended that you always + # use absolute paths for naming shared libraries, and exclude the + # DT_RUNPATH tag from executables and libraries. But doing so + # requires that you compile everything twice, which is a pain. + if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then + hardcode_libdir_flag_spec='$wl-rpath $wl$libdir' + archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + archive_expsym_cmds='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' + else + ld_shlibs=no + fi + ;; + esac + ;; + + sunos4*) + archive_cmds='$LD -assert pure-text -Bshareable -o $lib $libobjs $deplibs $linker_flags' + wlarc= + hardcode_direct=yes + hardcode_shlibpath_var=no + ;; + + *) + if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then + archive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + archive_expsym_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' + else + ld_shlibs=no + fi + ;; + esac + + if test no = "$ld_shlibs"; then + runpath_var= + hardcode_libdir_flag_spec= + export_dynamic_flag_spec= + whole_archive_flag_spec= + fi + else + # PORTME fill in a description of your system's linker (not GNU ld) + case $host_os in + aix3*) + allow_undefined_flag=unsupported + always_export_symbols=yes + archive_expsym_cmds='$LD -o $output_objdir/$soname $libobjs $deplibs $linker_flags -bE:$export_symbols -T512 -H512 -bM:SRE~$AR $AR_FLAGS $lib $output_objdir/$soname' + # Note: this linker hardcodes the directories in LIBPATH if there + # are no directories specified by -L. + hardcode_minus_L=yes + if test yes = "$GCC" && test -z "$lt_prog_compiler_static"; then + # Neither direct hardcoding nor static linking is supported with a + # broken collect2. + hardcode_direct=unsupported + fi + ;; + + aix[4-9]*) + if test ia64 = "$host_cpu"; then + # On IA64, the linker does run time linking by default, so we don't + # have to do anything special. + aix_use_runtimelinking=no + exp_sym_flag='-Bexport' + no_entry_flag= + else + # If we're using GNU nm, then we don't want the "-C" option. + # -C means demangle to GNU nm, but means don't demangle to AIX nm. + # Without the "-l" option, or with the "-B" option, AIX nm treats + # weak defined symbols like other global defined symbols, whereas + # GNU nm marks them as "W". + # While the 'weak' keyword is ignored in the Export File, we need + # it in the Import File for the 'aix-soname' feature, so we have + # to replace the "-B" option with "-P" for AIX nm. + if $NM -V 2>&1 | $GREP 'GNU' > /dev/null; then + export_symbols_cmds='$NM -Bpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B") || (\$ 2 == "W")) && (substr(\$ 3,1,1) != ".")) { if (\$ 2 == "W") { print \$ 3 " weak" } else { print \$ 3 } } }'\'' | sort -u > $export_symbols' + else + export_symbols_cmds='`func_echo_all $NM | $SED -e '\''s/B\([^B]*\)$/P\1/'\''` -PCpgl $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B") || (\$ 2 == "L") || (\$ 2 == "W") || (\$ 2 == "V") || (\$ 2 == "Z")) && (substr(\$ 1,1,1) != ".")) { if ((\$ 2 == "W") || (\$ 2 == "V") || (\$ 2 == "Z")) { print \$ 1 " weak" } else { print \$ 1 } } }'\'' | sort -u > $export_symbols' + fi + aix_use_runtimelinking=no + + # Test if we are trying to use run time linking or normal + # AIX style linking. If -brtl is somewhere in LDFLAGS, we + # have runtime linking enabled, and use it for executables. + # For shared libraries, we enable/disable runtime linking + # depending on the kind of the shared library created - + # when "with_aix_soname,aix_use_runtimelinking" is: + # "aix,no" lib.a(lib.so.V) shared, rtl:no, for executables + # "aix,yes" lib.so shared, rtl:yes, for executables + # lib.a static archive + # "both,no" lib.so.V(shr.o) shared, rtl:yes + # lib.a(lib.so.V) shared, rtl:no, for executables + # "both,yes" lib.so.V(shr.o) shared, rtl:yes, for executables + # lib.a(lib.so.V) shared, rtl:no + # "svr4,*" lib.so.V(shr.o) shared, rtl:yes, for executables + # lib.a static archive + case $host_os in aix4.[23]|aix4.[23].*|aix[5-9]*) + for ld_flag in $LDFLAGS; do + if (test x-brtl = "x$ld_flag" || test x-Wl,-brtl = "x$ld_flag"); then + aix_use_runtimelinking=yes + break + fi + done + if test svr4,no = "$with_aix_soname,$aix_use_runtimelinking"; then + # With aix-soname=svr4, we create the lib.so.V shared archives only, + # so we don't have lib.a shared libs to link our executables. + # We have to force runtime linking in this case. + aix_use_runtimelinking=yes + LDFLAGS="$LDFLAGS -Wl,-brtl" + fi + ;; + esac + + exp_sym_flag='-bexport' + no_entry_flag='-bnoentry' + fi + + # When large executables or shared objects are built, AIX ld can + # have problems creating the table of contents. If linking a library + # or program results in "error TOC overflow" add -mminimal-toc to + # CXXFLAGS/CFLAGS for g++/gcc. In the cases where that is not + # enough to fix the problem, add -Wl,-bbigtoc to LDFLAGS. + + archive_cmds='' + hardcode_direct=yes + hardcode_direct_absolute=yes + hardcode_libdir_separator=':' + link_all_deplibs=yes + file_list_spec='$wl-f,' + case $with_aix_soname,$aix_use_runtimelinking in + aix,*) ;; # traditional, no import file + svr4,* | *,yes) # use import file + # The Import File defines what to hardcode. + hardcode_direct=no + hardcode_direct_absolute=no + ;; + esac + + if test yes = "$GCC"; then + case $host_os in aix4.[012]|aix4.[012].*) + # We only want to do this on AIX 4.2 and lower, the check + # below for broken collect2 doesn't work under 4.3+ + collect2name=`$CC -print-prog-name=collect2` + if test -f "$collect2name" && + strings "$collect2name" | $GREP resolve_lib_name >/dev/null + then + # We have reworked collect2 + : + else + # We have old collect2 + hardcode_direct=unsupported + # It fails to find uninstalled libraries when the uninstalled + # path is not listed in the libpath. Setting hardcode_minus_L + # to unsupported forces relinking + hardcode_minus_L=yes + hardcode_libdir_flag_spec='-L$libdir' + hardcode_libdir_separator= + fi + ;; + esac + shared_flag='-shared' + if test yes = "$aix_use_runtimelinking"; then + shared_flag="$shared_flag "'$wl-G' + fi + # Need to ensure runtime linking is disabled for the traditional + # shared library, or the linker may eventually find shared libraries + # /with/ Import File - we do not want to mix them. + shared_flag_aix='-shared' + shared_flag_svr4='-shared $wl-G' + else + # not using gcc + if test ia64 = "$host_cpu"; then + # VisualAge C++, Version 5.5 for AIX 5L for IA-64, Beta 3 Release + # chokes on -Wl,-G. The following line is correct: + shared_flag='-G' + else + if test yes = "$aix_use_runtimelinking"; then + shared_flag='$wl-G' + else + shared_flag='$wl-bM:SRE' + fi + shared_flag_aix='$wl-bM:SRE' + shared_flag_svr4='$wl-G' + fi + fi + + export_dynamic_flag_spec='$wl-bexpall' + # It seems that -bexpall does not export symbols beginning with + # underscore (_), so it is better to generate a list of symbols to export. + always_export_symbols=yes + if test aix,yes = "$with_aix_soname,$aix_use_runtimelinking"; then + # Warning - without using the other runtime loading flags (-brtl), + # -berok will link without error, but may produce a broken library. + allow_undefined_flag='-berok' + # Determine the default libpath from the value encoded in an + # empty executable. + if test set = "${lt_cv_aix_libpath+set}"; then + aix_libpath=$lt_cv_aix_libpath +else + if test ${lt_cv_aix_libpath_+y} +then : + printf %s "(cached) " >&6 +else $as_nop + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +int +main (void) +{ + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + + lt_aix_libpath_sed=' + /Import File Strings/,/^$/ { + /^0/ { + s/^0 *\([^ ]*\) *$/\1/ + p + } + }' + lt_cv_aix_libpath_=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` + # Check for a 64-bit object if we didn't find anything. + if test -z "$lt_cv_aix_libpath_"; then + lt_cv_aix_libpath_=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` + fi +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext + if test -z "$lt_cv_aix_libpath_"; then + lt_cv_aix_libpath_=/usr/lib:/lib + fi + +fi + + aix_libpath=$lt_cv_aix_libpath_ +fi + + hardcode_libdir_flag_spec='$wl-blibpath:$libdir:'"$aix_libpath" + archive_expsym_cmds='$CC -o $output_objdir/$soname $libobjs $deplibs $wl'$no_entry_flag' $compiler_flags `if test -n "$allow_undefined_flag"; then func_echo_all "$wl$allow_undefined_flag"; else :; fi` $wl'$exp_sym_flag:\$export_symbols' '$shared_flag + else + if test ia64 = "$host_cpu"; then + hardcode_libdir_flag_spec='$wl-R $libdir:/usr/lib:/lib' + allow_undefined_flag="-z nodefs" + archive_expsym_cmds="\$CC $shared_flag"' -o $output_objdir/$soname $libobjs $deplibs '"\$wl$no_entry_flag"' $compiler_flags $wl$allow_undefined_flag '"\$wl$exp_sym_flag:\$export_symbols" + else + # Determine the default libpath from the value encoded in an + # empty executable. + if test set = "${lt_cv_aix_libpath+set}"; then + aix_libpath=$lt_cv_aix_libpath +else + if test ${lt_cv_aix_libpath_+y} +then : + printf %s "(cached) " >&6 +else $as_nop + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +int +main (void) +{ + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + + lt_aix_libpath_sed=' + /Import File Strings/,/^$/ { + /^0/ { + s/^0 *\([^ ]*\) *$/\1/ + p + } + }' + lt_cv_aix_libpath_=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` + # Check for a 64-bit object if we didn't find anything. + if test -z "$lt_cv_aix_libpath_"; then + lt_cv_aix_libpath_=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` + fi +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext + if test -z "$lt_cv_aix_libpath_"; then + lt_cv_aix_libpath_=/usr/lib:/lib + fi + +fi + + aix_libpath=$lt_cv_aix_libpath_ +fi + + hardcode_libdir_flag_spec='$wl-blibpath:$libdir:'"$aix_libpath" + # Warning - without using the other run time loading flags, + # -berok will link without error, but may produce a broken library. + no_undefined_flag=' $wl-bernotok' + allow_undefined_flag=' $wl-berok' + if test yes = "$with_gnu_ld"; then + # We only use this code for GNU lds that support --whole-archive. + whole_archive_flag_spec='$wl--whole-archive$convenience $wl--no-whole-archive' + else + # Exported symbols can be pulled into shared objects from archives + whole_archive_flag_spec='$convenience' + fi + archive_cmds_need_lc=yes + archive_expsym_cmds='$RM -r $output_objdir/$realname.d~$MKDIR $output_objdir/$realname.d' + # -brtl affects multiple linker settings, -berok does not and is overridden later + compiler_flags_filtered='`func_echo_all "$compiler_flags " | $SED -e "s%-brtl\\([, ]\\)%-berok\\1%g"`' + if test svr4 != "$with_aix_soname"; then + # This is similar to how AIX traditionally builds its shared libraries. + archive_expsym_cmds="$archive_expsym_cmds"'~$CC '$shared_flag_aix' -o $output_objdir/$realname.d/$soname $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$AR $AR_FLAGS $output_objdir/$libname$release.a $output_objdir/$realname.d/$soname' + fi + if test aix != "$with_aix_soname"; then + archive_expsym_cmds="$archive_expsym_cmds"'~$CC '$shared_flag_svr4' -o $output_objdir/$realname.d/$shared_archive_member_spec.o $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$STRIP -e $output_objdir/$realname.d/$shared_archive_member_spec.o~( func_echo_all "#! $soname($shared_archive_member_spec.o)"; if test shr_64 = "$shared_archive_member_spec"; then func_echo_all "# 64"; else func_echo_all "# 32"; fi; cat $export_symbols ) > $output_objdir/$realname.d/$shared_archive_member_spec.imp~$AR $AR_FLAGS $output_objdir/$soname $output_objdir/$realname.d/$shared_archive_member_spec.o $output_objdir/$realname.d/$shared_archive_member_spec.imp' + else + # used by -dlpreopen to get the symbols + archive_expsym_cmds="$archive_expsym_cmds"'~$MV $output_objdir/$realname.d/$soname $output_objdir' + fi + archive_expsym_cmds="$archive_expsym_cmds"'~$RM -r $output_objdir/$realname.d' + fi + fi + ;; + + amigaos*) + case $host_cpu in + powerpc) + # see comment about AmigaOS4 .so support + archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' + archive_expsym_cmds='' + ;; + m68k) + archive_cmds='$RM $output_objdir/a2ixlibrary.data~$ECHO "#define NAME $libname" > $output_objdir/a2ixlibrary.data~$ECHO "#define LIBRARY_ID 1" >> $output_objdir/a2ixlibrary.data~$ECHO "#define VERSION $major" >> $output_objdir/a2ixlibrary.data~$ECHO "#define REVISION $revision" >> $output_objdir/a2ixlibrary.data~$AR $AR_FLAGS $lib $libobjs~$RANLIB $lib~(cd $output_objdir && a2ixlibrary -32)' + hardcode_libdir_flag_spec='-L$libdir' + hardcode_minus_L=yes + ;; + esac + ;; + + bsdi[45]*) + export_dynamic_flag_spec=-rdynamic + ;; + + cygwin* | mingw* | pw32* | cegcc*) + # When not using gcc, we currently assume that we are using + # Microsoft Visual C++ or Intel C++ Compiler. + # hardcode_libdir_flag_spec is actually meaningless, as there is + # no search path for DLLs. + case $cc_basename in + cl* | icl*) + # Native MSVC or ICC + hardcode_libdir_flag_spec=' ' + allow_undefined_flag=unsupported + always_export_symbols=yes + file_list_spec='@' + # Tell ltmain to make .lib files, not .a files. + libext=lib + # Tell ltmain to make .dll files, not .so files. + shrext_cmds=.dll + # FIXME: Setting linknames here is a bad hack. + archive_cmds='$CC -o $output_objdir/$soname $libobjs $compiler_flags $deplibs -Wl,-DLL,-IMPLIB:"$tool_output_objdir$libname.dll.lib"~linknames=' + archive_expsym_cmds='if test DEF = "`$SED -n -e '\''s/^[ ]*//'\'' -e '\''/^\(;.*\)*$/d'\'' -e '\''s/^\(EXPORTS\|LIBRARY\)\([ ].*\)*$/DEF/p'\'' -e q $export_symbols`" ; then + cp "$export_symbols" "$output_objdir/$soname.def"; + echo "$tool_output_objdir$soname.def" > "$output_objdir/$soname.exp"; + else + $SED -e '\''s/^/-link -EXPORT:/'\'' < $export_symbols > $output_objdir/$soname.exp; + fi~ + $CC -o $tool_output_objdir$soname $libobjs $compiler_flags $deplibs "@$tool_output_objdir$soname.exp" -Wl,-DLL,-IMPLIB:"$tool_output_objdir$libname.dll.lib"~ + linknames=' + # The linker will not automatically build a static lib if we build a DLL. + # _LT_TAGVAR(old_archive_from_new_cmds, )='true' + enable_shared_with_static_runtimes=yes + exclude_expsyms='_NULL_IMPORT_DESCRIPTOR|_IMPORT_DESCRIPTOR_.*' + export_symbols_cmds='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[BCDGRS][ ]/s/.*[ ]\([^ ]*\)/\1,DATA/'\'' | $SED -e '\''/^[AITW][ ]/s/.*[ ]//'\'' | sort | uniq > $export_symbols' + # Don't use ranlib + old_postinstall_cmds='chmod 644 $oldlib' + postlink_cmds='lt_outputfile="@OUTPUT@"~ + lt_tool_outputfile="@TOOL_OUTPUT@"~ + case $lt_outputfile in + *.exe|*.EXE) ;; + *) + lt_outputfile=$lt_outputfile.exe + lt_tool_outputfile=$lt_tool_outputfile.exe + ;; + esac~ + if test : != "$MANIFEST_TOOL" && test -f "$lt_outputfile.manifest"; then + $MANIFEST_TOOL -manifest "$lt_tool_outputfile.manifest" -outputresource:"$lt_tool_outputfile" || exit 1; + $RM "$lt_outputfile.manifest"; + fi' + ;; + *) + # Assume MSVC and ICC wrapper + hardcode_libdir_flag_spec=' ' + allow_undefined_flag=unsupported + # Tell ltmain to make .lib files, not .a files. + libext=lib + # Tell ltmain to make .dll files, not .so files. + shrext_cmds=.dll + # FIXME: Setting linknames here is a bad hack. + archive_cmds='$CC -o $lib $libobjs $compiler_flags `func_echo_all "$deplibs" | $SED '\''s/ -lc$//'\''` -link -dll~linknames=' + # The linker will automatically build a .lib file if we build a DLL. + old_archive_from_new_cmds='true' + # FIXME: Should let the user specify the lib program. + old_archive_cmds='lib -OUT:$oldlib$oldobjs$old_deplibs' + enable_shared_with_static_runtimes=yes + ;; + esac + ;; + + darwin* | rhapsody*) + + + archive_cmds_need_lc=no + hardcode_direct=no + hardcode_automatic=yes + hardcode_shlibpath_var=unsupported + if test yes = "$lt_cv_ld_force_load"; then + whole_archive_flag_spec='`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience $wl-force_load,$conv\"; done; func_echo_all \"$new_convenience\"`' + + else + whole_archive_flag_spec='' + fi + link_all_deplibs=yes + allow_undefined_flag=$_lt_dar_allow_undefined + case $cc_basename in + ifort*|nagfor*) _lt_dar_can_shared=yes ;; + *) _lt_dar_can_shared=$GCC ;; + esac + if test yes = "$_lt_dar_can_shared"; then + output_verbose_link_cmd=func_echo_all + archive_cmds="\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$libobjs \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring $_lt_dar_single_mod$_lt_dsymutil" + module_cmds="\$CC \$allow_undefined_flag -o \$lib -bundle \$libobjs \$deplibs \$compiler_flags$_lt_dsymutil" + archive_expsym_cmds="$SED 's|^|_|' < \$export_symbols > \$output_objdir/\$libname-symbols.expsym~\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$libobjs \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring $_lt_dar_single_mod$_lt_dar_export_syms$_lt_dsymutil" + module_expsym_cmds="$SED -e 's|^|_|' < \$export_symbols > \$output_objdir/\$libname-symbols.expsym~\$CC \$allow_undefined_flag -o \$lib -bundle \$libobjs \$deplibs \$compiler_flags$_lt_dar_export_syms$_lt_dsymutil" + + else + ld_shlibs=no + fi + + ;; + + dgux*) + archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' + hardcode_libdir_flag_spec='-L$libdir' + hardcode_shlibpath_var=no + ;; + + # FreeBSD 2.2.[012] allows us to include c++rt0.o to get C++ constructor + # support. Future versions do this automatically, but an explicit c++rt0.o + # does not break anything, and helps significantly (at the cost of a little + # extra space). + freebsd2.2*) + archive_cmds='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags /usr/lib/c++rt0.o' + hardcode_libdir_flag_spec='-R$libdir' + hardcode_direct=yes + hardcode_shlibpath_var=no + ;; + + # Unfortunately, older versions of FreeBSD 2 do not have this feature. + freebsd2.*) + archive_cmds='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags' + hardcode_direct=yes + hardcode_minus_L=yes + hardcode_shlibpath_var=no + ;; + + # FreeBSD 3 and greater uses gcc -shared to do shared libraries. + freebsd* | dragonfly* | midnightbsd*) + archive_cmds='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' + hardcode_libdir_flag_spec='-R$libdir' + hardcode_direct=yes + hardcode_shlibpath_var=no + ;; + + hpux9*) + if test yes = "$GCC"; then + archive_cmds='$RM $output_objdir/$soname~$CC -shared $pic_flag $wl+b $wl$install_libdir -o $output_objdir/$soname $libobjs $deplibs $compiler_flags~test "x$output_objdir/$soname" = "x$lib" || mv $output_objdir/$soname $lib' + else + archive_cmds='$RM $output_objdir/$soname~$LD -b +b $install_libdir -o $output_objdir/$soname $libobjs $deplibs $linker_flags~test "x$output_objdir/$soname" = "x$lib" || mv $output_objdir/$soname $lib' + fi + hardcode_libdir_flag_spec='$wl+b $wl$libdir' + hardcode_libdir_separator=: + hardcode_direct=yes + + # hardcode_minus_L: Not really in the search PATH, + # but as the default location of the library. + hardcode_minus_L=yes + export_dynamic_flag_spec='$wl-E' + ;; + + hpux10*) + if test yes,no = "$GCC,$with_gnu_ld"; then + archive_cmds='$CC -shared $pic_flag $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags' + else + archive_cmds='$LD -b +h $soname +b $install_libdir -o $lib $libobjs $deplibs $linker_flags' + fi + if test no = "$with_gnu_ld"; then + hardcode_libdir_flag_spec='$wl+b $wl$libdir' + hardcode_libdir_separator=: + hardcode_direct=yes + hardcode_direct_absolute=yes + export_dynamic_flag_spec='$wl-E' + # hardcode_minus_L: Not really in the search PATH, + # but as the default location of the library. + hardcode_minus_L=yes + fi + ;; + + hpux11*) + if test yes,no = "$GCC,$with_gnu_ld"; then + case $host_cpu in + hppa*64*) + archive_cmds='$CC -shared $wl+h $wl$soname -o $lib $libobjs $deplibs $compiler_flags' + ;; + ia64*) + archive_cmds='$CC -shared $pic_flag $wl+h $wl$soname $wl+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags' + ;; + *) + archive_cmds='$CC -shared $pic_flag $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags' + ;; + esac + else + case $host_cpu in + hppa*64*) + archive_cmds='$CC -b $wl+h $wl$soname -o $lib $libobjs $deplibs $compiler_flags' + ;; + ia64*) + archive_cmds='$CC -b $wl+h $wl$soname $wl+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags' + ;; + *) + + # Older versions of the 11.00 compiler do not understand -b yet + # (HP92453-01 A.11.01.20 doesn't, HP92453-01 B.11.X.35175-35176.GP does) + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking if $CC understands -b" >&5 +printf %s "checking if $CC understands -b... " >&6; } +if test ${lt_cv_prog_compiler__b+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_prog_compiler__b=no + save_LDFLAGS=$LDFLAGS + LDFLAGS="$LDFLAGS -b" + echo "$lt_simple_link_test_code" > conftest.$ac_ext + if (eval $ac_link 2>conftest.err) && test -s conftest$ac_exeext; then + # The linker can only warn and ignore the option if not recognized + # So say no if there are warnings + if test -s conftest.err; then + # Append any errors to the config.log. + cat conftest.err 1>&5 + $ECHO "$_lt_linker_boilerplate" | $SED '/^$/d' > conftest.exp + $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 + if diff conftest.exp conftest.er2 >/dev/null; then + lt_cv_prog_compiler__b=yes + fi + else + lt_cv_prog_compiler__b=yes + fi + fi + $RM -r conftest* + LDFLAGS=$save_LDFLAGS + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler__b" >&5 +printf "%s\n" "$lt_cv_prog_compiler__b" >&6; } + +if test yes = "$lt_cv_prog_compiler__b"; then + archive_cmds='$CC -b $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags' +else + archive_cmds='$LD -b +h $soname +b $install_libdir -o $lib $libobjs $deplibs $linker_flags' +fi + + ;; + esac + fi + if test no = "$with_gnu_ld"; then + hardcode_libdir_flag_spec='$wl+b $wl$libdir' + hardcode_libdir_separator=: + + case $host_cpu in + hppa*64*|ia64*) + hardcode_direct=no + hardcode_shlibpath_var=no + ;; + *) + hardcode_direct=yes + hardcode_direct_absolute=yes + export_dynamic_flag_spec='$wl-E' + + # hardcode_minus_L: Not really in the search PATH, + # but as the default location of the library. + hardcode_minus_L=yes + ;; + esac + fi + ;; + + irix5* | irix6* | nonstopux*) + if test yes = "$GCC"; then + archive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' + # Try to use the -exported_symbol ld option, if it does not + # work, assume that -exports_file does not work either and + # implicitly export all symbols. + # This should be the same for all languages, so no per-tag cache variable. + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether the $host_os linker accepts -exported_symbol" >&5 +printf %s "checking whether the $host_os linker accepts -exported_symbol... " >&6; } +if test ${lt_cv_irix_exported_symbol+y} +then : + printf %s "(cached) " >&6 +else $as_nop + save_LDFLAGS=$LDFLAGS + LDFLAGS="$LDFLAGS -shared $wl-exported_symbol ${wl}foo $wl-update_registry $wl/dev/null" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +int foo (void) { return 0; } +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + lt_cv_irix_exported_symbol=yes +else $as_nop + lt_cv_irix_exported_symbol=no +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext + LDFLAGS=$save_LDFLAGS +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_irix_exported_symbol" >&5 +printf "%s\n" "$lt_cv_irix_exported_symbol" >&6; } + if test yes = "$lt_cv_irix_exported_symbol"; then + archive_expsym_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations $wl-exports_file $wl$export_symbols -o $lib' + fi + else + archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' + archive_expsym_cmds='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -exports_file $export_symbols -o $lib' + fi + archive_cmds_need_lc='no' + hardcode_libdir_flag_spec='$wl-rpath $wl$libdir' + hardcode_libdir_separator=: + inherit_rpath=yes + link_all_deplibs=yes + ;; + + linux*) + case $cc_basename in + tcc*) + # Fabrice Bellard et al's Tiny C Compiler + ld_shlibs=yes + archive_cmds='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' + ;; + esac + ;; + + netbsd*) + if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then + archive_cmds='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags' # a.out + else + archive_cmds='$LD -shared -o $lib $libobjs $deplibs $linker_flags' # ELF + fi + hardcode_libdir_flag_spec='-R$libdir' + hardcode_direct=yes + hardcode_shlibpath_var=no + ;; + + newsos6) + archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' + hardcode_direct=yes + hardcode_libdir_flag_spec='$wl-rpath $wl$libdir' + hardcode_libdir_separator=: + hardcode_shlibpath_var=no + ;; + + *nto* | *qnx*) + ;; + + openbsd* | bitrig*) + if test -f /usr/libexec/ld.so; then + hardcode_direct=yes + hardcode_shlibpath_var=no + hardcode_direct_absolute=yes + if test -z "`echo __ELF__ | $CC -E - | $GREP __ELF__`"; then + archive_cmds='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' + archive_expsym_cmds='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags $wl-retain-symbols-file,$export_symbols' + hardcode_libdir_flag_spec='$wl-rpath,$libdir' + export_dynamic_flag_spec='$wl-E' + else + archive_cmds='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' + hardcode_libdir_flag_spec='$wl-rpath,$libdir' + fi + else + ld_shlibs=no + fi + ;; + + os2*) + hardcode_libdir_flag_spec='-L$libdir' + hardcode_minus_L=yes + allow_undefined_flag=unsupported + shrext_cmds=.dll + archive_cmds='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ + $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ + $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ + $ECHO EXPORTS >> $output_objdir/$libname.def~ + emxexp $libobjs | $SED /"_DLL_InitTerm"/d >> $output_objdir/$libname.def~ + $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ + emximp -o $lib $output_objdir/$libname.def' + archive_expsym_cmds='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ + $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ + $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ + $ECHO EXPORTS >> $output_objdir/$libname.def~ + prefix_cmds="$SED"~ + if test EXPORTS = "`$SED 1q $export_symbols`"; then + prefix_cmds="$prefix_cmds -e 1d"; + fi~ + prefix_cmds="$prefix_cmds -e \"s/^\(.*\)$/_\1/g\""~ + cat $export_symbols | $prefix_cmds >> $output_objdir/$libname.def~ + $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ + emximp -o $lib $output_objdir/$libname.def' + old_archive_From_new_cmds='emximp -o $output_objdir/${libname}_dll.a $output_objdir/$libname.def' + enable_shared_with_static_runtimes=yes + file_list_spec='@' + ;; + + osf3*) + if test yes = "$GCC"; then + allow_undefined_flag=' $wl-expect_unresolved $wl\*' + archive_cmds='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' + else + allow_undefined_flag=' -expect_unresolved \*' + archive_cmds='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' + fi + archive_cmds_need_lc='no' + hardcode_libdir_flag_spec='$wl-rpath $wl$libdir' + hardcode_libdir_separator=: + ;; + + osf4* | osf5*) # as osf3* with the addition of -msym flag + if test yes = "$GCC"; then + allow_undefined_flag=' $wl-expect_unresolved $wl\*' + archive_cmds='$CC -shared$allow_undefined_flag $pic_flag $libobjs $deplibs $compiler_flags $wl-msym $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' + hardcode_libdir_flag_spec='$wl-rpath $wl$libdir' + else + allow_undefined_flag=' -expect_unresolved \*' + archive_cmds='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags -msym -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' + archive_expsym_cmds='for i in `cat $export_symbols`; do printf "%s %s\\n" -exported_symbol "\$i" >> $lib.exp; done; printf "%s\\n" "-hidden">> $lib.exp~ + $CC -shared$allow_undefined_flag $wl-input $wl$lib.exp $compiler_flags $libobjs $deplibs -soname $soname `test -n "$verstring" && $ECHO "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib~$RM $lib.exp' + + # Both c and cxx compiler support -rpath directly + hardcode_libdir_flag_spec='-rpath $libdir' + fi + archive_cmds_need_lc='no' + hardcode_libdir_separator=: + ;; + + solaris*) + no_undefined_flag=' -z defs' + if test yes = "$GCC"; then + wlarc='$wl' + archive_cmds='$CC -shared $pic_flag $wl-z ${wl}text $wl-h $wl$soname -o $lib $libobjs $deplibs $compiler_flags' + archive_expsym_cmds='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ + $CC -shared $pic_flag $wl-z ${wl}text $wl-M $wl$lib.exp $wl-h $wl$soname -o $lib $libobjs $deplibs $compiler_flags~$RM $lib.exp' + else + case `$CC -V 2>&1` in + *"Compilers 5.0"*) + wlarc='' + archive_cmds='$LD -G$allow_undefined_flag -h $soname -o $lib $libobjs $deplibs $linker_flags' + archive_expsym_cmds='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ + $LD -G$allow_undefined_flag -M $lib.exp -h $soname -o $lib $libobjs $deplibs $linker_flags~$RM $lib.exp' + ;; + *) + wlarc='$wl' + archive_cmds='$CC -G$allow_undefined_flag -h $soname -o $lib $libobjs $deplibs $compiler_flags' + archive_expsym_cmds='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ + $CC -G$allow_undefined_flag -M $lib.exp -h $soname -o $lib $libobjs $deplibs $compiler_flags~$RM $lib.exp' + ;; + esac + fi + hardcode_libdir_flag_spec='-R$libdir' + hardcode_shlibpath_var=no + case $host_os in + solaris2.[0-5] | solaris2.[0-5].*) ;; + *) + # The compiler driver will combine and reorder linker options, + # but understands '-z linker_flag'. GCC discards it without '$wl', + # but is careful enough not to reorder. + # Supported since Solaris 2.6 (maybe 2.5.1?) + if test yes = "$GCC"; then + whole_archive_flag_spec='$wl-z ${wl}allextract$convenience $wl-z ${wl}defaultextract' + else + whole_archive_flag_spec='-z allextract$convenience -z defaultextract' + fi + ;; + esac + link_all_deplibs=yes + ;; + + sunos4*) + if test sequent = "$host_vendor"; then + # Use $CC to link under sequent, because it throws in some extra .o + # files that make .init and .fini sections work. + archive_cmds='$CC -G $wl-h $soname -o $lib $libobjs $deplibs $compiler_flags' + else + archive_cmds='$LD -assert pure-text -Bstatic -o $lib $libobjs $deplibs $linker_flags' + fi + hardcode_libdir_flag_spec='-L$libdir' + hardcode_direct=yes + hardcode_minus_L=yes + hardcode_shlibpath_var=no + ;; + + sysv4) + case $host_vendor in + sni) + archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' + hardcode_direct=yes # is this really true??? + ;; + siemens) + ## LD is ld it makes a PLAMLIB + ## CC just makes a GrossModule. + archive_cmds='$LD -G -o $lib $libobjs $deplibs $linker_flags' + reload_cmds='$CC -r -o $output$reload_objs' + hardcode_direct=no + ;; + motorola) + archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' + hardcode_direct=no #Motorola manual says yes, but my tests say they lie + ;; + esac + runpath_var='LD_RUN_PATH' + hardcode_shlibpath_var=no + ;; + + sysv4.3*) + archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' + hardcode_shlibpath_var=no + export_dynamic_flag_spec='-Bexport' + ;; + + sysv4*MP*) + if test -d /usr/nec; then + archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' + hardcode_shlibpath_var=no + runpath_var=LD_RUN_PATH + hardcode_runpath_var=yes + ld_shlibs=yes + fi + ;; + + sysv4*uw2* | sysv5OpenUNIX* | sysv5UnixWare7.[01].[10]* | unixware7* | sco3.2v5.0.[024]*) + no_undefined_flag='$wl-z,text' + archive_cmds_need_lc=no + hardcode_shlibpath_var=no + runpath_var='LD_RUN_PATH' + + if test yes = "$GCC"; then + archive_cmds='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + archive_expsym_cmds='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + else + archive_cmds='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + archive_expsym_cmds='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + fi + ;; + + sysv5* | sco3.2v5* | sco5v6*) + # Note: We CANNOT use -z defs as we might desire, because we do not + # link with -lc, and that would cause any symbols used from libc to + # always be unresolved, which means just about no library would + # ever link correctly. If we're not using GNU ld we use -z text + # though, which does catch some bad symbols but isn't as heavy-handed + # as -z defs. + no_undefined_flag='$wl-z,text' + allow_undefined_flag='$wl-z,nodefs' + archive_cmds_need_lc=no + hardcode_shlibpath_var=no + hardcode_libdir_flag_spec='$wl-R,$libdir' + hardcode_libdir_separator=':' + link_all_deplibs=yes + export_dynamic_flag_spec='$wl-Bexport' + runpath_var='LD_RUN_PATH' + + if test yes = "$GCC"; then + archive_cmds='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + archive_expsym_cmds='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + else + archive_cmds='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + archive_expsym_cmds='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' + fi + ;; + + uts4*) + archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' + hardcode_libdir_flag_spec='-L$libdir' + hardcode_shlibpath_var=no + ;; + + *) + ld_shlibs=no + ;; + esac + + if test sni = "$host_vendor"; then + case $host in + sysv4 | sysv4.2uw2* | sysv4.3* | sysv5*) + export_dynamic_flag_spec='$wl-Blargedynsym' + ;; + esac + fi + fi + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ld_shlibs" >&5 +printf "%s\n" "$ld_shlibs" >&6; } +test no = "$ld_shlibs" && can_build_shared=no + +with_gnu_ld=$with_gnu_ld + + + + + + + + + + + + + + + +# +# Do we need to explicitly link libc? +# +case "x$archive_cmds_need_lc" in +x|xyes) + # Assume -lc should be added + archive_cmds_need_lc=yes + + if test yes,yes = "$GCC,$enable_shared"; then + case $archive_cmds in + *'~'*) + # FIXME: we may have to deal with multi-command sequences. + ;; + '$CC '*) + # Test whether the compiler implicitly links with -lc since on some + # systems, -lgcc has to come before -lc. If gcc already passes -lc + # to ld, don't add -lc before -lgcc. + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether -lc should be explicitly linked in" >&5 +printf %s "checking whether -lc should be explicitly linked in... " >&6; } +if test ${lt_cv_archive_cmds_need_lc+y} +then : + printf %s "(cached) " >&6 +else $as_nop + $RM conftest* + echo "$lt_simple_compile_test_code" > conftest.$ac_ext + + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 + (eval $ac_compile) 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } 2>conftest.err; then + soname=conftest + lib=conftest + libobjs=conftest.$ac_objext + deplibs= + wl=$lt_prog_compiler_wl + pic_flag=$lt_prog_compiler_pic + compiler_flags=-v + linker_flags=-v + verstring= + output_objdir=. + libname=conftest + lt_save_allow_undefined_flag=$allow_undefined_flag + allow_undefined_flag= + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$archive_cmds 2\>\&1 \| $GREP \" -lc \" \>/dev/null 2\>\&1\""; } >&5 + (eval $archive_cmds 2\>\&1 \| $GREP \" -lc \" \>/dev/null 2\>\&1) 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } + then + lt_cv_archive_cmds_need_lc=no + else + lt_cv_archive_cmds_need_lc=yes + fi + allow_undefined_flag=$lt_save_allow_undefined_flag + else + cat conftest.err 1>&5 + fi + $RM conftest* + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_archive_cmds_need_lc" >&5 +printf "%s\n" "$lt_cv_archive_cmds_need_lc" >&6; } + archive_cmds_need_lc=$lt_cv_archive_cmds_need_lc + ;; + esac + fi + ;; +esac + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking dynamic linker characteristics" >&5 +printf %s "checking dynamic linker characteristics... " >&6; } + +if test yes = "$GCC"; then + case $host_os in + darwin*) lt_awk_arg='/^libraries:/,/LR/' ;; + *) lt_awk_arg='/^libraries:/' ;; + esac + case $host_os in + mingw* | cegcc*) lt_sed_strip_eq='s|=\([A-Za-z]:\)|\1|g' ;; + *) lt_sed_strip_eq='s|=/|/|g' ;; + esac + lt_search_path_spec=`$CC -print-search-dirs | awk $lt_awk_arg | $SED -e "s/^libraries://" -e $lt_sed_strip_eq` + case $lt_search_path_spec in + *\;*) + # if the path contains ";" then we assume it to be the separator + # otherwise default to the standard path separator (i.e. ":") - it is + # assumed that no part of a normal pathname contains ";" but that should + # okay in the real world where ";" in dirpaths is itself problematic. + lt_search_path_spec=`$ECHO "$lt_search_path_spec" | $SED 's/;/ /g'` + ;; + *) + lt_search_path_spec=`$ECHO "$lt_search_path_spec" | $SED "s/$PATH_SEPARATOR/ /g"` + ;; + esac + # Ok, now we have the path, separated by spaces, we can step through it + # and add multilib dir if necessary... + lt_tmp_lt_search_path_spec= + lt_multi_os_dir=/`$CC $CPPFLAGS $CFLAGS $LDFLAGS -print-multi-os-directory 2>/dev/null` + # ...but if some path component already ends with the multilib dir we assume + # that all is fine and trust -print-search-dirs as is (GCC 4.2? or newer). + case "$lt_multi_os_dir; $lt_search_path_spec " in + "/; "* | "/.; "* | "/./; "* | *"$lt_multi_os_dir "* | *"$lt_multi_os_dir/ "*) + lt_multi_os_dir= + ;; + esac + for lt_sys_path in $lt_search_path_spec; do + if test -d "$lt_sys_path$lt_multi_os_dir"; then + lt_tmp_lt_search_path_spec="$lt_tmp_lt_search_path_spec $lt_sys_path$lt_multi_os_dir" + elif test -n "$lt_multi_os_dir"; then + test -d "$lt_sys_path" && \ + lt_tmp_lt_search_path_spec="$lt_tmp_lt_search_path_spec $lt_sys_path" + fi + done + lt_search_path_spec=`$ECHO "$lt_tmp_lt_search_path_spec" | awk ' +BEGIN {RS = " "; FS = "/|\n";} { + lt_foo = ""; + lt_count = 0; + for (lt_i = NF; lt_i > 0; lt_i--) { + if ($lt_i != "" && $lt_i != ".") { + if ($lt_i == "..") { + lt_count++; + } else { + if (lt_count == 0) { + lt_foo = "/" $lt_i lt_foo; + } else { + lt_count--; + } + } + } + } + if (lt_foo != "") { lt_freq[lt_foo]++; } + if (lt_freq[lt_foo] == 1) { print lt_foo; } +}'` + # AWK program above erroneously prepends '/' to C:/dos/paths + # for these hosts. + case $host_os in + mingw* | cegcc*) lt_search_path_spec=`$ECHO "$lt_search_path_spec" |\ + $SED 's|/\([A-Za-z]:\)|\1|g'` ;; + esac + sys_lib_search_path_spec=`$ECHO "$lt_search_path_spec" | $lt_NL2SP` +else + sys_lib_search_path_spec="/lib /usr/lib /usr/local/lib" +fi +library_names_spec= +libname_spec='lib$name' +soname_spec= +shrext_cmds=.so +postinstall_cmds= +postuninstall_cmds= +finish_cmds= +finish_eval= +shlibpath_var= +shlibpath_overrides_runpath=unknown +version_type=none +dynamic_linker="$host_os ld.so" +sys_lib_dlsearch_path_spec="/lib /usr/lib" +need_lib_prefix=unknown +hardcode_into_libs=no + +# when you set need_version to no, make sure it does not cause -set_version +# flags to be left without arguments +need_version=unknown + + + +case $host_os in +aix3*) + version_type=linux # correct to gnu/linux during the next big refactor + library_names_spec='$libname$release$shared_ext$versuffix $libname.a' + shlibpath_var=LIBPATH + + # AIX 3 has no versioning support, so we append a major version to the name. + soname_spec='$libname$release$shared_ext$major' + ;; + +aix[4-9]*) + version_type=linux # correct to gnu/linux during the next big refactor + need_lib_prefix=no + need_version=no + hardcode_into_libs=yes + if test ia64 = "$host_cpu"; then + # AIX 5 supports IA64 + library_names_spec='$libname$release$shared_ext$major $libname$release$shared_ext$versuffix $libname$shared_ext' + shlibpath_var=LD_LIBRARY_PATH + else + # With GCC up to 2.95.x, collect2 would create an import file + # for dependence libraries. The import file would start with + # the line '#! .'. This would cause the generated library to + # depend on '.', always an invalid library. This was fixed in + # development snapshots of GCC prior to 3.0. + case $host_os in + aix4 | aix4.[01] | aix4.[01].*) + if { echo '#if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 97)' + echo ' yes ' + echo '#endif'; } | $CC -E - | $GREP yes > /dev/null; then + : + else + can_build_shared=no + fi + ;; + esac + # Using Import Files as archive members, it is possible to support + # filename-based versioning of shared library archives on AIX. While + # this would work for both with and without runtime linking, it will + # prevent static linking of such archives. So we do filename-based + # shared library versioning with .so extension only, which is used + # when both runtime linking and shared linking is enabled. + # Unfortunately, runtime linking may impact performance, so we do + # not want this to be the default eventually. Also, we use the + # versioned .so libs for executables only if there is the -brtl + # linker flag in LDFLAGS as well, or --with-aix-soname=svr4 only. + # To allow for filename-based versioning support, we need to create + # libNAME.so.V as an archive file, containing: + # *) an Import File, referring to the versioned filename of the + # archive as well as the shared archive member, telling the + # bitwidth (32 or 64) of that shared object, and providing the + # list of exported symbols of that shared object, eventually + # decorated with the 'weak' keyword + # *) the shared object with the F_LOADONLY flag set, to really avoid + # it being seen by the linker. + # At run time we better use the real file rather than another symlink, + # but for link time we create the symlink libNAME.so -> libNAME.so.V + + case $with_aix_soname,$aix_use_runtimelinking in + # AIX (on Power*) has no versioning support, so currently we cannot hardcode correct + # soname into executable. Probably we can add versioning support to + # collect2, so additional links can be useful in future. + aix,yes) # traditional libtool + dynamic_linker='AIX unversionable lib.so' + # If using run time linking (on AIX 4.2 or later) use lib.so + # instead of lib.a to let people know that these are not + # typical AIX shared libraries. + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + ;; + aix,no) # traditional AIX only + dynamic_linker='AIX lib.a(lib.so.V)' + # We preserve .a as extension for shared libraries through AIX4.2 + # and later when we are not doing run time linking. + library_names_spec='$libname$release.a $libname.a' + soname_spec='$libname$release$shared_ext$major' + ;; + svr4,*) # full svr4 only + dynamic_linker="AIX lib.so.V($shared_archive_member_spec.o)" + library_names_spec='$libname$release$shared_ext$major $libname$shared_ext' + # We do not specify a path in Import Files, so LIBPATH fires. + shlibpath_overrides_runpath=yes + ;; + *,yes) # both, prefer svr4 + dynamic_linker="AIX lib.so.V($shared_archive_member_spec.o), lib.a(lib.so.V)" + library_names_spec='$libname$release$shared_ext$major $libname$shared_ext' + # unpreferred sharedlib libNAME.a needs extra handling + postinstall_cmds='test -n "$linkname" || linkname="$realname"~func_stripname "" ".so" "$linkname"~$install_shared_prog "$dir/$func_stripname_result.$libext" "$destdir/$func_stripname_result.$libext"~test -z "$tstripme" || test -z "$striplib" || $striplib "$destdir/$func_stripname_result.$libext"' + postuninstall_cmds='for n in $library_names $old_library; do :; done~func_stripname "" ".so" "$n"~test "$func_stripname_result" = "$n" || func_append rmfiles " $odir/$func_stripname_result.$libext"' + # We do not specify a path in Import Files, so LIBPATH fires. + shlibpath_overrides_runpath=yes + ;; + *,no) # both, prefer aix + dynamic_linker="AIX lib.a(lib.so.V), lib.so.V($shared_archive_member_spec.o)" + library_names_spec='$libname$release.a $libname.a' + soname_spec='$libname$release$shared_ext$major' + # unpreferred sharedlib libNAME.so.V and symlink libNAME.so need extra handling + postinstall_cmds='test -z "$dlname" || $install_shared_prog $dir/$dlname $destdir/$dlname~test -z "$tstripme" || test -z "$striplib" || $striplib $destdir/$dlname~test -n "$linkname" || linkname=$realname~func_stripname "" ".a" "$linkname"~(cd "$destdir" && $LN_S -f $dlname $func_stripname_result.so)' + postuninstall_cmds='test -z "$dlname" || func_append rmfiles " $odir/$dlname"~for n in $old_library $library_names; do :; done~func_stripname "" ".a" "$n"~func_append rmfiles " $odir/$func_stripname_result.so"' + ;; + esac + shlibpath_var=LIBPATH + fi + ;; + +amigaos*) + case $host_cpu in + powerpc) + # Since July 2007 AmigaOS4 officially supports .so libraries. + # When compiling the executable, add -use-dynld -Lsobjs: to the compileline. + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + ;; + m68k) + library_names_spec='$libname.ixlibrary $libname.a' + # Create ${libname}_ixlibrary.a entries in /sys/libs. + finish_eval='for lib in `ls $libdir/*.ixlibrary 2>/dev/null`; do libname=`func_echo_all "$lib" | $SED '\''s%^.*/\([^/]*\)\.ixlibrary$%\1%'\''`; $RM /sys/libs/${libname}_ixlibrary.a; $show "cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a"; cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a || exit 1; done' + ;; + esac + ;; + +beos*) + library_names_spec='$libname$shared_ext' + dynamic_linker="$host_os ld.so" + shlibpath_var=LIBRARY_PATH + ;; + +bsdi[45]*) + version_type=linux # correct to gnu/linux during the next big refactor + need_version=no + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + finish_cmds='PATH="\$PATH:/sbin" ldconfig $libdir' + shlibpath_var=LD_LIBRARY_PATH + sys_lib_search_path_spec="/shlib /usr/lib /usr/X11/lib /usr/contrib/lib /lib /usr/local/lib" + sys_lib_dlsearch_path_spec="/shlib /usr/lib /usr/local/lib" + # the default ld.so.conf also contains /usr/contrib/lib and + # /usr/X11R6/lib (/usr/X11 is a link to /usr/X11R6), but let us allow + # libtool to hard-code these into programs + ;; + +cygwin* | mingw* | pw32* | cegcc*) + version_type=windows + shrext_cmds=.dll + need_version=no + need_lib_prefix=no + + case $GCC,$cc_basename in + yes,*) + # gcc + library_names_spec='$libname.dll.a' + # DLL is installed to $(libdir)/../bin by postinstall_cmds + postinstall_cmds='base_file=`basename \$file`~ + dlpath=`$SHELL 2>&1 -c '\''. $dir/'\''\$base_file'\''i; echo \$dlname'\''`~ + dldir=$destdir/`dirname \$dlpath`~ + test -d \$dldir || mkdir -p \$dldir~ + $install_prog $dir/$dlname \$dldir/$dlname~ + chmod a+x \$dldir/$dlname~ + if test -n '\''$stripme'\'' && test -n '\''$striplib'\''; then + eval '\''$striplib \$dldir/$dlname'\'' || exit \$?; + fi' + postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\''. $file; echo \$dlname'\''`~ + dlpath=$dir/\$dldll~ + $RM \$dlpath' + shlibpath_overrides_runpath=yes + + case $host_os in + cygwin*) + # Cygwin DLLs use 'cyg' prefix rather than 'lib' + soname_spec='`echo $libname | $SED -e 's/^lib/cyg/'``echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext' + + sys_lib_search_path_spec="$sys_lib_search_path_spec /usr/lib/w32api" + ;; + mingw* | cegcc*) + # MinGW DLLs use traditional 'lib' prefix + soname_spec='$libname`echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext' + ;; + pw32*) + # pw32 DLLs use 'pw' prefix rather than 'lib' + library_names_spec='`echo $libname | $SED -e 's/^lib/pw/'``echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext' + ;; + esac + dynamic_linker='Win32 ld.exe' + ;; + + *,cl* | *,icl*) + # Native MSVC or ICC + libname_spec='$name' + soname_spec='$libname`echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext' + library_names_spec='$libname.dll.lib' + + case $build_os in + mingw*) + sys_lib_search_path_spec= + lt_save_ifs=$IFS + IFS=';' + for lt_path in $LIB + do + IFS=$lt_save_ifs + # Let DOS variable expansion print the short 8.3 style file name. + lt_path=`cd "$lt_path" 2>/dev/null && cmd //C "for %i in (".") do @echo %~si"` + sys_lib_search_path_spec="$sys_lib_search_path_spec $lt_path" + done + IFS=$lt_save_ifs + # Convert to MSYS style. + sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e 's|\\\\|/|g' -e 's| \\([a-zA-Z]\\):| /\\1|g' -e 's|^ ||'` + ;; + cygwin*) + # Convert to unix form, then to dos form, then back to unix form + # but this time dos style (no spaces!) so that the unix form looks + # like /cygdrive/c/PROGRA~1:/cygdr... + sys_lib_search_path_spec=`cygpath --path --unix "$LIB"` + sys_lib_search_path_spec=`cygpath --path --dos "$sys_lib_search_path_spec" 2>/dev/null` + sys_lib_search_path_spec=`cygpath --path --unix "$sys_lib_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` + ;; + *) + sys_lib_search_path_spec=$LIB + if $ECHO "$sys_lib_search_path_spec" | $GREP ';[c-zC-Z]:/' >/dev/null; then + # It is most probably a Windows format PATH. + sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e 's/;/ /g'` + else + sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` + fi + # FIXME: find the short name or the path components, as spaces are + # common. (e.g. "Program Files" -> "PROGRA~1") + ;; + esac + + # DLL is installed to $(libdir)/../bin by postinstall_cmds + postinstall_cmds='base_file=`basename \$file`~ + dlpath=`$SHELL 2>&1 -c '\''. $dir/'\''\$base_file'\''i; echo \$dlname'\''`~ + dldir=$destdir/`dirname \$dlpath`~ + test -d \$dldir || mkdir -p \$dldir~ + $install_prog $dir/$dlname \$dldir/$dlname' + postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\''. $file; echo \$dlname'\''`~ + dlpath=$dir/\$dldll~ + $RM \$dlpath' + shlibpath_overrides_runpath=yes + dynamic_linker='Win32 link.exe' + ;; + + *) + # Assume MSVC and ICC wrapper + library_names_spec='$libname`echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext $libname.lib' + dynamic_linker='Win32 ld.exe' + ;; + esac + # FIXME: first we should search . and the directory the executable is in + shlibpath_var=PATH + ;; + +darwin* | rhapsody*) + dynamic_linker="$host_os dyld" + version_type=darwin + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$major$shared_ext $libname$shared_ext' + soname_spec='$libname$release$major$shared_ext' + shlibpath_overrides_runpath=yes + shlibpath_var=DYLD_LIBRARY_PATH + shrext_cmds='`test .$module = .yes && echo .so || echo .dylib`' + + sys_lib_search_path_spec="$sys_lib_search_path_spec /usr/local/lib" + sys_lib_dlsearch_path_spec='/usr/local/lib /lib /usr/lib' + ;; + +dgux*) + version_type=linux # correct to gnu/linux during the next big refactor + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + shlibpath_var=LD_LIBRARY_PATH + ;; + +freebsd* | dragonfly* | midnightbsd*) + # DragonFly does not have aout. When/if they implement a new + # versioning mechanism, adjust this. + if test -x /usr/bin/objformat; then + objformat=`/usr/bin/objformat` + else + case $host_os in + freebsd[23].*) objformat=aout ;; + *) objformat=elf ;; + esac + fi + version_type=freebsd-$objformat + case $version_type in + freebsd-elf*) + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + need_version=no + need_lib_prefix=no + ;; + freebsd-*) + library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix' + need_version=yes + ;; + esac + shlibpath_var=LD_LIBRARY_PATH + case $host_os in + freebsd2.*) + shlibpath_overrides_runpath=yes + ;; + freebsd3.[01]* | freebsdelf3.[01]*) + shlibpath_overrides_runpath=yes + hardcode_into_libs=yes + ;; + freebsd3.[2-9]* | freebsdelf3.[2-9]* | \ + freebsd4.[0-5] | freebsdelf4.[0-5] | freebsd4.1.1 | freebsdelf4.1.1) + shlibpath_overrides_runpath=no + hardcode_into_libs=yes + ;; + *) # from 4.6 on, and DragonFly + shlibpath_overrides_runpath=yes + hardcode_into_libs=yes + ;; + esac + ;; + +haiku*) + version_type=linux # correct to gnu/linux during the next big refactor + need_lib_prefix=no + need_version=no + dynamic_linker="$host_os runtime_loader" + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + shlibpath_var=LIBRARY_PATH + shlibpath_overrides_runpath=no + sys_lib_dlsearch_path_spec='/boot/home/config/lib /boot/common/lib /boot/system/lib' + hardcode_into_libs=yes + ;; + +hpux9* | hpux10* | hpux11*) + # Give a soname corresponding to the major version so that dld.sl refuses to + # link against other versions. + version_type=sunos + need_lib_prefix=no + need_version=no + case $host_cpu in + ia64*) + shrext_cmds='.so' + hardcode_into_libs=yes + dynamic_linker="$host_os dld.so" + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=yes # Unless +noenvvar is specified. + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + if test 32 = "$HPUX_IA64_MODE"; then + sys_lib_search_path_spec="/usr/lib/hpux32 /usr/local/lib/hpux32 /usr/local/lib" + sys_lib_dlsearch_path_spec=/usr/lib/hpux32 + else + sys_lib_search_path_spec="/usr/lib/hpux64 /usr/local/lib/hpux64" + sys_lib_dlsearch_path_spec=/usr/lib/hpux64 + fi + ;; + hppa*64*) + shrext_cmds='.sl' + hardcode_into_libs=yes + dynamic_linker="$host_os dld.sl" + shlibpath_var=LD_LIBRARY_PATH # How should we handle SHLIB_PATH + shlibpath_overrides_runpath=yes # Unless +noenvvar is specified. + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + sys_lib_search_path_spec="/usr/lib/pa20_64 /usr/ccs/lib/pa20_64" + sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec + ;; + *) + shrext_cmds='.sl' + dynamic_linker="$host_os dld.sl" + shlibpath_var=SHLIB_PATH + shlibpath_overrides_runpath=no # +s is required to enable SHLIB_PATH + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + ;; + esac + # HP-UX runs *really* slowly unless shared libraries are mode 555, ... + postinstall_cmds='chmod 555 $lib' + # or fails outright, so override atomically: + install_override_mode=555 + ;; + +interix[3-9]*) + version_type=linux # correct to gnu/linux during the next big refactor + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + dynamic_linker='Interix 3.x ld.so.1 (PE, like ELF)' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=no + hardcode_into_libs=yes + ;; + +irix5* | irix6* | nonstopux*) + case $host_os in + nonstopux*) version_type=nonstopux ;; + *) + if test yes = "$lt_cv_prog_gnu_ld"; then + version_type=linux # correct to gnu/linux during the next big refactor + else + version_type=irix + fi ;; + esac + need_lib_prefix=no + need_version=no + soname_spec='$libname$release$shared_ext$major' + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$release$shared_ext $libname$shared_ext' + case $host_os in + irix5* | nonstopux*) + libsuff= shlibsuff= + ;; + *) + case $LD in # libtool.m4 will add one of these switches to LD + *-32|*"-32 "|*-melf32bsmip|*"-melf32bsmip ") + libsuff= shlibsuff= libmagic=32-bit;; + *-n32|*"-n32 "|*-melf32bmipn32|*"-melf32bmipn32 ") + libsuff=32 shlibsuff=N32 libmagic=N32;; + *-64|*"-64 "|*-melf64bmip|*"-melf64bmip ") + libsuff=64 shlibsuff=64 libmagic=64-bit;; + *) libsuff= shlibsuff= libmagic=never-match;; + esac + ;; + esac + shlibpath_var=LD_LIBRARY${shlibsuff}_PATH + shlibpath_overrides_runpath=no + sys_lib_search_path_spec="/usr/lib$libsuff /lib$libsuff /usr/local/lib$libsuff" + sys_lib_dlsearch_path_spec="/usr/lib$libsuff /lib$libsuff" + hardcode_into_libs=yes + ;; + +# No shared lib support for Linux oldld, aout, or coff. +linux*oldld* | linux*aout* | linux*coff*) + dynamic_linker=no + ;; + +linux*android*) + version_type=none # Android doesn't support versioned libraries. + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$shared_ext' + soname_spec='$libname$release$shared_ext' + finish_cmds= + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=yes + + # This implies no fast_install, which is unacceptable. + # Some rework will be needed to allow for fast_install + # before this can be enabled. + hardcode_into_libs=yes + + dynamic_linker='Android linker' + # Don't embed -rpath directories since the linker doesn't support them. + hardcode_libdir_flag_spec='-L$libdir' + ;; + +# This must be glibc/ELF. +linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) + version_type=linux # correct to gnu/linux during the next big refactor + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + finish_cmds='PATH="\$PATH:/sbin" ldconfig -n $libdir' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=no + + # Some binutils ld are patched to set DT_RUNPATH + if test ${lt_cv_shlibpath_overrides_runpath+y} +then : + printf %s "(cached) " >&6 +else $as_nop + lt_cv_shlibpath_overrides_runpath=no + save_LDFLAGS=$LDFLAGS + save_libdir=$libdir + eval "libdir=/foo; wl=\"$lt_prog_compiler_wl\"; \ + LDFLAGS=\"\$LDFLAGS $hardcode_libdir_flag_spec\"" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +int +main (void) +{ + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + if ($OBJDUMP -p conftest$ac_exeext) 2>/dev/null | grep "RUNPATH.*$libdir" >/dev/null +then : + lt_cv_shlibpath_overrides_runpath=yes +fi +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext + LDFLAGS=$save_LDFLAGS + libdir=$save_libdir + +fi + + shlibpath_overrides_runpath=$lt_cv_shlibpath_overrides_runpath + + # This implies no fast_install, which is unacceptable. + # Some rework will be needed to allow for fast_install + # before this can be enabled. + hardcode_into_libs=yes + + # Ideally, we could use ldconfig to report *all* directores which are + # searched for libraries, however this is still not possible. Aside from not + # being certain /sbin/ldconfig is available, command + # 'ldconfig -N -X -v | grep ^/' on 64bit Fedora does not report /usr/lib64, + # even though it is searched at run-time. Try to do the best guess by + # appending ld.so.conf contents (and includes) to the search path. + if test -f /etc/ld.so.conf; then + lt_ld_extra=`awk '/^include / { system(sprintf("cd /etc; cat %s 2>/dev/null", \$2)); skip = 1; } { if (!skip) print \$0; skip = 0; }' < /etc/ld.so.conf | $SED -e 's/#.*//;/^[ ]*hwcap[ ]/d;s/[:, ]/ /g;s/=[^=]*$//;s/=[^= ]* / /g;s/"//g;/^$/d' | tr '\n' ' '` + sys_lib_dlsearch_path_spec="/lib /usr/lib $lt_ld_extra" + fi + + # We used to test for /lib/ld.so.1 and disable shared libraries on + # powerpc, because MkLinux only supported shared libraries with the + # GNU dynamic linker. Since this was broken with cross compilers, + # most powerpc-linux boxes support dynamic linking these days and + # people can always --disable-shared, the test was removed, and we + # assume the GNU/Linux dynamic linker is in use. + dynamic_linker='GNU/Linux ld.so' + ;; + +netbsd*) + version_type=sunos + need_lib_prefix=no + need_version=no + if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then + library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix' + finish_cmds='PATH="\$PATH:/sbin" ldconfig -m $libdir' + dynamic_linker='NetBSD (a.out) ld.so' + else + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + dynamic_linker='NetBSD ld.elf_so' + fi + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=yes + hardcode_into_libs=yes + ;; + +newsos6) + version_type=linux # correct to gnu/linux during the next big refactor + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=yes + ;; + +*nto* | *qnx*) + version_type=qnx + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=no + hardcode_into_libs=yes + dynamic_linker='ldqnx.so' + ;; + +openbsd* | bitrig*) + version_type=sunos + sys_lib_dlsearch_path_spec=/usr/lib + need_lib_prefix=no + if test -z "`echo __ELF__ | $CC -E - | $GREP __ELF__`"; then + need_version=no + else + need_version=yes + fi + library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix' + finish_cmds='PATH="\$PATH:/sbin" ldconfig -m $libdir' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=yes + ;; + +os2*) + libname_spec='$name' + version_type=windows + shrext_cmds=.dll + need_version=no + need_lib_prefix=no + # OS/2 can only load a DLL with a base name of 8 characters or less. + soname_spec='`test -n "$os2dllname" && libname="$os2dllname"; + v=$($ECHO $release$versuffix | tr -d .-); + n=$($ECHO $libname | cut -b -$((8 - ${#v})) | tr . _); + $ECHO $n$v`$shared_ext' + library_names_spec='${libname}_dll.$libext' + dynamic_linker='OS/2 ld.exe' + shlibpath_var=BEGINLIBPATH + sys_lib_search_path_spec="/lib /usr/lib /usr/local/lib" + sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec + postinstall_cmds='base_file=`basename \$file`~ + dlpath=`$SHELL 2>&1 -c '\''. $dir/'\''\$base_file'\''i; $ECHO \$dlname'\''`~ + dldir=$destdir/`dirname \$dlpath`~ + test -d \$dldir || mkdir -p \$dldir~ + $install_prog $dir/$dlname \$dldir/$dlname~ + chmod a+x \$dldir/$dlname~ + if test -n '\''$stripme'\'' && test -n '\''$striplib'\''; then + eval '\''$striplib \$dldir/$dlname'\'' || exit \$?; + fi' + postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\''. $file; $ECHO \$dlname'\''`~ + dlpath=$dir/\$dldll~ + $RM \$dlpath' + ;; + +osf3* | osf4* | osf5*) + version_type=osf + need_lib_prefix=no + need_version=no + soname_spec='$libname$release$shared_ext$major' + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + shlibpath_var=LD_LIBRARY_PATH + sys_lib_search_path_spec="/usr/shlib /usr/ccs/lib /usr/lib/cmplrs/cc /usr/lib /usr/local/lib /var/shlib" + sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec + ;; + +rdos*) + dynamic_linker=no + ;; + +solaris*) + version_type=linux # correct to gnu/linux during the next big refactor + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=yes + hardcode_into_libs=yes + # ldd complains unless libraries are executable + postinstall_cmds='chmod +x $lib' + ;; + +sunos4*) + version_type=sunos + library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix' + finish_cmds='PATH="\$PATH:/usr/etc" ldconfig $libdir' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=yes + if test yes = "$with_gnu_ld"; then + need_lib_prefix=no + fi + need_version=yes + ;; + +sysv4 | sysv4.3*) + version_type=linux # correct to gnu/linux during the next big refactor + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + shlibpath_var=LD_LIBRARY_PATH + case $host_vendor in + sni) + shlibpath_overrides_runpath=no + need_lib_prefix=no + runpath_var=LD_RUN_PATH + ;; + siemens) + need_lib_prefix=no + ;; + motorola) + need_lib_prefix=no + need_version=no + shlibpath_overrides_runpath=no + sys_lib_search_path_spec='/lib /usr/lib /usr/ccs/lib' + ;; + esac + ;; + +sysv4*MP*) + if test -d /usr/nec; then + version_type=linux # correct to gnu/linux during the next big refactor + library_names_spec='$libname$shared_ext.$versuffix $libname$shared_ext.$major $libname$shared_ext' + soname_spec='$libname$shared_ext.$major' + shlibpath_var=LD_LIBRARY_PATH + fi + ;; + +sysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX* | sysv4*uw2*) + version_type=sco + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=yes + hardcode_into_libs=yes + if test yes = "$with_gnu_ld"; then + sys_lib_search_path_spec='/usr/local/lib /usr/gnu/lib /usr/ccs/lib /usr/lib /lib' + else + sys_lib_search_path_spec='/usr/ccs/lib /usr/lib' + case $host_os in + sco3.2v5*) + sys_lib_search_path_spec="$sys_lib_search_path_spec /lib" + ;; + esac + fi + sys_lib_dlsearch_path_spec='/usr/lib' + ;; + +tpf*) + # TPF is a cross-target only. Preferred cross-host = GNU/Linux. + version_type=linux # correct to gnu/linux during the next big refactor + need_lib_prefix=no + need_version=no + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=no + hardcode_into_libs=yes + ;; + +uts4*) + version_type=linux # correct to gnu/linux during the next big refactor + library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' + soname_spec='$libname$release$shared_ext$major' + shlibpath_var=LD_LIBRARY_PATH + ;; + +*) + dynamic_linker=no + ;; +esac +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $dynamic_linker" >&5 +printf "%s\n" "$dynamic_linker" >&6; } +test no = "$dynamic_linker" && can_build_shared=no + +variables_saved_for_relink="PATH $shlibpath_var $runpath_var" +if test yes = "$GCC"; then + variables_saved_for_relink="$variables_saved_for_relink GCC_EXEC_PREFIX COMPILER_PATH LIBRARY_PATH" +fi + +if test set = "${lt_cv_sys_lib_search_path_spec+set}"; then + sys_lib_search_path_spec=$lt_cv_sys_lib_search_path_spec +fi + +if test set = "${lt_cv_sys_lib_dlsearch_path_spec+set}"; then + sys_lib_dlsearch_path_spec=$lt_cv_sys_lib_dlsearch_path_spec +fi + +# remember unaugmented sys_lib_dlsearch_path content for libtool script decls... +configure_time_dlsearch_path=$sys_lib_dlsearch_path_spec + +# ... but it needs LT_SYS_LIBRARY_PATH munging for other configure-time code +func_munge_path_list sys_lib_dlsearch_path_spec "$LT_SYS_LIBRARY_PATH" + +# to be used as default LT_SYS_LIBRARY_PATH value in generated libtool +configure_time_lt_sys_library_path=$LT_SYS_LIBRARY_PATH + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking how to hardcode library paths into programs" >&5 +printf %s "checking how to hardcode library paths into programs... " >&6; } +hardcode_action= +if test -n "$hardcode_libdir_flag_spec" || + test -n "$runpath_var" || + test yes = "$hardcode_automatic"; then + + # We can hardcode non-existent directories. + if test no != "$hardcode_direct" && + # If the only mechanism to avoid hardcoding is shlibpath_var, we + # have to relink, otherwise we might link with an installed library + # when we should be linking with a yet-to-be-installed one + ## test no != "$_LT_TAGVAR(hardcode_shlibpath_var, )" && + test no != "$hardcode_minus_L"; then + # Linking always hardcodes the temporary library directory. + hardcode_action=relink + else + # We can link without hardcoding, and we can hardcode nonexisting dirs. + hardcode_action=immediate + fi +else + # We cannot hardcode anything, or else we can only hardcode existing + # directories. + hardcode_action=unsupported +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $hardcode_action" >&5 +printf "%s\n" "$hardcode_action" >&6; } + +if test relink = "$hardcode_action" || + test yes = "$inherit_rpath"; then + # Fast installation is not supported + enable_fast_install=no +elif test yes = "$shlibpath_overrides_runpath" || + test no = "$enable_shared"; then + # Fast installation is not necessary + enable_fast_install=needless +fi + + + + + + + if test yes != "$enable_dlopen"; then + enable_dlopen=unknown + enable_dlopen_self=unknown + enable_dlopen_self_static=unknown +else + lt_cv_dlopen=no + lt_cv_dlopen_libs= + + case $host_os in + beos*) + lt_cv_dlopen=load_add_on + lt_cv_dlopen_libs= + lt_cv_dlopen_self=yes + ;; + + mingw* | pw32* | cegcc*) + lt_cv_dlopen=LoadLibrary + lt_cv_dlopen_libs= + ;; + + cygwin*) + lt_cv_dlopen=dlopen + lt_cv_dlopen_libs= + ;; + + darwin*) + # if libdl is installed we need to link against it + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for dlopen in -ldl" >&5 +printf %s "checking for dlopen in -ldl... " >&6; } +if test ${ac_cv_lib_dl_dlopen+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ac_check_lib_save_LIBS=$LIBS +LIBS="-ldl $LIBS" +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +/* Override any GCC internal prototype to avoid an error. + Use char because int might match the return type of a GCC + builtin and then its argument prototype would still apply. */ +char dlopen (); +int +main (void) +{ +return dlopen (); + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + ac_cv_lib_dl_dlopen=yes +else $as_nop + ac_cv_lib_dl_dlopen=no +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext +LIBS=$ac_check_lib_save_LIBS +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dl_dlopen" >&5 +printf "%s\n" "$ac_cv_lib_dl_dlopen" >&6; } +if test "x$ac_cv_lib_dl_dlopen" = xyes +then : + lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-ldl +else $as_nop + + lt_cv_dlopen=dyld + lt_cv_dlopen_libs= + lt_cv_dlopen_self=yes + +fi + + ;; + + tpf*) + # Don't try to run any link tests for TPF. We know it's impossible + # because TPF is a cross-compiler, and we know how we open DSOs. + lt_cv_dlopen=dlopen + lt_cv_dlopen_libs= + lt_cv_dlopen_self=no + ;; + + *) + ac_fn_c_check_func "$LINENO" "shl_load" "ac_cv_func_shl_load" +if test "x$ac_cv_func_shl_load" = xyes +then : + lt_cv_dlopen=shl_load +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for shl_load in -ldld" >&5 +printf %s "checking for shl_load in -ldld... " >&6; } +if test ${ac_cv_lib_dld_shl_load+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ac_check_lib_save_LIBS=$LIBS +LIBS="-ldld $LIBS" +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +/* Override any GCC internal prototype to avoid an error. + Use char because int might match the return type of a GCC + builtin and then its argument prototype would still apply. */ +char shl_load (); +int +main (void) +{ +return shl_load (); + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + ac_cv_lib_dld_shl_load=yes +else $as_nop + ac_cv_lib_dld_shl_load=no +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext +LIBS=$ac_check_lib_save_LIBS +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dld_shl_load" >&5 +printf "%s\n" "$ac_cv_lib_dld_shl_load" >&6; } +if test "x$ac_cv_lib_dld_shl_load" = xyes +then : + lt_cv_dlopen=shl_load lt_cv_dlopen_libs=-ldld +else $as_nop + ac_fn_c_check_func "$LINENO" "dlopen" "ac_cv_func_dlopen" +if test "x$ac_cv_func_dlopen" = xyes +then : + lt_cv_dlopen=dlopen +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for dlopen in -ldl" >&5 +printf %s "checking for dlopen in -ldl... " >&6; } +if test ${ac_cv_lib_dl_dlopen+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ac_check_lib_save_LIBS=$LIBS +LIBS="-ldl $LIBS" +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +/* Override any GCC internal prototype to avoid an error. + Use char because int might match the return type of a GCC + builtin and then its argument prototype would still apply. */ +char dlopen (); +int +main (void) +{ +return dlopen (); + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + ac_cv_lib_dl_dlopen=yes +else $as_nop + ac_cv_lib_dl_dlopen=no +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext +LIBS=$ac_check_lib_save_LIBS +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dl_dlopen" >&5 +printf "%s\n" "$ac_cv_lib_dl_dlopen" >&6; } +if test "x$ac_cv_lib_dl_dlopen" = xyes +then : + lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-ldl +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for dlopen in -lsvld" >&5 +printf %s "checking for dlopen in -lsvld... " >&6; } +if test ${ac_cv_lib_svld_dlopen+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ac_check_lib_save_LIBS=$LIBS +LIBS="-lsvld $LIBS" +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +/* Override any GCC internal prototype to avoid an error. + Use char because int might match the return type of a GCC + builtin and then its argument prototype would still apply. */ +char dlopen (); +int +main (void) +{ +return dlopen (); + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + ac_cv_lib_svld_dlopen=yes +else $as_nop + ac_cv_lib_svld_dlopen=no +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext +LIBS=$ac_check_lib_save_LIBS +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_svld_dlopen" >&5 +printf "%s\n" "$ac_cv_lib_svld_dlopen" >&6; } +if test "x$ac_cv_lib_svld_dlopen" = xyes +then : + lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-lsvld +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for dld_link in -ldld" >&5 +printf %s "checking for dld_link in -ldld... " >&6; } +if test ${ac_cv_lib_dld_dld_link+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ac_check_lib_save_LIBS=$LIBS +LIBS="-ldld $LIBS" +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +/* Override any GCC internal prototype to avoid an error. + Use char because int might match the return type of a GCC + builtin and then its argument prototype would still apply. */ +char dld_link (); +int +main (void) +{ +return dld_link (); + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + ac_cv_lib_dld_dld_link=yes +else $as_nop + ac_cv_lib_dld_dld_link=no +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext +LIBS=$ac_check_lib_save_LIBS +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dld_dld_link" >&5 +printf "%s\n" "$ac_cv_lib_dld_dld_link" >&6; } +if test "x$ac_cv_lib_dld_dld_link" = xyes +then : + lt_cv_dlopen=dld_link lt_cv_dlopen_libs=-ldld +fi + + +fi + + +fi + + +fi + + +fi + + +fi + + ;; + esac + + if test no = "$lt_cv_dlopen"; then + enable_dlopen=no + else + enable_dlopen=yes + fi + + case $lt_cv_dlopen in + dlopen) + save_CPPFLAGS=$CPPFLAGS + test yes = "$ac_cv_header_dlfcn_h" && CPPFLAGS="$CPPFLAGS -DHAVE_DLFCN_H" + + save_LDFLAGS=$LDFLAGS + wl=$lt_prog_compiler_wl eval LDFLAGS=\"\$LDFLAGS $export_dynamic_flag_spec\" + + save_LIBS=$LIBS + LIBS="$lt_cv_dlopen_libs $LIBS" + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether a program can dlopen itself" >&5 +printf %s "checking whether a program can dlopen itself... " >&6; } +if test ${lt_cv_dlopen_self+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test yes = "$cross_compiling"; then : + lt_cv_dlopen_self=cross +else + lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2 + lt_status=$lt_dlunknown + cat > conftest.$ac_ext <<_LT_EOF +#line $LINENO "configure" +#include "confdefs.h" + +#if HAVE_DLFCN_H +#include +#endif + +#include + +#ifdef RTLD_GLOBAL +# define LT_DLGLOBAL RTLD_GLOBAL +#else +# ifdef DL_GLOBAL +# define LT_DLGLOBAL DL_GLOBAL +# else +# define LT_DLGLOBAL 0 +# endif +#endif + +/* We may have to define LT_DLLAZY_OR_NOW in the command line if we + find out it does not work in some platform. */ +#ifndef LT_DLLAZY_OR_NOW +# ifdef RTLD_LAZY +# define LT_DLLAZY_OR_NOW RTLD_LAZY +# else +# ifdef DL_LAZY +# define LT_DLLAZY_OR_NOW DL_LAZY +# else +# ifdef RTLD_NOW +# define LT_DLLAZY_OR_NOW RTLD_NOW +# else +# ifdef DL_NOW +# define LT_DLLAZY_OR_NOW DL_NOW +# else +# define LT_DLLAZY_OR_NOW 0 +# endif +# endif +# endif +# endif +#endif + +/* When -fvisibility=hidden is used, assume the code has been annotated + correspondingly for the symbols needed. */ +#if defined __GNUC__ && (((__GNUC__ == 3) && (__GNUC_MINOR__ >= 3)) || (__GNUC__ > 3)) +int fnord () __attribute__((visibility("default"))); +#endif + +int fnord () { return 42; } +int main () +{ + void *self = dlopen (0, LT_DLGLOBAL|LT_DLLAZY_OR_NOW); + int status = $lt_dlunknown; + + if (self) + { + if (dlsym (self,"fnord")) status = $lt_dlno_uscore; + else + { + if (dlsym( self,"_fnord")) status = $lt_dlneed_uscore; + else puts (dlerror ()); + } + /* dlclose (self); */ + } + else + puts (dlerror ()); + + return status; +} +_LT_EOF + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_link\""; } >&5 + (eval $ac_link) 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } && test -s "conftest$ac_exeext" 2>/dev/null; then + (./conftest; exit; ) >&5 2>/dev/null + lt_status=$? + case x$lt_status in + x$lt_dlno_uscore) lt_cv_dlopen_self=yes ;; + x$lt_dlneed_uscore) lt_cv_dlopen_self=yes ;; + x$lt_dlunknown|x*) lt_cv_dlopen_self=no ;; + esac + else : + # compilation failed + lt_cv_dlopen_self=no + fi +fi +rm -fr conftest* + + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_dlopen_self" >&5 +printf "%s\n" "$lt_cv_dlopen_self" >&6; } + + if test yes = "$lt_cv_dlopen_self"; then + wl=$lt_prog_compiler_wl eval LDFLAGS=\"\$LDFLAGS $lt_prog_compiler_static\" + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether a statically linked program can dlopen itself" >&5 +printf %s "checking whether a statically linked program can dlopen itself... " >&6; } +if test ${lt_cv_dlopen_self_static+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test yes = "$cross_compiling"; then : + lt_cv_dlopen_self_static=cross +else + lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2 + lt_status=$lt_dlunknown + cat > conftest.$ac_ext <<_LT_EOF +#line $LINENO "configure" +#include "confdefs.h" + +#if HAVE_DLFCN_H +#include +#endif + +#include + +#ifdef RTLD_GLOBAL +# define LT_DLGLOBAL RTLD_GLOBAL +#else +# ifdef DL_GLOBAL +# define LT_DLGLOBAL DL_GLOBAL +# else +# define LT_DLGLOBAL 0 +# endif +#endif + +/* We may have to define LT_DLLAZY_OR_NOW in the command line if we + find out it does not work in some platform. */ +#ifndef LT_DLLAZY_OR_NOW +# ifdef RTLD_LAZY +# define LT_DLLAZY_OR_NOW RTLD_LAZY +# else +# ifdef DL_LAZY +# define LT_DLLAZY_OR_NOW DL_LAZY +# else +# ifdef RTLD_NOW +# define LT_DLLAZY_OR_NOW RTLD_NOW +# else +# ifdef DL_NOW +# define LT_DLLAZY_OR_NOW DL_NOW +# else +# define LT_DLLAZY_OR_NOW 0 +# endif +# endif +# endif +# endif +#endif + +/* When -fvisibility=hidden is used, assume the code has been annotated + correspondingly for the symbols needed. */ +#if defined __GNUC__ && (((__GNUC__ == 3) && (__GNUC_MINOR__ >= 3)) || (__GNUC__ > 3)) +int fnord () __attribute__((visibility("default"))); +#endif + +int fnord () { return 42; } +int main () +{ + void *self = dlopen (0, LT_DLGLOBAL|LT_DLLAZY_OR_NOW); + int status = $lt_dlunknown; + + if (self) + { + if (dlsym (self,"fnord")) status = $lt_dlno_uscore; + else + { + if (dlsym( self,"_fnord")) status = $lt_dlneed_uscore; + else puts (dlerror ()); + } + /* dlclose (self); */ + } + else + puts (dlerror ()); + + return status; +} +_LT_EOF + if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_link\""; } >&5 + (eval $ac_link) 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; } && test -s "conftest$ac_exeext" 2>/dev/null; then + (./conftest; exit; ) >&5 2>/dev/null + lt_status=$? + case x$lt_status in + x$lt_dlno_uscore) lt_cv_dlopen_self_static=yes ;; + x$lt_dlneed_uscore) lt_cv_dlopen_self_static=yes ;; + x$lt_dlunknown|x*) lt_cv_dlopen_self_static=no ;; + esac + else : + # compilation failed + lt_cv_dlopen_self_static=no + fi +fi +rm -fr conftest* + + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $lt_cv_dlopen_self_static" >&5 +printf "%s\n" "$lt_cv_dlopen_self_static" >&6; } + fi + + CPPFLAGS=$save_CPPFLAGS + LDFLAGS=$save_LDFLAGS + LIBS=$save_LIBS + ;; + esac + + case $lt_cv_dlopen_self in + yes|no) enable_dlopen_self=$lt_cv_dlopen_self ;; + *) enable_dlopen_self=unknown ;; + esac + + case $lt_cv_dlopen_self_static in + yes|no) enable_dlopen_self_static=$lt_cv_dlopen_self_static ;; + *) enable_dlopen_self_static=unknown ;; + esac +fi + + + + + + + + + + + + + + + + + +striplib= +old_striplib= +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether stripping libraries is possible" >&5 +printf %s "checking whether stripping libraries is possible... " >&6; } +if test -z "$STRIP"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +else + if $STRIP -V 2>&1 | $GREP "GNU strip" >/dev/null; then + old_striplib="$STRIP --strip-debug" + striplib="$STRIP --strip-unneeded" + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +printf "%s\n" "yes" >&6; } + else + case $host_os in + darwin*) + # FIXME - insert some real tests, host_os isn't really good enough + striplib="$STRIP -x" + old_striplib="$STRIP -S" + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +printf "%s\n" "yes" >&6; } + ;; + freebsd*) + if $STRIP -V 2>&1 | $GREP "elftoolchain" >/dev/null; then + old_striplib="$STRIP --strip-debug" + striplib="$STRIP --strip-unneeded" + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +printf "%s\n" "yes" >&6; } + else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } + fi + ;; + *) + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } + ;; + esac + fi +fi + + + + + + + + + + + + + # Report what library types will actually be built + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking if libtool supports shared libraries" >&5 +printf %s "checking if libtool supports shared libraries... " >&6; } + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $can_build_shared" >&5 +printf "%s\n" "$can_build_shared" >&6; } + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether to build shared libraries" >&5 +printf %s "checking whether to build shared libraries... " >&6; } + test no = "$can_build_shared" && enable_shared=no + + # On AIX, shared libraries and static libraries use the same namespace, and + # are all built from PIC. + case $host_os in + aix3*) + test yes = "$enable_shared" && enable_static=no + if test -n "$RANLIB"; then + archive_cmds="$archive_cmds~\$RANLIB \$lib" + postinstall_cmds='$RANLIB $lib' + fi + ;; + + aix[4-9]*) + if test ia64 != "$host_cpu"; then + case $enable_shared,$with_aix_soname,$aix_use_runtimelinking in + yes,aix,yes) ;; # shared object as lib.so file only + yes,svr4,*) ;; # shared object as lib.so archive member only + yes,*) enable_static=no ;; # shared object in lib.a archive as well + esac + fi + ;; + esac + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $enable_shared" >&5 +printf "%s\n" "$enable_shared" >&6; } + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether to build static libraries" >&5 +printf %s "checking whether to build static libraries... " >&6; } + # Make sure either enable_shared or enable_static is yes. + test yes = "$enable_shared" || enable_static=yes + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $enable_static" >&5 +printf "%s\n" "$enable_static" >&6; } + + + + +fi +ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu + +CC=$lt_save_CC + + + + + + + + + + + + + + + + ac_config_commands="$ac_config_commands libtool" + + + + +# Only expand once: + + +ac_fn_c_check_header_compile "$LINENO" "windows.h" "ac_cv_header_windows_h" "$ac_includes_default" +if test "x$ac_cv_header_windows_h" = xyes +then : + if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}windres", so it can be a program name with args. +set dummy ${ac_tool_prefix}windres; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_RC+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$RC"; then + ac_cv_prog_RC="$RC" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_RC="${ac_tool_prefix}windres" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +RC=$ac_cv_prog_RC +if test -n "$RC"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $RC" >&5 +printf "%s\n" "$RC" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + +fi +if test -z "$ac_cv_prog_RC"; then + ac_ct_RC=$RC + # Extract the first word of "windres", so it can be a program name with args. +set dummy windres; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ac_ct_RC+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ac_ct_RC"; then + ac_cv_prog_ac_ct_RC="$ac_ct_RC" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_RC="windres" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +ac_ct_RC=$ac_cv_prog_ac_ct_RC +if test -n "$ac_ct_RC"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_ct_RC" >&5 +printf "%s\n" "$ac_ct_RC" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + if test "x$ac_ct_RC" = x; then + RC="" + else + case $cross_compiling:$ac_tool_warned in +yes:) +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 +printf "%s\n" "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} +ac_tool_warned=yes ;; +esac + RC=$ac_ct_RC + fi +else + RC="$ac_cv_prog_RC" +fi + + + +# Source file extension for RC test sources. +ac_ext=rc + +# Object file extension for compiled RC test sources. +objext=o +objext_RC=$objext + +# Code to be used in simple compile tests +lt_simple_compile_test_code='sample MENU { MENUITEM "&Soup", 100, CHECKED }' + +# Code to be used in simple link tests +lt_simple_link_test_code=$lt_simple_compile_test_code + +# ltmain only uses $CC for tagged configurations so make sure $CC is set. + + + + + + +# If no C compiler was specified, use CC. +LTCC=${LTCC-"$CC"} + +# If no C compiler flags were specified, use CFLAGS. +LTCFLAGS=${LTCFLAGS-"$CFLAGS"} + +# Allow CC to be a program name with arguments. +compiler=$CC + + +# save warnings/boilerplate of simple test code +ac_outfile=conftest.$ac_objext +echo "$lt_simple_compile_test_code" >conftest.$ac_ext +eval "$ac_compile" 2>&1 >/dev/null | $SED '/^$/d; /^ *+/d' >conftest.err +_lt_compiler_boilerplate=`cat conftest.err` +$RM conftest* + +ac_outfile=conftest.$ac_objext +echo "$lt_simple_link_test_code" >conftest.$ac_ext +eval "$ac_link" 2>&1 >/dev/null | $SED '/^$/d; /^ *+/d' >conftest.err +_lt_linker_boilerplate=`cat conftest.err` +$RM -r conftest* + + +# Allow CC to be a program name with arguments. +lt_save_CC=$CC +lt_save_CFLAGS=$CFLAGS +lt_save_GCC=$GCC +GCC= +CC=${RC-"windres"} +CFLAGS= +compiler=$CC +compiler_RC=$CC +func_cc_basename $compiler +cc_basename=$func_cc_basename_result + +lt_cv_prog_compiler_c_o_RC=yes + +if test -n "$compiler"; then + : + + + +fi + +GCC=$lt_save_GCC +ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu + +CC=$lt_save_CC +CFLAGS=$lt_save_CFLAGS + +fi + + + +# checks for native programs to generate building tool + +if test ${cross_compiling} = yes; then + # Extract the first word of "${build}-gcc", so it can be a program name with args. +set dummy ${build}-gcc; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_CC_BUILD+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$CC_BUILD"; then + ac_cv_prog_CC_BUILD="$CC_BUILD" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_CC_BUILD="${build}-gcc" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +CC_BUILD=$ac_cv_prog_CC_BUILD +if test -n "$CC_BUILD"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $CC_BUILD" >&5 +printf "%s\n" "$CC_BUILD" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + test -z "${CC_BUILD}" && # Extract the first word of "gcc", so it can be a program name with args. +set dummy gcc; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_CC_BUILD+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$CC_BUILD"; then + ac_cv_prog_CC_BUILD="$CC_BUILD" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_CC_BUILD="gcc" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +CC_BUILD=$ac_cv_prog_CC_BUILD +if test -n "$CC_BUILD"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $CC_BUILD" >&5 +printf "%s\n" "$CC_BUILD" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + test -z "${CC_BUILD}" && # Extract the first word of "cc", so it can be a program name with args. +set dummy cc; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_CC_BUILD+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$CC_BUILD"; then + ac_cv_prog_CC_BUILD="$CC_BUILD" # Let the user override the test. +else + ac_prog_rejected=no +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + if test "$as_dir$ac_word$ac_exec_ext" = "/usr/ucb/cc"; then + ac_prog_rejected=yes + continue + fi + ac_cv_prog_CC_BUILD="cc" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +if test $ac_prog_rejected = yes; then + # We found a bogon in the path, so make sure we never use it. + set dummy $ac_cv_prog_CC_BUILD + shift + if test $# != 0; then + # We chose a different compiler from the bogus one. + # However, it has the same basename, so the bogon will be chosen + # first if we set CC_BUILD to just the basename; use the full file name. + shift + ac_cv_prog_CC_BUILD="$as_dir$ac_word${1+' '}$@" + fi +fi +fi +fi +CC_BUILD=$ac_cv_prog_CC_BUILD +if test -n "$CC_BUILD"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $CC_BUILD" >&5 +printf "%s\n" "$CC_BUILD" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + test -z "${CC_BUILD}" && as_fn_error $? "cannot find native C compiler" "$LINENO" 5 + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for suffix of native executables" >&5 +printf %s "checking for suffix of native executables... " >&6; } + rm -f a.* b.* a_out.exe conftest.* + echo > conftest.c "int main(void) { return 0;}" + ${CC_BUILD} conftest.c || as_fn_error $? "native C compiler is not working" "$LINENO" 5 + rm -f conftest.c + if test -x a.out -o -x b.out -o -x conftest; then + EXEEXT_BUILD="" + elif test -x a_out.exe -o -x conftest.exe; then + EXEEXT_BUILD=".exe" + elif test -x conftest.*; then + EXEEXT_BUILD=`echo conftest.* | sed -n '1s/^.*\././'` + fi + rm -f a.* b.* a_out.exe conftest.* + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $EXEEXT_BUILD" >&5 +printf "%s\n" "$EXEEXT_BUILD" >&6; } +else + CC_BUILD=${CC} + EXEEXT_BUILD=${EXEEXT} +fi + + + + + +# Since these files will be eventually called from another directory (namely +# from the top level) we make the path of the scripts absolute. +# +# This small code snippet has been taken from automake's `ylwrap' script. + + + # Find a good install program. We prefer a C program (faster), +# so one script is as good as another. But avoid the broken or +# incompatible versions: +# SysV /etc/install, /usr/sbin/install +# SunOS /usr/etc/install +# IRIX /sbin/install +# AIX /bin/install +# AmigaOS /C/install, which installs bootblocks on floppy discs +# AIX 4 /usr/bin/installbsd, which doesn't work without a -g flag +# AFS /usr/afsws/bin/install, which mishandles nonexistent args +# SVR4 /usr/ucb/install, which tries to use the nonexistent group "staff" +# OS/2's system install, which has a completely different semantic +# ./install, which can be erroneously created by make from ./install.sh. +# Reject install programs that cannot install multiple files. +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for a BSD-compatible install" >&5 +printf %s "checking for a BSD-compatible install... " >&6; } +if test -z "$INSTALL"; then +if test ${ac_cv_path_install+y} +then : + printf %s "(cached) " >&6 +else $as_nop + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + # Account for fact that we put trailing slashes in our PATH walk. +case $as_dir in #(( + ./ | /[cC]/* | \ + /etc/* | /usr/sbin/* | /usr/etc/* | /sbin/* | /usr/afsws/bin/* | \ + ?:[\\/]os2[\\/]install[\\/]* | ?:[\\/]OS2[\\/]INSTALL[\\/]* | \ + /usr/ucb/* ) ;; + *) + # OSF1 and SCO ODT 3.0 have their own names for install. + # Don't use installbsd from OSF since it installs stuff as root + # by default. + for ac_prog in ginstall scoinst install; do + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_prog$ac_exec_ext"; then + if test $ac_prog = install && + grep dspmsg "$as_dir$ac_prog$ac_exec_ext" >/dev/null 2>&1; then + # AIX install. It has an incompatible calling convention. + : + elif test $ac_prog = install && + grep pwplus "$as_dir$ac_prog$ac_exec_ext" >/dev/null 2>&1; then + # program-specific install script used by HP pwplus--don't use. + : + else + rm -rf conftest.one conftest.two conftest.dir + echo one > conftest.one + echo two > conftest.two + mkdir conftest.dir + if "$as_dir$ac_prog$ac_exec_ext" -c conftest.one conftest.two "`pwd`/conftest.dir/" && + test -s conftest.one && test -s conftest.two && + test -s conftest.dir/conftest.one && + test -s conftest.dir/conftest.two + then + ac_cv_path_install="$as_dir$ac_prog$ac_exec_ext -c" + break 3 + fi + fi + fi + done + done + ;; +esac + + done +IFS=$as_save_IFS + +rm -rf conftest.one conftest.two conftest.dir + +fi + if test ${ac_cv_path_install+y}; then + INSTALL=$ac_cv_path_install + else + # As a last resort, use the slow shell script. Don't cache a + # value for INSTALL within a source directory, because that will + # break other packages using the cache if that directory is + # removed, or if the value is a relative name. + INSTALL=$ac_install_sh + fi +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $INSTALL" >&5 +printf "%s\n" "$INSTALL" >&6; } + +# Use test -z because SunOS4 sh mishandles braces in ${var-val}. +# It thinks the first close brace ends the variable substitution. +test -z "$INSTALL_PROGRAM" && INSTALL_PROGRAM='${INSTALL}' + +test -z "$INSTALL_SCRIPT" && INSTALL_SCRIPT='${INSTALL}' + +test -z "$INSTALL_DATA" && INSTALL_DATA='${INSTALL} -m 644' + +case "$INSTALL" in +[\\/]* | ?:[\\/]*) + ;; +*[\\/]*) + INSTALL="`pwd`/$INSTALL" + ;; +esac + + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for a race-free mkdir -p" >&5 +printf %s "checking for a race-free mkdir -p... " >&6; } +if test -z "$MKDIR_P"; then + if test ${ac_cv_path_mkdir+y} +then : + printf %s "(cached) " >&6 +else $as_nop + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH$PATH_SEPARATOR/opt/sfw/bin +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_prog in mkdir gmkdir; do + for ac_exec_ext in '' $ac_executable_extensions; do + as_fn_executable_p "$as_dir$ac_prog$ac_exec_ext" || continue + case `"$as_dir$ac_prog$ac_exec_ext" --version 2>&1` in #( + 'mkdir ('*'coreutils) '* | \ + 'BusyBox '* | \ + 'mkdir (fileutils) '4.1*) + ac_cv_path_mkdir=$as_dir$ac_prog$ac_exec_ext + break 3;; + esac + done + done + done +IFS=$as_save_IFS + +fi + + test -d ./--version && rmdir ./--version + if test ${ac_cv_path_mkdir+y}; then + MKDIR_P="$ac_cv_path_mkdir -p" + else + # As a last resort, use the slow shell script. Don't cache a + # value for MKDIR_P within a source directory, because that will + # break other packages using the cache if that directory is + # removed, or if the value is a relative name. + MKDIR_P="$ac_install_sh -d" + fi +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $MKDIR_P" >&5 +printf "%s\n" "$MKDIR_P" >&6; } + +case "$MKDIR_P" in +[\\/]* | ?:[\\/]*) + ;; +*[\\/]*) + MKDIR_P="`pwd`/$MKDIR_P" + ;; +esac + + +# checks for header files + +ac_fn_c_check_header_compile "$LINENO" "fcntl.h" "ac_cv_header_fcntl_h" "$ac_includes_default" +if test "x$ac_cv_header_fcntl_h" = xyes +then : + printf "%s\n" "#define HAVE_FCNTL_H 1" >>confdefs.h + +fi +ac_fn_c_check_header_compile "$LINENO" "unistd.h" "ac_cv_header_unistd_h" "$ac_includes_default" +if test "x$ac_cv_header_unistd_h" = xyes +then : + printf "%s\n" "#define HAVE_UNISTD_H 1" >>confdefs.h + +fi + + + +# checks for typedefs, structures, and compiler characteristics + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for an ANSI C-conforming const" >&5 +printf %s "checking for an ANSI C-conforming const... " >&6; } +if test ${ac_cv_c_const+y} +then : + printf %s "(cached) " >&6 +else $as_nop + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +int +main (void) +{ + +#ifndef __cplusplus + /* Ultrix mips cc rejects this sort of thing. */ + typedef int charset[2]; + const charset cs = { 0, 0 }; + /* SunOS 4.1.1 cc rejects this. */ + char const *const *pcpcc; + char **ppc; + /* NEC SVR4.0.2 mips cc rejects this. */ + struct point {int x, y;}; + static struct point const zero = {0,0}; + /* IBM XL C 1.02.0.0 rejects this. + It does not let you subtract one const X* pointer from another in + an arm of an if-expression whose if-part is not a constant + expression */ + const char *g = "string"; + pcpcc = &g + (g ? g-g : 0); + /* HPUX 7.0 cc rejects these. */ + ++pcpcc; + ppc = (char**) pcpcc; + pcpcc = (char const *const *) ppc; + { /* SCO 3.2v4 cc rejects this sort of thing. */ + char tx; + char *t = &tx; + char const *s = 0 ? (char *) 0 : (char const *) 0; + + *t++ = 0; + if (s) return 0; + } + { /* Someone thinks the Sun supposedly-ANSI compiler will reject this. */ + int x[] = {25, 17}; + const int *foo = &x[0]; + ++foo; + } + { /* Sun SC1.0 ANSI compiler rejects this -- but not the above. */ + typedef const int *iptr; + iptr p = 0; + ++p; + } + { /* IBM XL C 1.02.0.0 rejects this sort of thing, saying + "k.c", line 2.27: 1506-025 (S) Operand must be a modifiable lvalue. */ + struct s { int j; const int *ap[3]; } bx; + struct s *b = &bx; b->j = 5; + } + { /* ULTRIX-32 V3.1 (Rev 9) vcc rejects this */ + const int foo = 10; + if (!foo) return 0; + } + return !cs[0] && !zero.x; +#endif + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + ac_cv_c_const=yes +else $as_nop + ac_cv_c_const=no +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_c_const" >&5 +printf "%s\n" "$ac_cv_c_const" >&6; } +if test $ac_cv_c_const = no; then + +printf "%s\n" "#define const /**/" >>confdefs.h + +fi + + +# Check whether --enable-freetype-config was given. +if test ${enable_freetype_config+y} +then : + enableval=$enable_freetype_config; case "${enableval}" in + yes) enable_freetype_config="TRUE" ;; + no) enable_freetype_config="FALSE" ;; + *) as_fn_error $? "unknown value '${enableval}' passed with --enable-freetype-config" "$LINENO" 5 ;; + esac +else $as_nop + enable_freetype_config="FALSE" +fi + + +INSTALL_FT2_CONFIG=$enable_freetype_config + + +# checks for library functions + +# Check whether --enable-largefile was given. +if test ${enable_largefile+y} +then : + enableval=$enable_largefile; +fi + +if test "$enable_largefile" != no; then + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for special C compiler options needed for large files" >&5 +printf %s "checking for special C compiler options needed for large files... " >&6; } +if test ${ac_cv_sys_largefile_CC+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ac_cv_sys_largefile_CC=no + if test "$GCC" != yes; then + ac_save_CC=$CC + while :; do + # IRIX 6.2 and later do not support large files by default, + # so use the C compiler's -n32 option if that helps. + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#include + /* Check that off_t can represent 2**63 - 1 correctly. + We can't simply define LARGE_OFF_T to be 9223372036854775807, + since some C++ compilers masquerading as C compilers + incorrectly reject 9223372036854775807. */ +#define LARGE_OFF_T (((off_t) 1 << 31 << 31) - 1 + ((off_t) 1 << 31 << 31)) + int off_t_is_large[(LARGE_OFF_T % 2147483629 == 721 + && LARGE_OFF_T % 2147483647 == 1) + ? 1 : -1]; +int +main (void) +{ + + ; + return 0; +} +_ACEOF + if ac_fn_c_try_compile "$LINENO" +then : + break +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam + CC="$CC -n32" + if ac_fn_c_try_compile "$LINENO" +then : + ac_cv_sys_largefile_CC=' -n32'; break +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam + break + done + CC=$ac_save_CC + rm -f conftest.$ac_ext + fi +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sys_largefile_CC" >&5 +printf "%s\n" "$ac_cv_sys_largefile_CC" >&6; } + if test "$ac_cv_sys_largefile_CC" != no; then + CC=$CC$ac_cv_sys_largefile_CC + fi + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for _FILE_OFFSET_BITS value needed for large files" >&5 +printf %s "checking for _FILE_OFFSET_BITS value needed for large files... " >&6; } +if test ${ac_cv_sys_file_offset_bits+y} +then : + printf %s "(cached) " >&6 +else $as_nop + while :; do + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#include + /* Check that off_t can represent 2**63 - 1 correctly. + We can't simply define LARGE_OFF_T to be 9223372036854775807, + since some C++ compilers masquerading as C compilers + incorrectly reject 9223372036854775807. */ +#define LARGE_OFF_T (((off_t) 1 << 31 << 31) - 1 + ((off_t) 1 << 31 << 31)) + int off_t_is_large[(LARGE_OFF_T % 2147483629 == 721 + && LARGE_OFF_T % 2147483647 == 1) + ? 1 : -1]; +int +main (void) +{ + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + ac_cv_sys_file_offset_bits=no; break +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#define _FILE_OFFSET_BITS 64 +#include + /* Check that off_t can represent 2**63 - 1 correctly. + We can't simply define LARGE_OFF_T to be 9223372036854775807, + since some C++ compilers masquerading as C compilers + incorrectly reject 9223372036854775807. */ +#define LARGE_OFF_T (((off_t) 1 << 31 << 31) - 1 + ((off_t) 1 << 31 << 31)) + int off_t_is_large[(LARGE_OFF_T % 2147483629 == 721 + && LARGE_OFF_T % 2147483647 == 1) + ? 1 : -1]; +int +main (void) +{ + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + ac_cv_sys_file_offset_bits=64; break +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext + ac_cv_sys_file_offset_bits=unknown + break +done +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sys_file_offset_bits" >&5 +printf "%s\n" "$ac_cv_sys_file_offset_bits" >&6; } +case $ac_cv_sys_file_offset_bits in #( + no | unknown) ;; + *) +printf "%s\n" "#define _FILE_OFFSET_BITS $ac_cv_sys_file_offset_bits" >>confdefs.h +;; +esac +rm -rf conftest* + if test $ac_cv_sys_file_offset_bits = unknown; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for _LARGE_FILES value needed for large files" >&5 +printf %s "checking for _LARGE_FILES value needed for large files... " >&6; } +if test ${ac_cv_sys_large_files+y} +then : + printf %s "(cached) " >&6 +else $as_nop + while :; do + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#include + /* Check that off_t can represent 2**63 - 1 correctly. + We can't simply define LARGE_OFF_T to be 9223372036854775807, + since some C++ compilers masquerading as C compilers + incorrectly reject 9223372036854775807. */ +#define LARGE_OFF_T (((off_t) 1 << 31 << 31) - 1 + ((off_t) 1 << 31 << 31)) + int off_t_is_large[(LARGE_OFF_T % 2147483629 == 721 + && LARGE_OFF_T % 2147483647 == 1) + ? 1 : -1]; +int +main (void) +{ + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + ac_cv_sys_large_files=no; break +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#define _LARGE_FILES 1 +#include + /* Check that off_t can represent 2**63 - 1 correctly. + We can't simply define LARGE_OFF_T to be 9223372036854775807, + since some C++ compilers masquerading as C compilers + incorrectly reject 9223372036854775807. */ +#define LARGE_OFF_T (((off_t) 1 << 31 << 31) - 1 + ((off_t) 1 << 31 << 31)) + int off_t_is_large[(LARGE_OFF_T % 2147483629 == 721 + && LARGE_OFF_T % 2147483647 == 1) + ? 1 : -1]; +int +main (void) +{ + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + ac_cv_sys_large_files=1; break +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext + ac_cv_sys_large_files=unknown + break +done +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sys_large_files" >&5 +printf "%s\n" "$ac_cv_sys_large_files" >&6; } +case $ac_cv_sys_large_files in #( + no | unknown) ;; + *) +printf "%s\n" "#define _LARGE_FILES $ac_cv_sys_large_files" >>confdefs.h +;; +esac +rm -rf conftest* + fi +fi + + +# Here we check whether we can use our mmap file component. +# +# Note that `ftsystem.c` for Windows has its own mmap-like implementation +# not covered by `AC_FUNC_MMAP` and/or `FT_UNMAP_PARAM`. + +# Check whether --enable-mmap was given. +if test ${enable_mmap+y} +then : + enableval=$enable_mmap; enable_mmap="no" +else $as_nop + enable_mmap="yes" +fi + +if test "x${enable_mmap}" != "xno"; then + case "$host" in + *-*-mingw*) + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for working mmap" >&5 +printf %s "checking for working mmap... " >&6; } + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: using MapViewOfFile in Windows" >&5 +printf "%s\n" "using MapViewOfFile in Windows" >&6; } + FTSYS_SRC='$(TOP_DIR)/builds/windows/ftsystem.c' + ;; + *) + +ac_func= +for ac_item in $ac_func_c_list +do + if test $ac_func; then + ac_fn_c_check_func "$LINENO" $ac_func ac_cv_func_$ac_func + if eval test \"x\$ac_cv_func_$ac_func\" = xyes; then + echo "#define $ac_item 1" >> confdefs.h + fi + ac_func= + else + ac_func=$ac_item + fi +done + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for working mmap" >&5 +printf %s "checking for working mmap... " >&6; } +if test ${ac_cv_func_mmap_fixed_mapped+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test "$cross_compiling" = yes +then : + case "$host_os" in # (( + # Guess yes on platforms where we know the result. + linux*) ac_cv_func_mmap_fixed_mapped=yes ;; + # If we don't know, assume the worst. + *) ac_cv_func_mmap_fixed_mapped=no ;; + esac +else $as_nop + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +$ac_includes_default +/* malloc might have been renamed as rpl_malloc. */ +#undef malloc + +/* Thanks to Mike Haertel and Jim Avera for this test. + Here is a matrix of mmap possibilities: + mmap private not fixed + mmap private fixed at somewhere currently unmapped + mmap private fixed at somewhere already mapped + mmap shared not fixed + mmap shared fixed at somewhere currently unmapped + mmap shared fixed at somewhere already mapped + For private mappings, we should verify that changes cannot be read() + back from the file, nor mmap's back from the file at a different + address. (There have been systems where private was not correctly + implemented like the infamous i386 svr4.0, and systems where the + VM page cache was not coherent with the file system buffer cache + like early versions of FreeBSD and possibly contemporary NetBSD.) + For shared mappings, we should conversely verify that changes get + propagated back to all the places they're supposed to be. + + Grep wants private fixed already mapped. + The main things grep needs to know about mmap are: + * does it exist and is it safe to write into the mmap'd area + * how to use it (BSD variants) */ + +#include +#include + +/* This mess was copied from the GNU getpagesize.h. */ +#ifndef HAVE_GETPAGESIZE +# ifdef _SC_PAGESIZE +# define getpagesize() sysconf(_SC_PAGESIZE) +# else /* no _SC_PAGESIZE */ +# ifdef HAVE_SYS_PARAM_H +# include +# ifdef EXEC_PAGESIZE +# define getpagesize() EXEC_PAGESIZE +# else /* no EXEC_PAGESIZE */ +# ifdef NBPG +# define getpagesize() NBPG * CLSIZE +# ifndef CLSIZE +# define CLSIZE 1 +# endif /* no CLSIZE */ +# else /* no NBPG */ +# ifdef NBPC +# define getpagesize() NBPC +# else /* no NBPC */ +# ifdef PAGESIZE +# define getpagesize() PAGESIZE +# endif /* PAGESIZE */ +# endif /* no NBPC */ +# endif /* no NBPG */ +# endif /* no EXEC_PAGESIZE */ +# else /* no HAVE_SYS_PARAM_H */ +# define getpagesize() 8192 /* punt totally */ +# endif /* no HAVE_SYS_PARAM_H */ +# endif /* no _SC_PAGESIZE */ + +#endif /* no HAVE_GETPAGESIZE */ + +int +main (void) +{ + char *data, *data2, *data3; + const char *cdata2; + int i, pagesize; + int fd, fd2; + + pagesize = getpagesize (); + + /* First, make a file with some known garbage in it. */ + data = (char *) malloc (pagesize); + if (!data) + return 1; + for (i = 0; i < pagesize; ++i) + *(data + i) = rand (); + umask (0); + fd = creat ("conftest.mmap", 0600); + if (fd < 0) + return 2; + if (write (fd, data, pagesize) != pagesize) + return 3; + close (fd); + + /* Next, check that the tail of a page is zero-filled. File must have + non-zero length, otherwise we risk SIGBUS for entire page. */ + fd2 = open ("conftest.txt", O_RDWR | O_CREAT | O_TRUNC, 0600); + if (fd2 < 0) + return 4; + cdata2 = ""; + if (write (fd2, cdata2, 1) != 1) + return 5; + data2 = (char *) mmap (0, pagesize, PROT_READ | PROT_WRITE, MAP_SHARED, fd2, 0L); + if (data2 == MAP_FAILED) + return 6; + for (i = 0; i < pagesize; ++i) + if (*(data2 + i)) + return 7; + close (fd2); + if (munmap (data2, pagesize)) + return 8; + + /* Next, try to mmap the file at a fixed address which already has + something else allocated at it. If we can, also make sure that + we see the same garbage. */ + fd = open ("conftest.mmap", O_RDWR); + if (fd < 0) + return 9; + if (data2 != mmap (data2, pagesize, PROT_READ | PROT_WRITE, + MAP_PRIVATE | MAP_FIXED, fd, 0L)) + return 10; + for (i = 0; i < pagesize; ++i) + if (*(data + i) != *(data2 + i)) + return 11; + + /* Finally, make sure that changes to the mapped area do not + percolate back to the file as seen by read(). (This is a bug on + some variants of i386 svr4.0.) */ + for (i = 0; i < pagesize; ++i) + *(data2 + i) = *(data2 + i) + 1; + data3 = (char *) malloc (pagesize); + if (!data3) + return 12; + if (read (fd, data3, pagesize) != pagesize) + return 13; + for (i = 0; i < pagesize; ++i) + if (*(data + i) != *(data3 + i)) + return 14; + close (fd); + free (data); + free (data3); + return 0; +} +_ACEOF +if ac_fn_c_try_run "$LINENO" +then : + ac_cv_func_mmap_fixed_mapped=yes +else $as_nop + ac_cv_func_mmap_fixed_mapped=no +fi +rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \ + conftest.$ac_objext conftest.beam conftest.$ac_ext +fi + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_func_mmap_fixed_mapped" >&5 +printf "%s\n" "$ac_cv_func_mmap_fixed_mapped" >&6; } +if test $ac_cv_func_mmap_fixed_mapped = yes; then + +printf "%s\n" "#define HAVE_MMAP 1" >>confdefs.h + +fi +rm -f conftest.mmap conftest.txt + + if test "$ac_cv_func_mmap_fixed_mapped" = "yes"; then + FTSYS_SRC='$(PLATFORM_DIR)/ftsystem.c' + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $CC options needed to detect all undeclared functions" >&5 +printf %s "checking for $CC options needed to detect all undeclared functions... " >&6; } +if test ${ac_cv_c_undeclared_builtin_options+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ac_save_CFLAGS=$CFLAGS + ac_cv_c_undeclared_builtin_options='cannot detect' + for ac_arg in '' -fno-builtin; do + CFLAGS="$ac_save_CFLAGS $ac_arg" + # This test program should *not* compile successfully. + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +int +main (void) +{ +(void) strchr; + ; + return 0; +} +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + +else $as_nop + # This test program should compile successfully. + # No library function is consistently available on + # freestanding implementations, so test against a dummy + # declaration. Include always-available headers on the + # off chance that they somehow elicit warnings. + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#include +#include +#include +#include +extern void ac_decl (int, char *); + +int +main (void) +{ +(void) ac_decl (0, (char *) 0); + (void) ac_decl; + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + if test x"$ac_arg" = x +then : + ac_cv_c_undeclared_builtin_options='none needed' +else $as_nop + ac_cv_c_undeclared_builtin_options=$ac_arg +fi + break +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext + done + CFLAGS=$ac_save_CFLAGS + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_c_undeclared_builtin_options" >&5 +printf "%s\n" "$ac_cv_c_undeclared_builtin_options" >&6; } + case $ac_cv_c_undeclared_builtin_options in #( + 'cannot detect') : + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 +printf "%s\n" "$as_me: error: in \`$ac_pwd':" >&2;} +as_fn_error $? "cannot make $CC report undeclared builtins +See \`config.log' for more details" "$LINENO" 5; } ;; #( + 'none needed') : + ac_c_undeclared_builtin_options='' ;; #( + *) : + ac_c_undeclared_builtin_options=$ac_cv_c_undeclared_builtin_options ;; +esac + +ac_fn_check_decl "$LINENO" "munmap" "ac_cv_have_decl_munmap" " + +#ifdef HAVE_UNISTD_H +#include +#endif +#include + + +" "$ac_c_undeclared_builtin_options" "CFLAGS" +if test "x$ac_cv_have_decl_munmap" = xyes +then : + ac_have_decl=1 +else $as_nop + ac_have_decl=0 +fi +printf "%s\n" "#define HAVE_DECL_MUNMAP $ac_have_decl" >>confdefs.h + + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for munmap's first parameter type" >&5 +printf %s "checking for munmap's first parameter type... " >&6; } + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + + + +#include +#include +int munmap(void *, size_t); + + + +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: void *" >&5 +printf "%s\n" "void *" >&6; } + +printf "%s\n" "#define MUNMAP_USES_VOIDP /**/" >>confdefs.h + +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: char *" >&5 +printf "%s\n" "char *" >&6; } +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext + + fi + ;; + esac +fi + +if test -z "$FTSYS_SRC"; then + FTSYS_SRC='$(BASE_DIR)/ftsystem.c' +fi + + + +# get compiler flags right +# +# We try to make the compiler work for C99-strict source. Even if the +# C compiler is gcc and C99 flags are available, some system headers +# might be broken in C99 mode. We have to check whether compilation +# finishes successfully. +# +if test "x$GCC" = xyes; then + XX_CFLAGS="-Wall" + case "$host" in + *-*-mingw*) + XX_ANSIFLAGS="-pedantic" + ;; + *-*-aix*) + XX_ANSIFLAGS="-pedantic" + ;; + *) + XX_ANSIFLAGS="" + + for a in "-pedantic" "-std=c99" + do + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking $CC compiler flag ${a} to assure ANSI C99 works correctly" >&5 +printf %s "checking $CC compiler flag ${a} to assure ANSI C99 works correctly... " >&6; } + orig_CFLAGS="${CFLAGS}" + CFLAGS="${CFLAGS} ${XX_ANSIFLAGS} ${a}" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + + + +#include + + +int +main (void) +{ + + + { + puts( "" ); + return 0; + } + + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: ok, adding to XX_ANSIFLAGS" >&5 +printf "%s\n" "ok, adding to XX_ANSIFLAGS" >&6; } + XX_ANSIFLAGS="${XX_ANSIFLAGS} ${a}" + +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext + CFLAGS="${orig_CFLAGS}" + done + ;; + esac +else + case "$host" in + *-dec-osf*) + CFLAGS= + XX_CFLAGS="-std1 -g3" + XX_ANSIFLAGS= + ;; + *) + XX_CFLAGS= + XX_ANSIFLAGS= + ;; + esac +fi + + + + +# It is recommended that shared libraries hide symbols except those with +# explicit __attribute__((visibility("default"))). +# +found_visibility_flag=no +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for -fvisibility=hidden compiler flag" >&5 +printf %s "checking for -fvisibility=hidden compiler flag... " >&6; } +orig_CFLAGS="${CFLAGS}" +CFLAGS="${CFLAGS} -fvisibility=hidden" +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +int +main (void) +{ + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + found_visibility_flag=yes + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +printf "%s\n" "yes" >&6; } +else $as_nop + CFLAGS="${orig_CFLAGS}" + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext + +if test "${found_visibility_flag}" = "no"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for -xldscope=hidden compiler flag" >&5 +printf %s "checking for -xldscope=hidden compiler flag... " >&6; } + orig_CFLAGS="${CFLAGS}" + CFLAGS="${CFLAGS} -xldscope=hidden" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +int +main (void) +{ + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + found_visibility_flag=yes + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +printf "%s\n" "yes" >&6; } +else $as_nop + CFLAGS="${orig_CFLAGS}" + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext +fi + +# All library tests below try `pkg-config' first. If that fails, a function +# from the library is tested in the traditional autoconf way (zlib, bzip2), +# or a config script is called (libpng). +# +# The `xxx_reqpriv' variables are for the `Requires.private' field in +# `freetype2.pc'. The `xxx_libspriv' variables are for the `Libs.private' +# field in `freetype2.pc' if pkg-config doesn't find a proper .pc file. +# +# The `xxx_libsstaticconf' variables are for the `freetype-config' script. +# +# Note that a call to PKG_CHECK_MODULES(XXX, ...) sets and creates the +# output variables `XXX_CFLAGS' and `XXX_LIBS'. In case one or both are set +# for a library by the user, no entry for this library is added to +# `Requires.private'. Instead, it gets added to `Libs.private' + + +# check for system zlib + + +# Check whether --with-zlib was given. +if test ${with_zlib+y} +then : + withval=$with_zlib; +else $as_nop + with_zlib=auto +fi + + +have_zlib=no +if test x"$with_zlib" = xyes -o x"$with_zlib" = xauto; then + zlib_pkg="zlib" + have_zlib_pkg=no + + if test x"$ZLIB_CFLAGS" = x -a x"$ZLIB_LIBS" = x; then + if test -n "$PKG_CONFIG" && \ + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"\$zlib_pkg\""; } >&5 + ($PKG_CONFIG --exists --print-errors "$zlib_pkg") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + have_zlib_pkg=yes +fi + fi + +pkg_failed=no +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for ZLIB" >&5 +printf %s "checking for ZLIB... " >&6; } + +if test -n "$ZLIB_CFLAGS"; then + pkg_cv_ZLIB_CFLAGS="$ZLIB_CFLAGS" + elif test -n "$PKG_CONFIG"; then + if test -n "$PKG_CONFIG" && \ + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"\$zlib_pkg\""; } >&5 + ($PKG_CONFIG --exists --print-errors "$zlib_pkg") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + pkg_cv_ZLIB_CFLAGS=`$PKG_CONFIG --cflags "$zlib_pkg" 2>/dev/null` + test "x$?" != "x0" && pkg_failed=yes +else + pkg_failed=yes +fi + else + pkg_failed=untried +fi +if test -n "$ZLIB_LIBS"; then + pkg_cv_ZLIB_LIBS="$ZLIB_LIBS" + elif test -n "$PKG_CONFIG"; then + if test -n "$PKG_CONFIG" && \ + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"\$zlib_pkg\""; } >&5 + ($PKG_CONFIG --exists --print-errors "$zlib_pkg") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + pkg_cv_ZLIB_LIBS=`$PKG_CONFIG --libs "$zlib_pkg" 2>/dev/null` + test "x$?" != "x0" && pkg_failed=yes +else + pkg_failed=yes +fi + else + pkg_failed=untried +fi + + + +if test $pkg_failed = yes; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } + +if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then + _pkg_short_errors_supported=yes +else + _pkg_short_errors_supported=no +fi + if test $_pkg_short_errors_supported = yes; then + ZLIB_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "$zlib_pkg" 2>&1` + else + ZLIB_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "$zlib_pkg" 2>&1` + fi + # Put the nasty error message in config.log where it belongs + echo "$ZLIB_PKG_ERRORS" >&5 + + : +elif test $pkg_failed = untried; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } + : +else + ZLIB_CFLAGS=$pkg_cv_ZLIB_CFLAGS + ZLIB_LIBS=$pkg_cv_ZLIB_LIBS + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +printf "%s\n" "yes" >&6; } + have_zlib="yes (pkg-config)" +fi + + if test $have_zlib_pkg = yes; then + # we have zlib.pc + zlib_reqpriv="$zlib_pkg" + zlib_libspriv= + zlib_libsstaticconf=`$PKG_CONFIG --static --libs "$zlib_pkg"` + else + zlib_reqpriv= + + if test "$have_zlib" != no; then + # ZLIB_CFLAGS and ZLIB_LIBS are set by the user + zlib_libspriv="$ZLIB_LIBS" + zlib_libsstaticconf="$ZLIB_LIBS" + have_zlib="yes (ZLIB_CFLAGS and ZLIB_LIBS)" + else + # fall back to standard autoconf test + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for gzsetparams in -lz" >&5 +printf %s "checking for gzsetparams in -lz... " >&6; } +if test ${ac_cv_lib_z_gzsetparams+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ac_check_lib_save_LIBS=$LIBS +LIBS="-lz $LIBS" +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +/* Override any GCC internal prototype to avoid an error. + Use char because int might match the return type of a GCC + builtin and then its argument prototype would still apply. */ +char gzsetparams (); +int +main (void) +{ +return gzsetparams (); + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + ac_cv_lib_z_gzsetparams=yes +else $as_nop + ac_cv_lib_z_gzsetparams=no +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext +LIBS=$ac_check_lib_save_LIBS +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_z_gzsetparams" >&5 +printf "%s\n" "$ac_cv_lib_z_gzsetparams" >&6; } +if test "x$ac_cv_lib_z_gzsetparams" = xyes +then : + ac_fn_c_check_header_compile "$LINENO" "zlib.h" "ac_cv_header_zlib_h" "$ac_includes_default" +if test "x$ac_cv_header_zlib_h" = xyes +then : + have_zlib="yes (autoconf test)" + zlib_libspriv="-lz" + zlib_libsstaticconf="$zlib_libspriv" + ZLIB_LIBS="$zlib_libspriv" +fi + +fi + + fi + fi +fi + +if test x"$with_zlib" = xyes -a "$have_zlib" = no; then + as_fn_error $? "external zlib support requested but library not found" "$LINENO" 5 +fi + +SYSTEM_ZLIB= +if test "$have_zlib" != no; then + SYSTEM_ZLIB=yes +fi + + + +# check for system libbz2 + + +# Check whether --with-bzip2 was given. +if test ${with_bzip2+y} +then : + withval=$with_bzip2; +else $as_nop + with_bzip2=auto +fi + + +have_bzip2=no +if test x"$with_bzip2" = xyes -o x"$with_bzip2" = xauto; then + bzip2_pkg="bzip2" + have_bzip2_pkg=no + + if test x"$BZIP2_CFLAGS" = x -a x"$BZIP2_LIBS" = x; then + if test -n "$PKG_CONFIG" && \ + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"\$bzip2_pkg\""; } >&5 + ($PKG_CONFIG --exists --print-errors "$bzip2_pkg") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + have_bzip2_pkg=yes +fi + fi + +pkg_failed=no +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for BZIP2" >&5 +printf %s "checking for BZIP2... " >&6; } + +if test -n "$BZIP2_CFLAGS"; then + pkg_cv_BZIP2_CFLAGS="$BZIP2_CFLAGS" + elif test -n "$PKG_CONFIG"; then + if test -n "$PKG_CONFIG" && \ + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"\$bzip2_pkg\""; } >&5 + ($PKG_CONFIG --exists --print-errors "$bzip2_pkg") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + pkg_cv_BZIP2_CFLAGS=`$PKG_CONFIG --cflags "$bzip2_pkg" 2>/dev/null` + test "x$?" != "x0" && pkg_failed=yes +else + pkg_failed=yes +fi + else + pkg_failed=untried +fi +if test -n "$BZIP2_LIBS"; then + pkg_cv_BZIP2_LIBS="$BZIP2_LIBS" + elif test -n "$PKG_CONFIG"; then + if test -n "$PKG_CONFIG" && \ + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"\$bzip2_pkg\""; } >&5 + ($PKG_CONFIG --exists --print-errors "$bzip2_pkg") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + pkg_cv_BZIP2_LIBS=`$PKG_CONFIG --libs "$bzip2_pkg" 2>/dev/null` + test "x$?" != "x0" && pkg_failed=yes +else + pkg_failed=yes +fi + else + pkg_failed=untried +fi + + + +if test $pkg_failed = yes; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } + +if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then + _pkg_short_errors_supported=yes +else + _pkg_short_errors_supported=no +fi + if test $_pkg_short_errors_supported = yes; then + BZIP2_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "$bzip2_pkg" 2>&1` + else + BZIP2_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "$bzip2_pkg" 2>&1` + fi + # Put the nasty error message in config.log where it belongs + echo "$BZIP2_PKG_ERRORS" >&5 + + : +elif test $pkg_failed = untried; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } + : +else + BZIP2_CFLAGS=$pkg_cv_BZIP2_CFLAGS + BZIP2_LIBS=$pkg_cv_BZIP2_LIBS + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +printf "%s\n" "yes" >&6; } + have_bzip2="yes (pkg-config)" +fi + + if test $have_bzip2_pkg = yes; then + # we have bzip2.pc + bzip2_reqpriv="$bzip2_pkg" + bzip2_libspriv= + bzip2_libsstaticconf=`$PKG_CONFIG --static --libs "$bzip2_pkg"` + else + bzip2_reqpriv= + + if test "$have_bzip2" != no; then + # BZIP2_CFLAGS and BZIP2_LIBS are set by the user + bzip2_libspriv="$BZIP2_LIBS" + bzip2_libsstaticconf="$BZIP2_LIBS" + have_bzip2="yes (BZIP2_CFLAGS and BZIP2_LIBS)" + else + # fall back to standard autoconf test + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for BZ2_bzDecompress in -lbz2" >&5 +printf %s "checking for BZ2_bzDecompress in -lbz2... " >&6; } +if test ${ac_cv_lib_bz2_BZ2_bzDecompress+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ac_check_lib_save_LIBS=$LIBS +LIBS="-lbz2 $LIBS" +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +/* Override any GCC internal prototype to avoid an error. + Use char because int might match the return type of a GCC + builtin and then its argument prototype would still apply. */ +char BZ2_bzDecompress (); +int +main (void) +{ +return BZ2_bzDecompress (); + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + ac_cv_lib_bz2_BZ2_bzDecompress=yes +else $as_nop + ac_cv_lib_bz2_BZ2_bzDecompress=no +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext +LIBS=$ac_check_lib_save_LIBS +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_bz2_BZ2_bzDecompress" >&5 +printf "%s\n" "$ac_cv_lib_bz2_BZ2_bzDecompress" >&6; } +if test "x$ac_cv_lib_bz2_BZ2_bzDecompress" = xyes +then : + ac_fn_c_check_header_compile "$LINENO" "bzlib.h" "ac_cv_header_bzlib_h" "$ac_includes_default" +if test "x$ac_cv_header_bzlib_h" = xyes +then : + have_bzip2="yes (autoconf test)" + bzip2_libspriv="-lbz2" + bzip2_libsstaticconf="$bzip2_libspriv" + BZIP2_LIBS="$bzip2_libspriv" +fi + +fi + + fi + fi +fi + +if test x"$with_bzip2" = xyes -a "$have_bzip2" = no; then + as_fn_error $? "bzip2 support requested but library not found" "$LINENO" 5 +fi + + +# check for system libpng + + +# Check whether --with-png was given. +if test ${with_png+y} +then : + withval=$with_png; +else $as_nop + with_png=auto +fi + + +have_libpng=no +if test x"$with_png" = xyes -o x"$with_png" = xauto; then + libpng_pkg="libpng" + have_libpng_pkg=no + + if test x"$LIBPNG_CFLAGS" = x -a x"$LIBPNG_LIBS" = x; then + if test -n "$PKG_CONFIG" && \ + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"\$libpng_pkg\""; } >&5 + ($PKG_CONFIG --exists --print-errors "$libpng_pkg") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + have_libpng_pkg=yes +fi + fi + +pkg_failed=no +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for LIBPNG" >&5 +printf %s "checking for LIBPNG... " >&6; } + +if test -n "$LIBPNG_CFLAGS"; then + pkg_cv_LIBPNG_CFLAGS="$LIBPNG_CFLAGS" + elif test -n "$PKG_CONFIG"; then + if test -n "$PKG_CONFIG" && \ + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"\$libpng_pkg\""; } >&5 + ($PKG_CONFIG --exists --print-errors "$libpng_pkg") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + pkg_cv_LIBPNG_CFLAGS=`$PKG_CONFIG --cflags "$libpng_pkg" 2>/dev/null` + test "x$?" != "x0" && pkg_failed=yes +else + pkg_failed=yes +fi + else + pkg_failed=untried +fi +if test -n "$LIBPNG_LIBS"; then + pkg_cv_LIBPNG_LIBS="$LIBPNG_LIBS" + elif test -n "$PKG_CONFIG"; then + if test -n "$PKG_CONFIG" && \ + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"\$libpng_pkg\""; } >&5 + ($PKG_CONFIG --exists --print-errors "$libpng_pkg") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + pkg_cv_LIBPNG_LIBS=`$PKG_CONFIG --libs "$libpng_pkg" 2>/dev/null` + test "x$?" != "x0" && pkg_failed=yes +else + pkg_failed=yes +fi + else + pkg_failed=untried +fi + + + +if test $pkg_failed = yes; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } + +if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then + _pkg_short_errors_supported=yes +else + _pkg_short_errors_supported=no +fi + if test $_pkg_short_errors_supported = yes; then + LIBPNG_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "$libpng_pkg" 2>&1` + else + LIBPNG_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "$libpng_pkg" 2>&1` + fi + # Put the nasty error message in config.log where it belongs + echo "$LIBPNG_PKG_ERRORS" >&5 + + : +elif test $pkg_failed = untried; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } + : +else + LIBPNG_CFLAGS=$pkg_cv_LIBPNG_CFLAGS + LIBPNG_LIBS=$pkg_cv_LIBPNG_LIBS + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +printf "%s\n" "yes" >&6; } + have_libpng="yes (pkg-config)" +fi + + if test $have_libpng_pkg = yes; then + # we have libpng.pc + libpng_reqpriv="$libpng_pkg" + libpng_libspriv= + libpng_libsstaticconf=`$PKG_CONFIG --static --libs "$libpng_pkg"` + else + libpng_reqpriv= + + if test "$have_libpng" != no; then + # LIBPNG_CFLAGS and LIBPNG_LIBS are set by the user + libpng_libspriv="$LIBPNG_LIBS" + libpng_libsstaticconf="$LIBPNG_LIBS" + have_libpng="yes (LIBPNG_CFLAGS and LIBPNG_LIBS)" + else + # fall back to config script + # Extract the first word of "libpng-config", so it can be a program name with args. +set dummy libpng-config; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_have_libpng+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$have_libpng"; then + ac_cv_prog_have_libpng="$have_libpng" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_have_libpng="yes (libpng-config)" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + + test -z "$ac_cv_prog_have_libpng" && ac_cv_prog_have_libpng="no" +fi +fi +have_libpng=$ac_cv_prog_have_libpng +if test -n "$have_libpng"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $have_libpng" >&5 +printf "%s\n" "$have_libpng" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + if test "$have_libpng" != no; then + LIBPNG_CFLAGS=`libpng-config --cflags` + LIBPNG_LIBS=`libpng-config --ldflags` + libpng_libspriv=`libpng-config --static --ldflags` + libpng_libsstaticconf="$libpng_libspriv" + fi + fi + fi +fi + +if test x"$with_png" = xyes -a "$have_libpng" = no; then + as_fn_error $? "libpng support requested but library not found" "$LINENO" 5 +fi + + +# check for system libharfbuzz + + +# Check whether --with-harfbuzz was given. +if test ${with_harfbuzz+y} +then : + withval=$with_harfbuzz; +else $as_nop + with_harfbuzz=auto +fi + + +have_harfbuzz=no +if test x"$with_harfbuzz" = xyes -o x"$with_harfbuzz" = xauto; then + harfbuzz_pkg="harfbuzz >= 2.0.0" + have_harfbuzz_pkg=no + + if test x"$HARFBUZZ_CFLAGS" = x -a x"$HARFBUZZ_LIBS" = x; then + if test -n "$PKG_CONFIG" && \ + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"\$harfbuzz_pkg\""; } >&5 + ($PKG_CONFIG --exists --print-errors "$harfbuzz_pkg") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + have_harfbuzz_pkg=yes +fi + fi + +pkg_failed=no +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for HARFBUZZ" >&5 +printf %s "checking for HARFBUZZ... " >&6; } + +if test -n "$HARFBUZZ_CFLAGS"; then + pkg_cv_HARFBUZZ_CFLAGS="$HARFBUZZ_CFLAGS" + elif test -n "$PKG_CONFIG"; then + if test -n "$PKG_CONFIG" && \ + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"\$harfbuzz_pkg\""; } >&5 + ($PKG_CONFIG --exists --print-errors "$harfbuzz_pkg") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + pkg_cv_HARFBUZZ_CFLAGS=`$PKG_CONFIG --cflags "$harfbuzz_pkg" 2>/dev/null` + test "x$?" != "x0" && pkg_failed=yes +else + pkg_failed=yes +fi + else + pkg_failed=untried +fi +if test -n "$HARFBUZZ_LIBS"; then + pkg_cv_HARFBUZZ_LIBS="$HARFBUZZ_LIBS" + elif test -n "$PKG_CONFIG"; then + if test -n "$PKG_CONFIG" && \ + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"\$harfbuzz_pkg\""; } >&5 + ($PKG_CONFIG --exists --print-errors "$harfbuzz_pkg") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + pkg_cv_HARFBUZZ_LIBS=`$PKG_CONFIG --libs "$harfbuzz_pkg" 2>/dev/null` + test "x$?" != "x0" && pkg_failed=yes +else + pkg_failed=yes +fi + else + pkg_failed=untried +fi + + + +if test $pkg_failed = yes; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } + +if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then + _pkg_short_errors_supported=yes +else + _pkg_short_errors_supported=no +fi + if test $_pkg_short_errors_supported = yes; then + HARFBUZZ_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "$harfbuzz_pkg" 2>&1` + else + HARFBUZZ_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "$harfbuzz_pkg" 2>&1` + fi + # Put the nasty error message in config.log where it belongs + echo "$HARFBUZZ_PKG_ERRORS" >&5 + + : +elif test $pkg_failed = untried; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } + : +else + HARFBUZZ_CFLAGS=$pkg_cv_HARFBUZZ_CFLAGS + HARFBUZZ_LIBS=$pkg_cv_HARFBUZZ_LIBS + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +printf "%s\n" "yes" >&6; } + have_harfbuzz="yes (pkg-config)" +fi + + if test $have_harfbuzz_pkg = yes; then + # we have harfbuzz.pc + harfbuzz_reqpriv="$harfbuzz_pkg" + harfbuzz_libspriv= + harfbuzz_libsstaticconf=`$PKG_CONFIG --static --libs "$harfbuzz_pkg"` + else + harfbuzz_reqpriv= + + if test "$have_harfbuzz" != no; then + # HARFBUZZ_CFLAGS and HARFBUZZ_LIBS are set by the user + harfbuzz_libspriv="$HARFBUZZ_LIBS" + harfbuzz_libsstaticconf="$HARFBUZZ_LIBS" + have_harfbuzz="yes (HARFBUZZ_CFLAGS and HARFBUZZ_LIBS)" + else + # since HarfBuzz is quite a new library we don't fall back to a + # different test; additionally, it has too many dependencies + : + fi + fi +fi + +if test x"$with_harfbuzz" = xyes -a "$have_harfbuzz" = no; then + as_fn_error $? "harfbuzz support requested but library not found" "$LINENO" 5 +fi + + +# check for system libbrotlidec + + +# Check whether --with-brotli was given. +if test ${with_brotli+y} +then : + withval=$with_brotli; +else $as_nop + with_brotli=auto +fi + + +have_brotli=no +if test x"$with_brotli" = xyes -o x"$with_brotli" = xauto; then + brotli_pkg="libbrotlidec" + have_brotli_pkg=no + + if test x"$BROTLI_CFLAGS" = x -a x"$BROTLI_LIBS" = x; then + if test -n "$PKG_CONFIG" && \ + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"\$brotli_pkg\""; } >&5 + ($PKG_CONFIG --exists --print-errors "$brotli_pkg") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + have_brotli_pkg=yes +fi + fi + +pkg_failed=no +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for BROTLI" >&5 +printf %s "checking for BROTLI... " >&6; } + +if test -n "$BROTLI_CFLAGS"; then + pkg_cv_BROTLI_CFLAGS="$BROTLI_CFLAGS" + elif test -n "$PKG_CONFIG"; then + if test -n "$PKG_CONFIG" && \ + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"\$brotli_pkg\""; } >&5 + ($PKG_CONFIG --exists --print-errors "$brotli_pkg") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + pkg_cv_BROTLI_CFLAGS=`$PKG_CONFIG --cflags "$brotli_pkg" 2>/dev/null` + test "x$?" != "x0" && pkg_failed=yes +else + pkg_failed=yes +fi + else + pkg_failed=untried +fi +if test -n "$BROTLI_LIBS"; then + pkg_cv_BROTLI_LIBS="$BROTLI_LIBS" + elif test -n "$PKG_CONFIG"; then + if test -n "$PKG_CONFIG" && \ + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"\$brotli_pkg\""; } >&5 + ($PKG_CONFIG --exists --print-errors "$brotli_pkg") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + pkg_cv_BROTLI_LIBS=`$PKG_CONFIG --libs "$brotli_pkg" 2>/dev/null` + test "x$?" != "x0" && pkg_failed=yes +else + pkg_failed=yes +fi + else + pkg_failed=untried +fi + + + +if test $pkg_failed = yes; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } + +if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then + _pkg_short_errors_supported=yes +else + _pkg_short_errors_supported=no +fi + if test $_pkg_short_errors_supported = yes; then + BROTLI_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "$brotli_pkg" 2>&1` + else + BROTLI_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "$brotli_pkg" 2>&1` + fi + # Put the nasty error message in config.log where it belongs + echo "$BROTLI_PKG_ERRORS" >&5 + + : +elif test $pkg_failed = untried; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } + : +else + BROTLI_CFLAGS=$pkg_cv_BROTLI_CFLAGS + BROTLI_LIBS=$pkg_cv_BROTLI_LIBS + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +printf "%s\n" "yes" >&6; } + have_brotli="yes (pkg-config)" +fi + + if test $have_brotli_pkg = yes; then + # we have libbrotlidec.pc + brotli_reqpriv="$brotli_pkg" + brotli_libspriv= + brotli_libsstaticconf=`$PKG_CONFIG --static --libs "$brotli_pkg"` + else + brotli_reqpriv= + + if test "$have_brotli" != no; then + # BROTLI_CFLAGS and BROTLI_LIBS are set by the user + brotli_libspriv="$BROTLI_LIBS" + brotli_libsstaticconf="$BROTLI_LIBS" + have_brotli="yes (BROTLI_CFLAGS and BROTLI_LIBS)" + else + # since Brotli is quite a new library we don't fall back to a + # different test + : + fi + fi +fi + +if test x"$with_brotli" = xyes -a "$have_brotli" = no; then + as_fn_error $? "brotli support requested but library not found" "$LINENO" 5 +fi + + +# Checks for the demo programs. +# +# FreeType doesn't need this. However, since the demo program repository +# doesn't come with a `configure` script of its own, we integrate the tests +# here for simplicity. + +# We need `clock_gettime` from 'librt' for the `ftbench` demo program. +# +# The code is modeled after gnulib's file `clock_time.m4`, ignoring +# very old Solaris systems. +LIB_CLOCK_GETTIME= +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for library containing clock_gettime" >&5 +printf %s "checking for library containing clock_gettime... " >&6; } +if test ${ac_cv_search_clock_gettime+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ac_func_search_save_LIBS=$LIBS +cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +/* Override any GCC internal prototype to avoid an error. + Use char because int might match the return type of a GCC + builtin and then its argument prototype would still apply. */ +char clock_gettime (); +int +main (void) +{ +return clock_gettime (); + ; + return 0; +} +_ACEOF +for ac_lib in '' rt +do + if test -z "$ac_lib"; then + ac_res="none required" + else + ac_res=-l$ac_lib + LIBS="-l$ac_lib $ac_func_search_save_LIBS" + fi + if ac_fn_c_try_link "$LINENO" +then : + ac_cv_search_clock_gettime=$ac_res +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext + if test ${ac_cv_search_clock_gettime+y} +then : + break +fi +done +if test ${ac_cv_search_clock_gettime+y} +then : + +else $as_nop + ac_cv_search_clock_gettime=no +fi +rm conftest.$ac_ext +LIBS=$ac_func_search_save_LIBS +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_search_clock_gettime" >&5 +printf "%s\n" "$ac_cv_search_clock_gettime" >&6; } +ac_res=$ac_cv_search_clock_gettime +if test "$ac_res" != no +then : + test "$ac_res" = "none required" || LIBS="$ac_res $LIBS" + test "$ac_cv_search_clock_gettime" = "none required" \ + || LIB_CLOCK_GETTIME=$ac_cv_search_clock_gettime +fi + + +FT_DEMO_CFLAGS="" +FT_DEMO_LDFLAGS="$LIB_CLOCK_GETTIME" + +# 'librsvg' is needed to demonstrate SVG support. + +# Check whether --with-librsvg was given. +if test ${with_librsvg+y} +then : + withval=$with_librsvg; +else $as_nop + with_librsvg=auto +fi + + +have_librsvg=no +if test x"$with_librsvg" = xyes -o x"$with_librsvg" = xauto; then + +pkg_failed=no +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for LIBRSVG" >&5 +printf %s "checking for LIBRSVG... " >&6; } + +if test -n "$LIBRSVG_CFLAGS"; then + pkg_cv_LIBRSVG_CFLAGS="$LIBRSVG_CFLAGS" + elif test -n "$PKG_CONFIG"; then + if test -n "$PKG_CONFIG" && \ + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"librsvg-2.0 >= 2.46.0\""; } >&5 + ($PKG_CONFIG --exists --print-errors "librsvg-2.0 >= 2.46.0") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + pkg_cv_LIBRSVG_CFLAGS=`$PKG_CONFIG --cflags "librsvg-2.0 >= 2.46.0" 2>/dev/null` + test "x$?" != "x0" && pkg_failed=yes +else + pkg_failed=yes +fi + else + pkg_failed=untried +fi +if test -n "$LIBRSVG_LIBS"; then + pkg_cv_LIBRSVG_LIBS="$LIBRSVG_LIBS" + elif test -n "$PKG_CONFIG"; then + if test -n "$PKG_CONFIG" && \ + { { printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"librsvg-2.0 >= 2.46.0\""; } >&5 + ($PKG_CONFIG --exists --print-errors "librsvg-2.0 >= 2.46.0") 2>&5 + ac_status=$? + printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 + test $ac_status = 0; }; then + pkg_cv_LIBRSVG_LIBS=`$PKG_CONFIG --libs "librsvg-2.0 >= 2.46.0" 2>/dev/null` + test "x$?" != "x0" && pkg_failed=yes +else + pkg_failed=yes +fi + else + pkg_failed=untried +fi + + + +if test $pkg_failed = yes; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } + +if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then + _pkg_short_errors_supported=yes +else + _pkg_short_errors_supported=no +fi + if test $_pkg_short_errors_supported = yes; then + LIBRSVG_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "librsvg-2.0 >= 2.46.0" 2>&1` + else + LIBRSVG_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "librsvg-2.0 >= 2.46.0" 2>&1` + fi + # Put the nasty error message in config.log where it belongs + echo "$LIBRSVG_PKG_ERRORS" >&5 + + : +elif test $pkg_failed = untried; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } + : +else + LIBRSVG_CFLAGS=$pkg_cv_LIBRSVG_CFLAGS + LIBRSVG_LIBS=$pkg_cv_LIBRSVG_LIBS + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +printf "%s\n" "yes" >&6; } + have_librsvg="yes (pkg-config)" +fi + + if test "$have_librsvg" != no; then + FT_DEMO_CFLAGS="$FT_DEMO_CFLAGS $LIBRSVG_CFLAGS -DHAVE_LIBRSVG" + FT_DEMO_LDFLAGS="$FT_DEMO_LDFLAGS $LIBRSVG_LIBS" + fi +fi + +if test x"$with_librsvg" = xyes -a "$have_librsvg" = no; then + as_fn_error $? "librsvg support requested but library not found" "$LINENO" 5 +fi + + + + + +# Some options handling SDKs/archs in CFLAGS should be copied +# to LDFLAGS. Apple TechNote 2137 recommends to include these +# options in CFLAGS but not in LDFLAGS. + +save_config_args=$* +set dummy ${CFLAGS} +i=1 +while test $i -le $# +do + c=$1 + + case "${c}" in + -isysroot|-arch) # options taking 1 argument + a=$2 + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether CFLAGS and LDFLAGS share ${c} ${a}" >&5 +printf %s "checking whether CFLAGS and LDFLAGS share ${c} ${a}... " >&6; } + if expr " ${LDFLAGS} " : ".* ${c} *${a}.*" > /dev/null + then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +printf "%s\n" "yes" >&6; } + else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no, copy to LDFLAGS" >&5 +printf "%s\n" "no, copy to LDFLAGS" >&6; } + LDFLAGS="${LDFLAGS} ${c} ${a}" + fi + shift 1 + ;; + -m32|-m64|-march=*|-mcpu=*) # options taking no argument + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether CFLAGS and LDFLAGS share ${c}" >&5 +printf %s "checking whether CFLAGS and LDFLAGS share ${c}... " >&6; } + if expr " ${LDFLAGS} " : ".* ${c} *${a}.*" > /dev/null + then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +printf "%s\n" "yes" >&6; } + else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no, copy to LDFLAGS" >&5 +printf "%s\n" "no, copy to LDFLAGS" >&6; } + LDFLAGS="${LDFLAGS} ${c}" + fi + ;; + # *) + # AC_MSG_RESULT([${c} is not copied to LDFLAGS]) + # ;; + esac + + shift 1 +done +set ${save_config_args} + + +# Whether to use Mac OS resource-based fonts. + +ftmac_c="" # src/base/ftmac.c should not be included in makefiles by default + + +# Check whether --with-old-mac-fonts was given. +if test ${with_old_mac_fonts+y} +then : + withval=$with_old_mac_fonts; +fi + +if test x$with_old_mac_fonts = xyes; then + orig_LDFLAGS="${LDFLAGS}" + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking CoreServices & ApplicationServices of Mac OS X" >&5 +printf %s "checking CoreServices & ApplicationServices of Mac OS X... " >&6; } + ft2_extra_libs="-Wl,-framework,CoreServices -Wl,-framework,ApplicationServices" + LDFLAGS="$LDFLAGS $ft2_extra_libs" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + + + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + +int +main (void) +{ + + + short res = 0; + + + UseResFile( res ); + + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: ok" >&5 +printf "%s\n" "ok" >&6; } + ftmac_c='ftmac.c' + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether OS_INLINE macro is ANSI compatible" >&5 +printf %s "checking whether OS_INLINE macro is ANSI compatible... " >&6; } + orig_CFLAGS="$CFLAGS -DFT_MACINTOSH" + CFLAGS="$CFLAGS $XX_CFLAGS $XX_ANSIFLAGS" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + + + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + +int +main (void) +{ + + + /* OSHostByteOrder() is typed as OS_INLINE */ + int32_t os_byte_order = OSHostByteOrder(); + + + if ( OSBigEndian != os_byte_order ) + return 1; + + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: ok" >&5 +printf "%s\n" "ok" >&6; } + CFLAGS="$orig_CFLAGS" + CFLAGS="$CFLAGS -DHAVE_ANSI_OS_INLINE=1" + +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no, ANSI incompatible" >&5 +printf "%s\n" "no, ANSI incompatible" >&6; } + CFLAGS="$orig_CFLAGS" + +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking type ResourceIndex" >&5 +printf %s "checking type ResourceIndex... " >&6; } + orig_CFLAGS="$CFLAGS" + CFLAGS="$CFLAGS $XX_CFLAGS $XX_ANSIFLAGS" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + + + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +# include +#endif + + +int +main (void) +{ + + + ResourceIndex i = 0; + return i; + + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_compile "$LINENO" +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: ok" >&5 +printf "%s\n" "ok" >&6; } + CFLAGS="$orig_CFLAGS" + CFLAGS="$CFLAGS -DHAVE_TYPE_RESOURCE_INDEX=1" + +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } + CFLAGS="$orig_CFLAGS" + CFLAGS="$CFLAGS -DHAVE_TYPE_RESOURCE_INDEX=0" + +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: not found" >&5 +printf "%s\n" "not found" >&6; } + ft2_extra_libs="" + LDFLAGS="${orig_LDFLAGS}" + CFLAGS="$CFLAGS -DDARWIN_NO_CARBON" +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext +else + case x$host_os in + xdarwin*) + CFLAGS="$CFLAGS -DDARWIN_NO_CARBON" + ;; + *) + ;; + esac +fi + + +# Whether to use FileManager, which is deprecated since Mac OS X 10.4. + + +# Check whether --with-fsspec was given. +if test ${with_fsspec+y} +then : + withval=$with_fsspec; +fi + +if test x$with_fsspec = xno; then + CFLAGS="$CFLAGS -DHAVE_FSSPEC=0" +elif test x$with_old_mac_fonts = xyes -a x$with_fsspec != x; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking FSSpec-based FileManager" >&5 +printf %s "checking FSSpec-based FileManager... " >&6; } + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + + + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + +int +main (void) +{ + + + FCBPBPtr paramBlock; + short vRefNum; + long dirID; + ConstStr255Param fileName; + FSSpec* spec; + + + /* FSSpec functions: deprecated since Mac OS X 10.4 */ + PBGetFCBInfoSync( paramBlock ); + FSMakeFSSpec( vRefNum, dirID, fileName, spec ); + + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: ok" >&5 +printf "%s\n" "ok" >&6; } + CFLAGS="$CFLAGS -DHAVE_FSSPEC=1" +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: not found" >&5 +printf "%s\n" "not found" >&6; } + CFLAGS="$CFLAGS -DHAVE_FSSPEC=0" +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext +fi + + +# Whether to use FileManager in Carbon since MacOS 9.x. + + +# Check whether --with-fsref was given. +if test ${with_fsref+y} +then : + withval=$with_fsref; +fi + +if test x$with_fsref = xno; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: +*** WARNING + FreeType2 built without FSRef API cannot load + data-fork fonts on MacOS, except of XXX.dfont. + " >&5 +printf "%s\n" "$as_me: WARNING: +*** WARNING + FreeType2 built without FSRef API cannot load + data-fork fonts on MacOS, except of XXX.dfont. + " >&2;} + CFLAGS="$CFLAGS -DHAVE_FSREF=0" +elif test x$with_old_mac_fonts = xyes -a x$with_fsref != x; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking FSRef-based FileManager" >&5 +printf %s "checking FSRef-based FileManager... " >&6; } + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + + + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + +int +main (void) +{ + + + short vRefNum; + long dirID; + ConstStr255Param fileName; + + Boolean* isDirectory; + UInt8* path; + SInt16 desiredRefNum; + SInt16* iterator; + SInt16* actualRefNum; + HFSUniStr255* outForkName; + FSVolumeRefNum volume; + FSCatalogInfoBitmap whichInfo; + FSCatalogInfo* catalogInfo; + FSForkInfo* forkInfo; + FSRef* ref; + +#if HAVE_FSSPEC + FSSpec* spec; +#endif + + /* FSRef functions: no need to check? */ + FSGetForkCBInfo( desiredRefNum, volume, iterator, + actualRefNum, forkInfo, ref, + outForkName ); + FSPathMakeRef( path, ref, isDirectory ); + +#if HAVE_FSSPEC + FSpMakeFSRef ( spec, ref ); + FSGetCatalogInfo( ref, whichInfo, catalogInfo, + outForkName, spec, ref ); +#endif + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: ok" >&5 +printf "%s\n" "ok" >&6; } + CFLAGS="$CFLAGS -DHAVE_FSREF=1" +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: not found" >&5 +printf "%s\n" "not found" >&6; } + CFLAGS="$CFLAGS -DHAVE_FSREF=0" +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext +fi + + +# Whether to use QuickDraw API in ToolBox, which is deprecated since +# Mac OS X 10.4. + + +# Check whether --with-quickdraw-toolbox was given. +if test ${with_quickdraw_toolbox+y} +then : + withval=$with_quickdraw_toolbox; +fi + +if test x$with_quickdraw_toolbox = xno; then + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_TOOLBOX=0" +elif test x$with_old_mac_fonts = xyes -a x$with_quickdraw_toolbox != x; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking QuickDraw FontManager functions in ToolBox" >&5 +printf %s "checking QuickDraw FontManager functions in ToolBox... " >&6; } + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + + + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + +int +main (void) +{ + + + Str255 familyName; + SInt16 familyID = 0; + FMInput* fmIn = NULL; + FMOutput* fmOut = NULL; + + + GetFontName( familyID, familyName ); + GetFNum( familyName, &familyID ); + fmOut = FMSwapFont( fmIn ); + + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: ok" >&5 +printf "%s\n" "ok" >&6; } + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_TOOLBOX=1" +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: not found" >&5 +printf "%s\n" "not found" >&6; } + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_TOOLBOX=0" +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext +fi + + +# Whether to use QuickDraw API in Carbon, which is deprecated since +# Mac OS X 10.4. + + +# Check whether --with-quickdraw-carbon was given. +if test ${with_quickdraw_carbon+y} +then : + withval=$with_quickdraw_carbon; +fi + +if test x$with_quickdraw_carbon = xno; then + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_CARBON=0" +elif test x$with_old_mac_fonts = xyes -a x$with_quickdraw_carbon != x; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking QuickDraw FontManager functions in Carbon" >&5 +printf %s "checking QuickDraw FontManager functions in Carbon... " >&6; } + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + + + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + +int +main (void) +{ + + + FMFontFamilyIterator famIter; + FMFontFamily family; + Str255 famNameStr; + FMFontFamilyInstanceIterator instIter; + FMFontStyle style; + FMFontSize size; + FMFont font; + FSSpec* pathSpec; + + + FMCreateFontFamilyIterator( NULL, NULL, kFMUseGlobalScopeOption, + &famIter ); + FMGetNextFontFamily( &famIter, &family ); + FMGetFontFamilyName( family, famNameStr ); + FMCreateFontFamilyInstanceIterator( family, &instIter ); + FMGetNextFontFamilyInstance( &instIter, &font, &style, &size ); + FMDisposeFontFamilyInstanceIterator( &instIter ); + FMDisposeFontFamilyIterator( &famIter ); + FMGetFontContainer( font, pathSpec ); + + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: ok" >&5 +printf "%s\n" "ok" >&6; } + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_CARBON=1" +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: not found" >&5 +printf "%s\n" "not found" >&6; } + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_CARBON=0" +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext +fi + + +# Whether to use AppleTypeService since Mac OS X. + + +# Check whether --with-ats was given. +if test ${with_ats+y} +then : + withval=$with_ats; +fi + +if test x$with_ats = xno; then + CFLAGS="$CFLAGS -DHAVE_ATS=0" +elif test x$with_old_mac_fonts = xyes -a x$with_ats != x; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking AppleTypeService functions" >&5 +printf %s "checking AppleTypeService functions... " >&6; } + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + + + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + +int +main (void) +{ + + + FSSpec* pathSpec; + + + ATSFontFindFromName( NULL, kATSOptionFlagsUnRestrictedScope ); +#if HAVE_FSSPEC + ATSFontGetFileSpecification( 0, pathSpec ); +#endif + + + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: ok" >&5 +printf "%s\n" "ok" >&6; } + CFLAGS="$CFLAGS -DHAVE_ATS=1" +else $as_nop + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: not found" >&5 +printf "%s\n" "not found" >&6; } + CFLAGS="$CFLAGS -DHAVE_ATS=0" +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext +fi + +case "$CFLAGS" in + *HAVE_FSSPEC* | *HAVE_FSREF* | *HAVE_QUICKDRAW* | *HAVE_ATS* ) + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: +*** WARNING + FSSpec/FSRef/QuickDraw/ATS options are explicitly given, + thus it is recommended to replace src/base/ftmac.c by builds/mac/ftmac.c. + " >&5 +printf "%s\n" "$as_me: WARNING: +*** WARNING + FSSpec/FSRef/QuickDraw/ATS options are explicitly given, + thus it is recommended to replace src/base/ftmac.c by builds/mac/ftmac.c. + " >&2;} + CFLAGS="$CFLAGS "'-I$(TOP_DIR)/builds/mac/' + ;; + *) + ;; +esac + +# Check for pthreads + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking target system type" >&5 +printf %s "checking target system type... " >&6; } +if test ${ac_cv_target+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test "x$target_alias" = x; then + ac_cv_target=$ac_cv_host +else + ac_cv_target=`$SHELL "${ac_aux_dir}config.sub" $target_alias` || + as_fn_error $? "$SHELL ${ac_aux_dir}config.sub $target_alias failed" "$LINENO" 5 +fi + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ac_cv_target" >&5 +printf "%s\n" "$ac_cv_target" >&6; } +case $ac_cv_target in +*-*-*) ;; +*) as_fn_error $? "invalid value of canonical target" "$LINENO" 5;; +esac +target=$ac_cv_target +ac_save_IFS=$IFS; IFS='-' +set x $ac_cv_target +shift +target_cpu=$1 +target_vendor=$2 +shift; shift +# Remember, the first character of IFS is used to create $*, +# except with old shells: +target_os=$* +IFS=$ac_save_IFS +case $target_os in *\ *) target_os=`echo "$target_os" | sed 's/ /-/g'`;; esac + + +# The aliases save the names the user supplied, while $host etc. +# will get canonicalized. +test -n "$target_alias" && + test "$program_prefix$program_suffix$program_transform_name" = \ + NONENONEs,x,x, && + program_prefix=${target_alias}- + + + + + +ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu + +ax_pthread_ok=no + +# We used to check for pthread.h first, but this fails if pthread.h +# requires special compiler flags (e.g. on Tru64 or Sequent). +# It gets checked for in the link test anyway. + +# First of all, check if the user has set any of the PTHREAD_LIBS, +# etcetera environment variables, and if threads linking works using +# them: +if test "x$PTHREAD_CFLAGS$PTHREAD_LIBS" != "x"; then + ax_pthread_save_CC="$CC" + ax_pthread_save_CFLAGS="$CFLAGS" + ax_pthread_save_LIBS="$LIBS" + if test "x$PTHREAD_CC" != "x" +then : + CC="$PTHREAD_CC" +fi + if test "x$PTHREAD_CXX" != "x" +then : + CXX="$PTHREAD_CXX" +fi + CFLAGS="$CFLAGS $PTHREAD_CFLAGS" + LIBS="$PTHREAD_LIBS $LIBS" + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for pthread_join using $CC $PTHREAD_CFLAGS $PTHREAD_LIBS" >&5 +printf %s "checking for pthread_join using $CC $PTHREAD_CFLAGS $PTHREAD_LIBS... " >&6; } + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +/* Override any GCC internal prototype to avoid an error. + Use char because int might match the return type of a GCC + builtin and then its argument prototype would still apply. */ +char pthread_join (); +int +main (void) +{ +return pthread_join (); + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + ax_pthread_ok=yes +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ax_pthread_ok" >&5 +printf "%s\n" "$ax_pthread_ok" >&6; } + if test "x$ax_pthread_ok" = "xno"; then + PTHREAD_LIBS="" + PTHREAD_CFLAGS="" + fi + CC="$ax_pthread_save_CC" + CFLAGS="$ax_pthread_save_CFLAGS" + LIBS="$ax_pthread_save_LIBS" +fi + +# We must check for the threads library under a number of different +# names; the ordering is very important because some systems +# (e.g. DEC) have both -lpthread and -lpthreads, where one of the +# libraries is broken (non-POSIX). + +# Create a list of thread flags to try. Items with a "," contain both +# C compiler flags (before ",") and linker flags (after ","). Other items +# starting with a "-" are C compiler flags, and remaining items are +# library names, except for "none" which indicates that we try without +# any flags at all, and "pthread-config" which is a program returning +# the flags for the Pth emulation library. + +ax_pthread_flags="pthreads none -Kthread -pthread -pthreads -mthreads pthread --thread-safe -mt pthread-config" + +# The ordering *is* (sometimes) important. Some notes on the +# individual items follow: + +# pthreads: AIX (must check this before -lpthread) +# none: in case threads are in libc; should be tried before -Kthread and +# other compiler flags to prevent continual compiler warnings +# -Kthread: Sequent (threads in libc, but -Kthread needed for pthread.h) +# -pthread: Linux/gcc (kernel threads), BSD/gcc (userland threads), Tru64 +# (Note: HP C rejects this with "bad form for `-t' option") +# -pthreads: Solaris/gcc (Note: HP C also rejects) +# -mt: Sun Workshop C (may only link SunOS threads [-lthread], but it +# doesn't hurt to check since this sometimes defines pthreads and +# -D_REENTRANT too), HP C (must be checked before -lpthread, which +# is present but should not be used directly; and before -mthreads, +# because the compiler interprets this as "-mt" + "-hreads") +# -mthreads: Mingw32/gcc, Lynx/gcc +# pthread: Linux, etcetera +# --thread-safe: KAI C++ +# pthread-config: use pthread-config program (for GNU Pth library) + +case $target_os in + + freebsd*) + + # -kthread: FreeBSD kernel threads (preferred to -pthread since SMP-able) + # lthread: LinuxThreads port on FreeBSD (also preferred to -pthread) + + ax_pthread_flags="-kthread lthread $ax_pthread_flags" + ;; + + hpux*) + + # From the cc(1) man page: "[-mt] Sets various -D flags to enable + # multi-threading and also sets -lpthread." + + ax_pthread_flags="-mt -pthread pthread $ax_pthread_flags" + ;; + + openedition*) + + # IBM z/OS requires a feature-test macro to be defined in order to + # enable POSIX threads at all, so give the user a hint if this is + # not set. (We don't define these ourselves, as they can affect + # other portions of the system API in unpredictable ways.) + + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ + +# if !defined(_OPEN_THREADS) && !defined(_UNIX03_THREADS) + AX_PTHREAD_ZOS_MISSING +# endif + +_ACEOF +if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | + $EGREP "AX_PTHREAD_ZOS_MISSING" >/dev/null 2>&1 +then : + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: IBM z/OS requires -D_OPEN_THREADS or -D_UNIX03_THREADS to enable pthreads support." >&5 +printf "%s\n" "$as_me: WARNING: IBM z/OS requires -D_OPEN_THREADS or -D_UNIX03_THREADS to enable pthreads support." >&2;} +fi +rm -rf conftest* + + ;; + + solaris*) + + # On Solaris (at least, for some versions), libc contains stubbed + # (non-functional) versions of the pthreads routines, so link-based + # tests will erroneously succeed. (N.B.: The stubs are missing + # pthread_cleanup_push, or rather a function called by this macro, + # so we could check for that, but who knows whether they'll stub + # that too in a future libc.) So we'll check first for the + # standard Solaris way of linking pthreads (-mt -lpthread). + + ax_pthread_flags="-mt,-lpthread pthread $ax_pthread_flags" + ;; +esac + +# Are we compiling with Clang? + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether $CC is Clang" >&5 +printf %s "checking whether $CC is Clang... " >&6; } +if test ${ax_cv_PTHREAD_CLANG+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ax_cv_PTHREAD_CLANG=no + # Note that Autoconf sets GCC=yes for Clang as well as GCC + if test "x$GCC" = "xyes"; then + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +/* Note: Clang 2.7 lacks __clang_[a-z]+__ */ +# if defined(__clang__) && defined(__llvm__) + AX_PTHREAD_CC_IS_CLANG +# endif + +_ACEOF +if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | + $EGREP "AX_PTHREAD_CC_IS_CLANG" >/dev/null 2>&1 +then : + ax_cv_PTHREAD_CLANG=yes +fi +rm -rf conftest* + + fi + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ax_cv_PTHREAD_CLANG" >&5 +printf "%s\n" "$ax_cv_PTHREAD_CLANG" >&6; } +ax_pthread_clang="$ax_cv_PTHREAD_CLANG" + + +# GCC generally uses -pthread, or -pthreads on some platforms (e.g. SPARC) + +# Note that for GCC and Clang -pthread generally implies -lpthread, +# except when -nostdlib is passed. +# This is problematic using libtool to build C++ shared libraries with pthread: +# [1] https://gcc.gnu.org/bugzilla/show_bug.cgi?id=25460 +# [2] https://bugzilla.redhat.com/show_bug.cgi?id=661333 +# [3] https://bugs.debian.org/cgi-bin/bugreport.cgi?bug=468555 +# To solve this, first try -pthread together with -lpthread for GCC + +if test "x$GCC" = "xyes" +then : + ax_pthread_flags="-pthread,-lpthread -pthread -pthreads $ax_pthread_flags" +fi + +# Clang takes -pthread (never supported any other flag), but we'll try with -lpthread first + +if test "x$ax_pthread_clang" = "xyes" +then : + ax_pthread_flags="-pthread,-lpthread -pthread" +fi + + +# The presence of a feature test macro requesting re-entrant function +# definitions is, on some systems, a strong hint that pthreads support is +# correctly enabled + +case $target_os in + darwin* | hpux* | linux* | osf* | solaris*) + ax_pthread_check_macro="_REENTRANT" + ;; + + aix*) + ax_pthread_check_macro="_THREAD_SAFE" + ;; + + *) + ax_pthread_check_macro="--" + ;; +esac +if test "x$ax_pthread_check_macro" = "x--" +then : + ax_pthread_check_cond=0 +else $as_nop + ax_pthread_check_cond="!defined($ax_pthread_check_macro)" +fi + + +if test "x$ax_pthread_ok" = "xno"; then +for ax_pthread_try_flag in $ax_pthread_flags; do + + case $ax_pthread_try_flag in + none) + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether pthreads work without any flags" >&5 +printf %s "checking whether pthreads work without any flags... " >&6; } + ;; + + *,*) + PTHREAD_CFLAGS=`echo $ax_pthread_try_flag | sed "s/^\(.*\),\(.*\)$/\1/"` + PTHREAD_LIBS=`echo $ax_pthread_try_flag | sed "s/^\(.*\),\(.*\)$/\2/"` + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether pthreads work with \"$PTHREAD_CFLAGS\" and \"$PTHREAD_LIBS\"" >&5 +printf %s "checking whether pthreads work with \"$PTHREAD_CFLAGS\" and \"$PTHREAD_LIBS\"... " >&6; } + ;; + + -*) + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether pthreads work with $ax_pthread_try_flag" >&5 +printf %s "checking whether pthreads work with $ax_pthread_try_flag... " >&6; } + PTHREAD_CFLAGS="$ax_pthread_try_flag" + ;; + + pthread-config) + # Extract the first word of "pthread-config", so it can be a program name with args. +set dummy pthread-config; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_ax_pthread_config+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$ax_pthread_config"; then + ac_cv_prog_ax_pthread_config="$ax_pthread_config" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_ax_pthread_config="yes" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + + test -z "$ac_cv_prog_ax_pthread_config" && ac_cv_prog_ax_pthread_config="no" +fi +fi +ax_pthread_config=$ac_cv_prog_ax_pthread_config +if test -n "$ax_pthread_config"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ax_pthread_config" >&5 +printf "%s\n" "$ax_pthread_config" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + if test "x$ax_pthread_config" = "xno" +then : + continue +fi + PTHREAD_CFLAGS="`pthread-config --cflags`" + PTHREAD_LIBS="`pthread-config --ldflags` `pthread-config --libs`" + ;; + + *) + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for the pthreads library -l$ax_pthread_try_flag" >&5 +printf %s "checking for the pthreads library -l$ax_pthread_try_flag... " >&6; } + PTHREAD_LIBS="-l$ax_pthread_try_flag" + ;; + esac + + ax_pthread_save_CFLAGS="$CFLAGS" + ax_pthread_save_LIBS="$LIBS" + CFLAGS="$CFLAGS $PTHREAD_CFLAGS" + LIBS="$PTHREAD_LIBS $LIBS" + + # Check for various functions. We must include pthread.h, + # since some functions may be macros. (On the Sequent, we + # need a special flag -Kthread to make this header compile.) + # We check for pthread_join because it is in -lpthread on IRIX + # while pthread_create is in libc. We check for pthread_attr_init + # due to DEC craziness with -lpthreads. We check for + # pthread_cleanup_push because it is one of the few pthread + # functions on Solaris that doesn't have a non-functional libc stub. + # We try pthread_create on general principles. + + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#include +# if $ax_pthread_check_cond +# error "$ax_pthread_check_macro must be defined" +# endif + static void *some_global = NULL; + static void routine(void *a) + { + /* To avoid any unused-parameter or + unused-but-set-parameter warning. */ + some_global = a; + } + static void *start_routine(void *a) { return a; } +int +main (void) +{ +pthread_t th; pthread_attr_t attr; + pthread_create(&th, 0, start_routine, 0); + pthread_join(th, 0); + pthread_attr_init(&attr); + pthread_cleanup_push(routine, 0); + pthread_cleanup_pop(0) /* ; */ + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + ax_pthread_ok=yes +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext + + CFLAGS="$ax_pthread_save_CFLAGS" + LIBS="$ax_pthread_save_LIBS" + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ax_pthread_ok" >&5 +printf "%s\n" "$ax_pthread_ok" >&6; } + if test "x$ax_pthread_ok" = "xyes" +then : + break +fi + + PTHREAD_LIBS="" + PTHREAD_CFLAGS="" +done +fi + + +# Clang needs special handling, because older versions handle the -pthread +# option in a rather... idiosyncratic way + +if test "x$ax_pthread_clang" = "xyes"; then + + # Clang takes -pthread; it has never supported any other flag + + # (Note 1: This will need to be revisited if a system that Clang + # supports has POSIX threads in a separate library. This tends not + # to be the way of modern systems, but it's conceivable.) + + # (Note 2: On some systems, notably Darwin, -pthread is not needed + # to get POSIX threads support; the API is always present and + # active. We could reasonably leave PTHREAD_CFLAGS empty. But + # -pthread does define _REENTRANT, and while the Darwin headers + # ignore this macro, third-party headers might not.) + + # However, older versions of Clang make a point of warning the user + # that, in an invocation where only linking and no compilation is + # taking place, the -pthread option has no effect ("argument unused + # during compilation"). They expect -pthread to be passed in only + # when source code is being compiled. + # + # Problem is, this is at odds with the way Automake and most other + # C build frameworks function, which is that the same flags used in + # compilation (CFLAGS) are also used in linking. Many systems + # supported by AX_PTHREAD require exactly this for POSIX threads + # support, and in fact it is often not straightforward to specify a + # flag that is used only in the compilation phase and not in + # linking. Such a scenario is extremely rare in practice. + # + # Even though use of the -pthread flag in linking would only print + # a warning, this can be a nuisance for well-run software projects + # that build with -Werror. So if the active version of Clang has + # this misfeature, we search for an option to squash it. + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether Clang needs flag to prevent \"argument unused\" warning when linking with -pthread" >&5 +printf %s "checking whether Clang needs flag to prevent \"argument unused\" warning when linking with -pthread... " >&6; } +if test ${ax_cv_PTHREAD_CLANG_NO_WARN_FLAG+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ax_cv_PTHREAD_CLANG_NO_WARN_FLAG=unknown + # Create an alternate version of $ac_link that compiles and + # links in two steps (.c -> .o, .o -> exe) instead of one + # (.c -> exe), because the warning occurs only in the second + # step + ax_pthread_save_ac_link="$ac_link" + ax_pthread_sed='s/conftest\.\$ac_ext/conftest.$ac_objext/g' + ax_pthread_link_step=`printf "%s\n" "$ac_link" | sed "$ax_pthread_sed"` + ax_pthread_2step_ac_link="($ac_compile) && (echo ==== >&5) && ($ax_pthread_link_step)" + ax_pthread_save_CFLAGS="$CFLAGS" + for ax_pthread_try in '' -Qunused-arguments -Wno-unused-command-line-argument unknown; do + if test "x$ax_pthread_try" = "xunknown" +then : + break +fi + CFLAGS="-Werror -Wunknown-warning-option $ax_pthread_try -pthread $ax_pthread_save_CFLAGS" + ac_link="$ax_pthread_save_ac_link" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +int main(void){return 0;} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + ac_link="$ax_pthread_2step_ac_link" + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +int main(void){return 0;} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + break +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext + +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext + done + ac_link="$ax_pthread_save_ac_link" + CFLAGS="$ax_pthread_save_CFLAGS" + if test "x$ax_pthread_try" = "x" +then : + ax_pthread_try=no +fi + ax_cv_PTHREAD_CLANG_NO_WARN_FLAG="$ax_pthread_try" + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ax_cv_PTHREAD_CLANG_NO_WARN_FLAG" >&5 +printf "%s\n" "$ax_cv_PTHREAD_CLANG_NO_WARN_FLAG" >&6; } + + case "$ax_cv_PTHREAD_CLANG_NO_WARN_FLAG" in + no | unknown) ;; + *) PTHREAD_CFLAGS="$ax_cv_PTHREAD_CLANG_NO_WARN_FLAG $PTHREAD_CFLAGS" ;; + esac + +fi # $ax_pthread_clang = yes + + + +# Various other checks: +if test "x$ax_pthread_ok" = "xyes"; then + ax_pthread_save_CFLAGS="$CFLAGS" + ax_pthread_save_LIBS="$LIBS" + CFLAGS="$CFLAGS $PTHREAD_CFLAGS" + LIBS="$PTHREAD_LIBS $LIBS" + + # Detect AIX lossage: JOINABLE attribute is called UNDETACHED. + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for joinable pthread attribute" >&5 +printf %s "checking for joinable pthread attribute... " >&6; } +if test ${ax_cv_PTHREAD_JOINABLE_ATTR+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ax_cv_PTHREAD_JOINABLE_ATTR=unknown + for ax_pthread_attr in PTHREAD_CREATE_JOINABLE PTHREAD_CREATE_UNDETACHED; do + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#include +int +main (void) +{ +int attr = $ax_pthread_attr; return attr /* ; */ + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + ax_cv_PTHREAD_JOINABLE_ATTR=$ax_pthread_attr; break +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext + done + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ax_cv_PTHREAD_JOINABLE_ATTR" >&5 +printf "%s\n" "$ax_cv_PTHREAD_JOINABLE_ATTR" >&6; } + if test "x$ax_cv_PTHREAD_JOINABLE_ATTR" != "xunknown" && \ + test "x$ax_cv_PTHREAD_JOINABLE_ATTR" != "xPTHREAD_CREATE_JOINABLE" && \ + test "x$ax_pthread_joinable_attr_defined" != "xyes" +then : + +printf "%s\n" "#define PTHREAD_CREATE_JOINABLE $ax_cv_PTHREAD_JOINABLE_ATTR" >>confdefs.h + + ax_pthread_joinable_attr_defined=yes + +fi + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking whether more special flags are required for pthreads" >&5 +printf %s "checking whether more special flags are required for pthreads... " >&6; } +if test ${ax_cv_PTHREAD_SPECIAL_FLAGS+y} +then : + printf %s "(cached) " >&6 +else $as_nop + ax_cv_PTHREAD_SPECIAL_FLAGS=no + case $target_os in + solaris*) + ax_cv_PTHREAD_SPECIAL_FLAGS="-D_POSIX_PTHREAD_SEMANTICS" + ;; + esac + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ax_cv_PTHREAD_SPECIAL_FLAGS" >&5 +printf "%s\n" "$ax_cv_PTHREAD_SPECIAL_FLAGS" >&6; } + if test "x$ax_cv_PTHREAD_SPECIAL_FLAGS" != "xno" && \ + test "x$ax_pthread_special_flags_added" != "xyes" +then : + PTHREAD_CFLAGS="$ax_cv_PTHREAD_SPECIAL_FLAGS $PTHREAD_CFLAGS" + ax_pthread_special_flags_added=yes +fi + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for PTHREAD_PRIO_INHERIT" >&5 +printf %s "checking for PTHREAD_PRIO_INHERIT... " >&6; } +if test ${ax_cv_PTHREAD_PRIO_INHERIT+y} +then : + printf %s "(cached) " >&6 +else $as_nop + cat confdefs.h - <<_ACEOF >conftest.$ac_ext +/* end confdefs.h. */ +#include +int +main (void) +{ +int i = PTHREAD_PRIO_INHERIT; + return i; + ; + return 0; +} +_ACEOF +if ac_fn_c_try_link "$LINENO" +then : + ax_cv_PTHREAD_PRIO_INHERIT=yes +else $as_nop + ax_cv_PTHREAD_PRIO_INHERIT=no +fi +rm -f core conftest.err conftest.$ac_objext conftest.beam \ + conftest$ac_exeext conftest.$ac_ext + +fi +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $ax_cv_PTHREAD_PRIO_INHERIT" >&5 +printf "%s\n" "$ax_cv_PTHREAD_PRIO_INHERIT" >&6; } + if test "x$ax_cv_PTHREAD_PRIO_INHERIT" = "xyes" && \ + test "x$ax_pthread_prio_inherit_defined" != "xyes" +then : + +printf "%s\n" "#define HAVE_PTHREAD_PRIO_INHERIT 1" >>confdefs.h + + ax_pthread_prio_inherit_defined=yes + +fi + + CFLAGS="$ax_pthread_save_CFLAGS" + LIBS="$ax_pthread_save_LIBS" + + # More AIX lossage: compile with *_r variant + if test "x$GCC" != "xyes"; then + case $target_os in + aix*) + case "x/$CC" in #( + x*/c89|x*/c89_128|x*/c99|x*/c99_128|x*/cc|x*/cc128|x*/xlc|x*/xlc_v6|x*/xlc128|x*/xlc128_v6) : + #handle absolute path differently from PATH based program lookup + case "x$CC" in #( + x/*) : + + if as_fn_executable_p ${CC}_r +then : + PTHREAD_CC="${CC}_r" +fi + if test "x${CXX}" != "x" +then : + if as_fn_executable_p ${CXX}_r +then : + PTHREAD_CXX="${CXX}_r" +fi +fi + ;; #( + *) : + + for ac_prog in ${CC}_r +do + # Extract the first word of "$ac_prog", so it can be a program name with args. +set dummy $ac_prog; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_PTHREAD_CC+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$PTHREAD_CC"; then + ac_cv_prog_PTHREAD_CC="$PTHREAD_CC" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_PTHREAD_CC="$ac_prog" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +PTHREAD_CC=$ac_cv_prog_PTHREAD_CC +if test -n "$PTHREAD_CC"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $PTHREAD_CC" >&5 +printf "%s\n" "$PTHREAD_CC" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + test -n "$PTHREAD_CC" && break +done +test -n "$PTHREAD_CC" || PTHREAD_CC="$CC" + + if test "x${CXX}" != "x" +then : + for ac_prog in ${CXX}_r +do + # Extract the first word of "$ac_prog", so it can be a program name with args. +set dummy $ac_prog; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_PTHREAD_CXX+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$PTHREAD_CXX"; then + ac_cv_prog_PTHREAD_CXX="$PTHREAD_CXX" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_PTHREAD_CXX="$ac_prog" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +PTHREAD_CXX=$ac_cv_prog_PTHREAD_CXX +if test -n "$PTHREAD_CXX"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $PTHREAD_CXX" >&5 +printf "%s\n" "$PTHREAD_CXX" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + test -n "$PTHREAD_CXX" && break +done +test -n "$PTHREAD_CXX" || PTHREAD_CXX="$CXX" + +fi + + ;; +esac + ;; #( + *) : + ;; +esac + ;; + esac + fi +fi + +test -n "$PTHREAD_CC" || PTHREAD_CC="$CC" +test -n "$PTHREAD_CXX" || PTHREAD_CXX="$CXX" + + + + + + +# Finally, execute ACTION-IF-FOUND/ACTION-IF-NOT-FOUND: +if test "x$ax_pthread_ok" = "xyes"; then + have_pthread=yes + : +else + ax_pthread_ok=no + have_pthread=no +fi +ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu + + + +# Check for Python and docwriter +PYTHON_MIN_VERSION=3.5 +have_py3=no +have_docwriter=no +PIP=pip + +for ac_prog in python3 python +do + # Extract the first word of "$ac_prog", so it can be a program name with args. +set dummy $ac_prog; ac_word=$2 +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 +printf %s "checking for $ac_word... " >&6; } +if test ${ac_cv_prog_PYTHON+y} +then : + printf %s "(cached) " >&6 +else $as_nop + if test -n "$PYTHON"; then + ac_cv_prog_PYTHON="$PYTHON" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + for ac_exec_ext in '' $ac_executable_extensions; do + if as_fn_executable_p "$as_dir$ac_word$ac_exec_ext"; then + ac_cv_prog_PYTHON="$ac_prog" + printf "%s\n" "$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext" >&5 + break 2 + fi +done + done +IFS=$as_save_IFS + +fi +fi +PYTHON=$ac_cv_prog_PYTHON +if test -n "$PYTHON"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $PYTHON" >&5 +printf "%s\n" "$PYTHON" >&6; } +else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } +fi + + + test -n "$PYTHON" && break +done +test -n "$PYTHON" || PYTHON="missing" + +if test "x$PYTHON" != "xmissing"; then + + + + + if test -n "$PYTHON" +then : + + ax_python_version="$PYTHON_MIN_VERSION" + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for python version" >&5 +printf %s "checking for python version... " >&6; } + + python_version=`$PYTHON -V 2>&1 | $GREP "^Python " | $SED -e 's/^.* \([0-9]*\.[0-9]*\.[0-9]*\)/\1/'` + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $python_version" >&5 +printf "%s\n" "$python_version" >&6; } + + PYTHON_VERSION=$python_version + + + + + + # Used to indicate true or false condition + ax_compare_version=false + + # Convert the two version strings to be compared into a format that + # allows a simple string comparison. The end result is that a version + # string of the form 1.12.5-r617 will be converted to the form + # 0001001200050617. In other words, each number is zero padded to four + # digits, and non digits are removed. + + ax_compare_version_A=`echo "$ax_python_version" | sed -e 's/\([0-9]*\)/Z\1Z/g' \ + -e 's/Z\([0-9]\)Z/Z0\1Z/g' \ + -e 's/Z\([0-9][0-9]\)Z/Z0\1Z/g' \ + -e 's/Z\([0-9][0-9][0-9]\)Z/Z0\1Z/g' \ + -e 's/[^0-9]//g'` + + + ax_compare_version_B=`echo "$python_version" | sed -e 's/\([0-9]*\)/Z\1Z/g' \ + -e 's/Z\([0-9]\)Z/Z0\1Z/g' \ + -e 's/Z\([0-9][0-9]\)Z/Z0\1Z/g' \ + -e 's/Z\([0-9][0-9][0-9]\)Z/Z0\1Z/g' \ + -e 's/[^0-9]//g'` + + + ax_compare_version=`echo "x$ax_compare_version_A +x$ax_compare_version_B" | sed 's/^ *//' | sort | sed "s/x${ax_compare_version_A}/true/;s/x${ax_compare_version_B}/false/;1q"` + + + + if test "$ax_compare_version" = "true" ; then + + : + have_py3=yes + + else + : + + + fi + + +else $as_nop + + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: could not find the python interpreter" >&5 +printf "%s\n" "$as_me: WARNING: could not find the python interpreter" >&2;} + + +fi + + + if test "x$have_py3" = "xyes"; then + PIP="$PYTHON -m $PIP" + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking for \`docwriter' Python module" >&5 +printf %s "checking for \`docwriter' Python module... " >&6; } + $PYTHON -m docwriter -h > /dev/null 2>&1 + if test "x$?" = "x0"; then + have_docwriter=yes + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: yes" >&5 +printf "%s\n" "yes" >&6; } + else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: no" >&5 +printf "%s\n" "no" >&6; } + fi + fi +fi + + +# entries in Requires.private are separated by commas +PKGCONFIG_REQUIRES_PRIVATE="$zlib_reqpriv, \ + $bzip2_reqpriv, \ + $libpng_reqpriv, \ + $harfbuzz_reqpriv, \ + $brotli_reqpriv" +# beautify +PKGCONFIG_REQUIRES_PRIVATE=`echo "$PKGCONFIG_REQUIRES_PRIVATE" \ + | sed -e 's/^ *//' \ + -e 's/ *$//' \ + -e 's/, */,/g' \ + -e 's/,,*/,/g' \ + -e 's/^,*//' \ + -e 's/,*$//' \ + -e 's/,/, /g'` + +PKGCONFIG_LIBS_PRIVATE="$zlib_libspriv \ + $bzip2_libspriv \ + $libpng_libspriv \ + $harfbuzz_libspriv \ + $brotli_libspriv \ + $ft2_extra_libs" +# beautify +PKGCONFIG_LIBS_PRIVATE=`echo "$PKGCONFIG_LIBS_PRIVATE" \ + | sed -e 's/^ *//' \ + -e 's/ *$//' \ + -e 's/ */ /g'` + +LIBSSTATIC_CONFIG="-lfreetype \ + $zlib_libsstaticconf \ + $bzip2_libsstaticconf \ + $libpng_libsstaticconf \ + $harfbuzz_libsstaticconf \ + $brotli_libsstaticconf \ + $ft2_extra_libs" +# remove -L/usr/lib and -L/usr/lib64 since `freetype-config' adds them later +# on if necessary; also beautify +LIBSSTATIC_CONFIG=`echo "$LIBSSTATIC_CONFIG" \ + | sed -e 's|-L */usr/lib64/* | |g' \ + -e 's|-L */usr/lib/* | |g' \ + -e 's/^ *//' \ + -e 's/ *$//' \ + -e 's/ */ /g'` + +# If FreeType gets installed with `--disable-shared', don't use +# 'private' fields. `pkg-config' only looks into `.pc' files and is +# completely agnostic to whether shared libraries are actually present +# or not. As a consequence, the user had to specify `--static' while +# calling `pkg-config', which configure scripts are normally not +# prepared for. + +PKGCONFIG_REQUIRES= +PKGCONFIG_LIBS='-L${libdir} -lfreetype' + +if test $enable_shared = "no"; then + PKGCONFIG_REQUIRES="$PKGCONFIG_REQUIRES $PKGCONFIG_REQUIRES_PRIVATE" + PKGCONFIG_REQUIRES_PRIVATE= + PKGCONFIG_LIBS="$PKGCONFIG_LIBS $PKGCONFIG_LIBS_PRIVATE" + PKGCONFIG_LIBS_PRIVATE= +fi + + + + + + + + + + + + + +# changing LDFLAGS value should only be done after +# lt_cv_prog_compiler_static_works test + +ftoption_set() +{ + regexp="-e \\\"s|.*#.*def.*$1.*|#define $1|\\\"" + FTOPTION_H_SED="$FTOPTION_H_SED $regexp" +} + +ftoption_unset() +{ + regexp="-e \\\"s|.*#.*def.*$1.*|/* #undef $1 */|\\\"" + FTOPTION_H_SED="$FTOPTION_H_SED $regexp" +} + +if test "$have_zlib" != no; then + CFLAGS="$CFLAGS $ZLIB_CFLAGS" + LDFLAGS="$LDFLAGS $ZLIB_LIBS" + ftoption_set FT_CONFIG_OPTION_SYSTEM_ZLIB +else + ftoption_unset FT_CONFIG_OPTION_SYSTEM_ZLIB +fi +if test "$have_bzip2" != no; then + CFLAGS="$CFLAGS $BZIP2_CFLAGS" + LDFLAGS="$LDFLAGS $BZIP2_LIBS" + ftoption_set FT_CONFIG_OPTION_USE_BZIP2 +else + ftoption_unset FT_CONFIG_OPTION_USE_BZIP2 +fi +if test "$have_libpng" != no; then + CFLAGS="$CFLAGS $LIBPNG_CFLAGS" + LDFLAGS="$LDFLAGS $LIBPNG_LIBS" + ftoption_set FT_CONFIG_OPTION_USE_PNG +else + ftoption_unset FT_CONFIG_OPTION_USE_PNG +fi +if test "$have_harfbuzz" != no; then + CFLAGS="$CFLAGS $HARFBUZZ_CFLAGS" + LDFLAGS="$LDFLAGS $HARFBUZZ_LIBS" + ftoption_set FT_CONFIG_OPTION_USE_HARFBUZZ +else + ftoption_unset FT_CONFIG_OPTION_USE_HARFBUZZ +fi +if test "$have_brotli" != no; then + CFLAGS="$CFLAGS $BROTLI_CFLAGS" + LDFLAGS="$LDFLAGS $BROTLI_LIBS" + ftoption_set FT_CONFIG_OPTION_USE_BROTLI +else + ftoption_unset FT_CONFIG_OPTION_USE_BROTLI +fi + +if test "$have_pthread" != no; then + CFLAGS="$CFLAGS $PTHREAD_CFLAGS" + LDFLAGS="$LDFLAGS $PTHREAD_CFLAGS $PTHREAD_LIBS" +fi + + + + +# We don't want to use a template file for `ftoption.h', since compilation +# should work without calling a configure script also. For this reason, we +# copy the `include/freetype/config/ftoption.h' file to the `unix/builds' +# directory (using a dummy `AC_CONFIG_FILES' call) and apply the just +# constructed $FTOPTION_H_SED regexp (using the post-action of +# `AC_CONFIG_FILES'); this is also the version that gets installed later on. +# +ac_config_files="$ac_config_files ftoption.h:${srcdir}/../../include/freetype/config/ftoption.h" + + +ac_config_headers="$ac_config_headers ftconfig.h" + + +# create the Unix-specific sub-Makefiles `builds/unix/unix-def.mk' +# and `builds/unix/unix-cc.mk' that will be used by the build system +# +ac_config_files="$ac_config_files unix-cc.mk:unix-cc.in unix-def.mk:unix-def.in" + + +cat >confcache <<\_ACEOF +# This file is a shell script that caches the results of configure +# tests run on this system so they can be shared between configure +# scripts and configure runs, see configure's option --config-cache. +# It is not useful on other systems. If it contains results you don't +# want to keep, you may remove or edit it. +# +# config.status only pays attention to the cache file if you give it +# the --recheck option to rerun configure. +# +# `ac_cv_env_foo' variables (set or unset) will be overridden when +# loading this file, other *unset* `ac_cv_foo' will be assigned the +# following values. + +_ACEOF + +# The following way of writing the cache mishandles newlines in values, +# but we know of no workaround that is simple, portable, and efficient. +# So, we kill variables containing newlines. +# Ultrix sh set writes to stderr and can't be redirected directly, +# and sets the high bit in the cache file unless we assign to the vars. +( + for ac_var in `(set) 2>&1 | sed -n 's/^\([a-zA-Z_][a-zA-Z0-9_]*\)=.*/\1/p'`; do + eval ac_val=\$$ac_var + case $ac_val in #( + *${as_nl}*) + case $ac_var in #( + *_cv_*) { printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline" >&5 +printf "%s\n" "$as_me: WARNING: cache variable $ac_var contains a newline" >&2;} ;; + esac + case $ac_var in #( + _ | IFS | as_nl) ;; #( + BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #( + *) { eval $ac_var=; unset $ac_var;} ;; + esac ;; + esac + done + + (set) 2>&1 | + case $as_nl`(ac_space=' '; set) 2>&1` in #( + *${as_nl}ac_space=\ *) + # `set' does not quote correctly, so add quotes: double-quote + # substitution turns \\\\ into \\, and sed turns \\ into \. + sed -n \ + "s/'/'\\\\''/g; + s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='\\2'/p" + ;; #( + *) + # `set' quotes correctly as required by POSIX, so do not add quotes. + sed -n "/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p" + ;; + esac | + sort +) | + sed ' + /^ac_cv_env_/b end + t clear + :clear + s/^\([^=]*\)=\(.*[{}].*\)$/test ${\1+y} || &/ + t end + s/^\([^=]*\)=\(.*\)$/\1=${\1=\2}/ + :end' >>confcache +if diff "$cache_file" confcache >/dev/null 2>&1; then :; else + if test -w "$cache_file"; then + if test "x$cache_file" != "x/dev/null"; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: updating cache $cache_file" >&5 +printf "%s\n" "$as_me: updating cache $cache_file" >&6;} + if test ! -f "$cache_file" || test -h "$cache_file"; then + cat confcache >"$cache_file" + else + case $cache_file in #( + */* | ?:*) + mv -f confcache "$cache_file"$$ && + mv -f "$cache_file"$$ "$cache_file" ;; #( + *) + mv -f confcache "$cache_file" ;; + esac + fi + fi + else + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: not updating unwritable cache $cache_file" >&5 +printf "%s\n" "$as_me: not updating unwritable cache $cache_file" >&6;} + fi +fi +rm -f confcache + +test "x$prefix" = xNONE && prefix=$ac_default_prefix +# Let make expand exec_prefix. +test "x$exec_prefix" = xNONE && exec_prefix='${prefix}' + +DEFS=-DHAVE_CONFIG_H + +ac_libobjs= +ac_ltlibobjs= +U= +for ac_i in : $LIBOBJS; do test "x$ac_i" = x: && continue + # 1. Remove the extension, and $U if already installed. + ac_script='s/\$U\././;s/\.o$//;s/\.obj$//' + ac_i=`printf "%s\n" "$ac_i" | sed "$ac_script"` + # 2. Prepend LIBOBJDIR. When used with automake>=1.10 LIBOBJDIR + # will be set to the directory where LIBOBJS objects are built. + as_fn_append ac_libobjs " \${LIBOBJDIR}$ac_i\$U.$ac_objext" + as_fn_append ac_ltlibobjs " \${LIBOBJDIR}$ac_i"'$U.lo' +done +LIBOBJS=$ac_libobjs + +LTLIBOBJS=$ac_ltlibobjs + + + +: "${CONFIG_STATUS=./config.status}" +ac_write_fail=0 +ac_clean_files_save=$ac_clean_files +ac_clean_files="$ac_clean_files $CONFIG_STATUS" +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: creating $CONFIG_STATUS" >&5 +printf "%s\n" "$as_me: creating $CONFIG_STATUS" >&6;} +as_write_fail=0 +cat >$CONFIG_STATUS <<_ASEOF || as_write_fail=1 +#! $SHELL +# Generated by $as_me. +# Run this file to recreate the current configuration. +# Compiler output produced by configure, useful for debugging +# configure, is in config.log if it exists. + +debug=false +ac_cs_recheck=false +ac_cs_silent=false + +SHELL=\${CONFIG_SHELL-$SHELL} +export SHELL +_ASEOF +cat >>$CONFIG_STATUS <<\_ASEOF || as_write_fail=1 +## -------------------- ## +## M4sh Initialization. ## +## -------------------- ## + +# Be more Bourne compatible +DUALCASE=1; export DUALCASE # for MKS sh +as_nop=: +if test ${ZSH_VERSION+y} && (emulate sh) >/dev/null 2>&1 +then : + emulate sh + NULLCMD=: + # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which + # is contrary to our usage. Disable this feature. + alias -g '${1+"$@"}'='"$@"' + setopt NO_GLOB_SUBST +else $as_nop + case `(set -o) 2>/dev/null` in #( + *posix*) : + set -o posix ;; #( + *) : + ;; +esac +fi + + + +# Reset variables that may have inherited troublesome values from +# the environment. + +# IFS needs to be set, to space, tab, and newline, in precisely that order. +# (If _AS_PATH_WALK were called with IFS unset, it would have the +# side effect of setting IFS to empty, thus disabling word splitting.) +# Quoting is to prevent editors from complaining about space-tab. +as_nl=' +' +export as_nl +IFS=" "" $as_nl" + +PS1='$ ' +PS2='> ' +PS4='+ ' + +# Ensure predictable behavior from utilities with locale-dependent output. +LC_ALL=C +export LC_ALL +LANGUAGE=C +export LANGUAGE + +# We cannot yet rely on "unset" to work, but we need these variables +# to be unset--not just set to an empty or harmless value--now, to +# avoid bugs in old shells (e.g. pre-3.0 UWIN ksh). This construct +# also avoids known problems related to "unset" and subshell syntax +# in other old shells (e.g. bash 2.01 and pdksh 5.2.14). +for as_var in BASH_ENV ENV MAIL MAILPATH CDPATH +do eval test \${$as_var+y} \ + && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || : +done + +# Ensure that fds 0, 1, and 2 are open. +if (exec 3>&0) 2>/dev/null; then :; else exec 0&1) 2>/dev/null; then :; else exec 1>/dev/null; fi +if (exec 3>&2) ; then :; else exec 2>/dev/null; fi + +# The user is always right. +if ${PATH_SEPARATOR+false} :; then + PATH_SEPARATOR=: + (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && { + (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 || + PATH_SEPARATOR=';' + } +fi + + +# Find who we are. Look in the path if we contain no directory separator. +as_myself= +case $0 in #(( + *[\\/]* ) as_myself=$0 ;; + *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + case $as_dir in #((( + '') as_dir=./ ;; + */) ;; + *) as_dir=$as_dir/ ;; + esac + test -r "$as_dir$0" && as_myself=$as_dir$0 && break + done +IFS=$as_save_IFS + + ;; +esac +# We did not find ourselves, most probably we were run as `sh COMMAND' +# in which case we are not to be found in the path. +if test "x$as_myself" = x; then + as_myself=$0 +fi +if test ! -f "$as_myself"; then + printf "%s\n" "$as_myself: error: cannot find myself; rerun with an absolute file name" >&2 + exit 1 +fi + + + +# as_fn_error STATUS ERROR [LINENO LOG_FD] +# ---------------------------------------- +# Output "`basename $0`: error: ERROR" to stderr. If LINENO and LOG_FD are +# provided, also output the error to LOG_FD, referencing LINENO. Then exit the +# script with STATUS, using 1 if that was 0. +as_fn_error () +{ + as_status=$1; test $as_status -eq 0 && as_status=1 + if test "$4"; then + as_lineno=${as_lineno-"$3"} as_lineno_stack=as_lineno_stack=$as_lineno_stack + printf "%s\n" "$as_me:${as_lineno-$LINENO}: error: $2" >&$4 + fi + printf "%s\n" "$as_me: error: $2" >&2 + as_fn_exit $as_status +} # as_fn_error + + + +# as_fn_set_status STATUS +# ----------------------- +# Set $? to STATUS, without forking. +as_fn_set_status () +{ + return $1 +} # as_fn_set_status + +# as_fn_exit STATUS +# ----------------- +# Exit the shell with STATUS, even in a "trap 0" or "set -e" context. +as_fn_exit () +{ + set +e + as_fn_set_status $1 + exit $1 +} # as_fn_exit + +# as_fn_unset VAR +# --------------- +# Portably unset VAR. +as_fn_unset () +{ + { eval $1=; unset $1;} +} +as_unset=as_fn_unset + +# as_fn_append VAR VALUE +# ---------------------- +# Append the text in VALUE to the end of the definition contained in VAR. Take +# advantage of any shell optimizations that allow amortized linear growth over +# repeated appends, instead of the typical quadratic growth present in naive +# implementations. +if (eval "as_var=1; as_var+=2; test x\$as_var = x12") 2>/dev/null +then : + eval 'as_fn_append () + { + eval $1+=\$2 + }' +else $as_nop + as_fn_append () + { + eval $1=\$$1\$2 + } +fi # as_fn_append + +# as_fn_arith ARG... +# ------------------ +# Perform arithmetic evaluation on the ARGs, and store the result in the +# global $as_val. Take advantage of shells that can avoid forks. The arguments +# must be portable across $(()) and expr. +if (eval "test \$(( 1 + 1 )) = 2") 2>/dev/null +then : + eval 'as_fn_arith () + { + as_val=$(( $* )) + }' +else $as_nop + as_fn_arith () + { + as_val=`expr "$@" || test $? -eq 1` + } +fi # as_fn_arith + + +if expr a : '\(a\)' >/dev/null 2>&1 && + test "X`expr 00001 : '.*\(...\)'`" = X001; then + as_expr=expr +else + as_expr=false +fi + +if (basename -- /) >/dev/null 2>&1 && test "X`basename -- / 2>&1`" = "X/"; then + as_basename=basename +else + as_basename=false +fi + +if (as_dir=`dirname -- /` && test "X$as_dir" = X/) >/dev/null 2>&1; then + as_dirname=dirname +else + as_dirname=false +fi + +as_me=`$as_basename -- "$0" || +$as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \ + X"$0" : 'X\(//\)$' \| \ + X"$0" : 'X\(/\)' \| . 2>/dev/null || +printf "%s\n" X/"$0" | + sed '/^.*\/\([^/][^/]*\)\/*$/{ + s//\1/ + q + } + /^X\/\(\/\/\)$/{ + s//\1/ + q + } + /^X\/\(\/\).*/{ + s//\1/ + q + } + s/.*/./; q'` + +# Avoid depending upon Character Ranges. +as_cr_letters='abcdefghijklmnopqrstuvwxyz' +as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ' +as_cr_Letters=$as_cr_letters$as_cr_LETTERS +as_cr_digits='0123456789' +as_cr_alnum=$as_cr_Letters$as_cr_digits + + +# Determine whether it's possible to make 'echo' print without a newline. +# These variables are no longer used directly by Autoconf, but are AC_SUBSTed +# for compatibility with existing Makefiles. +ECHO_C= ECHO_N= ECHO_T= +case `echo -n x` in #((((( +-n*) + case `echo 'xy\c'` in + *c*) ECHO_T=' ';; # ECHO_T is single tab character. + xy) ECHO_C='\c';; + *) echo `echo ksh88 bug on AIX 6.1` > /dev/null + ECHO_T=' ';; + esac;; +*) + ECHO_N='-n';; +esac + +# For backward compatibility with old third-party macros, we provide +# the shell variables $as_echo and $as_echo_n. New code should use +# AS_ECHO(["message"]) and AS_ECHO_N(["message"]), respectively. +as_echo='printf %s\n' +as_echo_n='printf %s' + +rm -f conf$$ conf$$.exe conf$$.file +if test -d conf$$.dir; then + rm -f conf$$.dir/conf$$.file +else + rm -f conf$$.dir + mkdir conf$$.dir 2>/dev/null +fi +if (echo >conf$$.file) 2>/dev/null; then + if ln -s conf$$.file conf$$ 2>/dev/null; then + as_ln_s='ln -s' + # ... but there are two gotchas: + # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail. + # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable. + # In both cases, we have to default to `cp -pR'. + ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe || + as_ln_s='cp -pR' + elif ln conf$$.file conf$$ 2>/dev/null; then + as_ln_s=ln + else + as_ln_s='cp -pR' + fi +else + as_ln_s='cp -pR' +fi +rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file +rmdir conf$$.dir 2>/dev/null + + +# as_fn_mkdir_p +# ------------- +# Create "$as_dir" as a directory, including parents if necessary. +as_fn_mkdir_p () +{ + + case $as_dir in #( + -*) as_dir=./$as_dir;; + esac + test -d "$as_dir" || eval $as_mkdir_p || { + as_dirs= + while :; do + case $as_dir in #( + *\'*) as_qdir=`printf "%s\n" "$as_dir" | sed "s/'/'\\\\\\\\''/g"`;; #'( + *) as_qdir=$as_dir;; + esac + as_dirs="'$as_qdir' $as_dirs" + as_dir=`$as_dirname -- "$as_dir" || +$as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ + X"$as_dir" : 'X\(//\)[^/]' \| \ + X"$as_dir" : 'X\(//\)$' \| \ + X"$as_dir" : 'X\(/\)' \| . 2>/dev/null || +printf "%s\n" X"$as_dir" | + sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ + s//\1/ + q + } + /^X\(\/\/\)[^/].*/{ + s//\1/ + q + } + /^X\(\/\/\)$/{ + s//\1/ + q + } + /^X\(\/\).*/{ + s//\1/ + q + } + s/.*/./; q'` + test -d "$as_dir" && break + done + test -z "$as_dirs" || eval "mkdir $as_dirs" + } || test -d "$as_dir" || as_fn_error $? "cannot create directory $as_dir" + + +} # as_fn_mkdir_p +if mkdir -p . 2>/dev/null; then + as_mkdir_p='mkdir -p "$as_dir"' +else + test -d ./-p && rmdir ./-p + as_mkdir_p=false +fi + + +# as_fn_executable_p FILE +# ----------------------- +# Test if FILE is an executable regular file. +as_fn_executable_p () +{ + test -f "$1" && test -x "$1" +} # as_fn_executable_p +as_test_x='test -x' +as_executable_p=as_fn_executable_p + +# Sed expression to map a string onto a valid CPP name. +as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'" + +# Sed expression to map a string onto a valid variable name. +as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'" + + +exec 6>&1 +## ----------------------------------- ## +## Main body of $CONFIG_STATUS script. ## +## ----------------------------------- ## +_ASEOF +test $as_write_fail = 0 && chmod +x $CONFIG_STATUS || ac_write_fail=1 + +cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 +# Save the log message, to keep $0 and so on meaningful, and to +# report actual input values of CONFIG_FILES etc. instead of their +# values after options handling. +ac_log=" +This file was extended by FreeType $as_me 2.13.2, which was +generated by GNU Autoconf 2.71. Invocation command line was + + CONFIG_FILES = $CONFIG_FILES + CONFIG_HEADERS = $CONFIG_HEADERS + CONFIG_LINKS = $CONFIG_LINKS + CONFIG_COMMANDS = $CONFIG_COMMANDS + $ $0 $@ + +on `(hostname || uname -n) 2>/dev/null | sed 1q` +" + +_ACEOF + +case $ac_config_files in *" +"*) set x $ac_config_files; shift; ac_config_files=$*;; +esac + +case $ac_config_headers in *" +"*) set x $ac_config_headers; shift; ac_config_headers=$*;; +esac + + +cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 +# Files that config.status was made for. +config_files="$ac_config_files" +config_headers="$ac_config_headers" +config_commands="$ac_config_commands" + +_ACEOF + +cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 +ac_cs_usage="\ +\`$as_me' instantiates files and other configuration actions +from templates according to the current configuration. Unless the files +and actions are specified as TAGs, all are instantiated by default. + +Usage: $0 [OPTION]... [TAG]... + + -h, --help print this help, then exit + -V, --version print version number and configuration settings, then exit + --config print configuration, then exit + -q, --quiet, --silent + do not print progress messages + -d, --debug don't remove temporary files + --recheck update $as_me by reconfiguring in the same conditions + --file=FILE[:TEMPLATE] + instantiate the configuration file FILE + --header=FILE[:TEMPLATE] + instantiate the configuration header FILE + +Configuration files: +$config_files + +Configuration headers: +$config_headers + +Configuration commands: +$config_commands + +Report bugs to ." + +_ACEOF +ac_cs_config=`printf "%s\n" "$ac_configure_args" | sed "$ac_safe_unquote"` +ac_cs_config_escaped=`printf "%s\n" "$ac_cs_config" | sed "s/^ //; s/'/'\\\\\\\\''/g"` +cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 +ac_cs_config='$ac_cs_config_escaped' +ac_cs_version="\\ +FreeType config.status 2.13.2 +configured by $0, generated by GNU Autoconf 2.71, + with options \\"\$ac_cs_config\\" + +Copyright (C) 2021 Free Software Foundation, Inc. +This config.status script is free software; the Free Software Foundation +gives unlimited permission to copy, distribute and modify it." + +ac_pwd='$ac_pwd' +srcdir='$srcdir' +INSTALL='$INSTALL' +MKDIR_P='$MKDIR_P' +AWK='$AWK' +test -n "\$AWK" || AWK=awk +_ACEOF + +cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 +# The default lists apply if the user does not specify any file. +ac_need_defaults=: +while test $# != 0 +do + case $1 in + --*=?*) + ac_option=`expr "X$1" : 'X\([^=]*\)='` + ac_optarg=`expr "X$1" : 'X[^=]*=\(.*\)'` + ac_shift=: + ;; + --*=) + ac_option=`expr "X$1" : 'X\([^=]*\)='` + ac_optarg= + ac_shift=: + ;; + *) + ac_option=$1 + ac_optarg=$2 + ac_shift=shift + ;; + esac + + case $ac_option in + # Handling of the options. + -recheck | --recheck | --rechec | --reche | --rech | --rec | --re | --r) + ac_cs_recheck=: ;; + --version | --versio | --versi | --vers | --ver | --ve | --v | -V ) + printf "%s\n" "$ac_cs_version"; exit ;; + --config | --confi | --conf | --con | --co | --c ) + printf "%s\n" "$ac_cs_config"; exit ;; + --debug | --debu | --deb | --de | --d | -d ) + debug=: ;; + --file | --fil | --fi | --f ) + $ac_shift + case $ac_optarg in + *\'*) ac_optarg=`printf "%s\n" "$ac_optarg" | sed "s/'/'\\\\\\\\''/g"` ;; + '') as_fn_error $? "missing file argument" ;; + esac + as_fn_append CONFIG_FILES " '$ac_optarg'" + ac_need_defaults=false;; + --header | --heade | --head | --hea ) + $ac_shift + case $ac_optarg in + *\'*) ac_optarg=`printf "%s\n" "$ac_optarg" | sed "s/'/'\\\\\\\\''/g"` ;; + esac + as_fn_append CONFIG_HEADERS " '$ac_optarg'" + ac_need_defaults=false;; + --he | --h) + # Conflict between --help and --header + as_fn_error $? "ambiguous option: \`$1' +Try \`$0 --help' for more information.";; + --help | --hel | -h ) + printf "%s\n" "$ac_cs_usage"; exit ;; + -q | -quiet | --quiet | --quie | --qui | --qu | --q \ + | -silent | --silent | --silen | --sile | --sil | --si | --s) + ac_cs_silent=: ;; + + # This is an error. + -*) as_fn_error $? "unrecognized option: \`$1' +Try \`$0 --help' for more information." ;; + + *) as_fn_append ac_config_targets " $1" + ac_need_defaults=false ;; + + esac + shift +done + +ac_configure_extra_args= + +if $ac_cs_silent; then + exec 6>/dev/null + ac_configure_extra_args="$ac_configure_extra_args --silent" +fi + +_ACEOF +cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 +if \$ac_cs_recheck; then + set X $SHELL '$0' $ac_configure_args \$ac_configure_extra_args --no-create --no-recursion + shift + \printf "%s\n" "running CONFIG_SHELL=$SHELL \$*" >&6 + CONFIG_SHELL='$SHELL' + export CONFIG_SHELL + exec "\$@" +fi + +_ACEOF +cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 +exec 5>>config.log +{ + echo + sed 'h;s/./-/g;s/^.../## /;s/...$/ ##/;p;x;p;x' <<_ASBOX +## Running $as_me. ## +_ASBOX + printf "%s\n" "$ac_log" +} >&5 + +_ACEOF +cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 +# +# INIT-COMMANDS +# + + +# The HP-UX ksh and POSIX shell print the target directory to stdout +# if CDPATH is set. +(unset CDPATH) >/dev/null 2>&1 && unset CDPATH + +sed_quote_subst='$sed_quote_subst' +double_quote_subst='$double_quote_subst' +delay_variable_subst='$delay_variable_subst' +macro_version='`$ECHO "$macro_version" | $SED "$delay_single_quote_subst"`' +macro_revision='`$ECHO "$macro_revision" | $SED "$delay_single_quote_subst"`' +AS='`$ECHO "$AS" | $SED "$delay_single_quote_subst"`' +DLLTOOL='`$ECHO "$DLLTOOL" | $SED "$delay_single_quote_subst"`' +OBJDUMP='`$ECHO "$OBJDUMP" | $SED "$delay_single_quote_subst"`' +enable_shared='`$ECHO "$enable_shared" | $SED "$delay_single_quote_subst"`' +enable_static='`$ECHO "$enable_static" | $SED "$delay_single_quote_subst"`' +pic_mode='`$ECHO "$pic_mode" | $SED "$delay_single_quote_subst"`' +enable_fast_install='`$ECHO "$enable_fast_install" | $SED "$delay_single_quote_subst"`' +shared_archive_member_spec='`$ECHO "$shared_archive_member_spec" | $SED "$delay_single_quote_subst"`' +SHELL='`$ECHO "$SHELL" | $SED "$delay_single_quote_subst"`' +ECHO='`$ECHO "$ECHO" | $SED "$delay_single_quote_subst"`' +PATH_SEPARATOR='`$ECHO "$PATH_SEPARATOR" | $SED "$delay_single_quote_subst"`' +host_alias='`$ECHO "$host_alias" | $SED "$delay_single_quote_subst"`' +host='`$ECHO "$host" | $SED "$delay_single_quote_subst"`' +host_os='`$ECHO "$host_os" | $SED "$delay_single_quote_subst"`' +build_alias='`$ECHO "$build_alias" | $SED "$delay_single_quote_subst"`' +build='`$ECHO "$build" | $SED "$delay_single_quote_subst"`' +build_os='`$ECHO "$build_os" | $SED "$delay_single_quote_subst"`' +SED='`$ECHO "$SED" | $SED "$delay_single_quote_subst"`' +Xsed='`$ECHO "$Xsed" | $SED "$delay_single_quote_subst"`' +GREP='`$ECHO "$GREP" | $SED "$delay_single_quote_subst"`' +EGREP='`$ECHO "$EGREP" | $SED "$delay_single_quote_subst"`' +FGREP='`$ECHO "$FGREP" | $SED "$delay_single_quote_subst"`' +LD='`$ECHO "$LD" | $SED "$delay_single_quote_subst"`' +NM='`$ECHO "$NM" | $SED "$delay_single_quote_subst"`' +LN_S='`$ECHO "$LN_S" | $SED "$delay_single_quote_subst"`' +max_cmd_len='`$ECHO "$max_cmd_len" | $SED "$delay_single_quote_subst"`' +ac_objext='`$ECHO "$ac_objext" | $SED "$delay_single_quote_subst"`' +exeext='`$ECHO "$exeext" | $SED "$delay_single_quote_subst"`' +lt_unset='`$ECHO "$lt_unset" | $SED "$delay_single_quote_subst"`' +lt_SP2NL='`$ECHO "$lt_SP2NL" | $SED "$delay_single_quote_subst"`' +lt_NL2SP='`$ECHO "$lt_NL2SP" | $SED "$delay_single_quote_subst"`' +lt_cv_to_host_file_cmd='`$ECHO "$lt_cv_to_host_file_cmd" | $SED "$delay_single_quote_subst"`' +lt_cv_to_tool_file_cmd='`$ECHO "$lt_cv_to_tool_file_cmd" | $SED "$delay_single_quote_subst"`' +reload_flag='`$ECHO "$reload_flag" | $SED "$delay_single_quote_subst"`' +reload_cmds='`$ECHO "$reload_cmds" | $SED "$delay_single_quote_subst"`' +FILECMD='`$ECHO "$FILECMD" | $SED "$delay_single_quote_subst"`' +deplibs_check_method='`$ECHO "$deplibs_check_method" | $SED "$delay_single_quote_subst"`' +file_magic_cmd='`$ECHO "$file_magic_cmd" | $SED "$delay_single_quote_subst"`' +file_magic_glob='`$ECHO "$file_magic_glob" | $SED "$delay_single_quote_subst"`' +want_nocaseglob='`$ECHO "$want_nocaseglob" | $SED "$delay_single_quote_subst"`' +sharedlib_from_linklib_cmd='`$ECHO "$sharedlib_from_linklib_cmd" | $SED "$delay_single_quote_subst"`' +AR='`$ECHO "$AR" | $SED "$delay_single_quote_subst"`' +lt_ar_flags='`$ECHO "$lt_ar_flags" | $SED "$delay_single_quote_subst"`' +AR_FLAGS='`$ECHO "$AR_FLAGS" | $SED "$delay_single_quote_subst"`' +archiver_list_spec='`$ECHO "$archiver_list_spec" | $SED "$delay_single_quote_subst"`' +STRIP='`$ECHO "$STRIP" | $SED "$delay_single_quote_subst"`' +RANLIB='`$ECHO "$RANLIB" | $SED "$delay_single_quote_subst"`' +old_postinstall_cmds='`$ECHO "$old_postinstall_cmds" | $SED "$delay_single_quote_subst"`' +old_postuninstall_cmds='`$ECHO "$old_postuninstall_cmds" | $SED "$delay_single_quote_subst"`' +old_archive_cmds='`$ECHO "$old_archive_cmds" | $SED "$delay_single_quote_subst"`' +lock_old_archive_extraction='`$ECHO "$lock_old_archive_extraction" | $SED "$delay_single_quote_subst"`' +CC='`$ECHO "$CC" | $SED "$delay_single_quote_subst"`' +CFLAGS='`$ECHO "$CFLAGS" | $SED "$delay_single_quote_subst"`' +compiler='`$ECHO "$compiler" | $SED "$delay_single_quote_subst"`' +GCC='`$ECHO "$GCC" | $SED "$delay_single_quote_subst"`' +lt_cv_sys_global_symbol_pipe='`$ECHO "$lt_cv_sys_global_symbol_pipe" | $SED "$delay_single_quote_subst"`' +lt_cv_sys_global_symbol_to_cdecl='`$ECHO "$lt_cv_sys_global_symbol_to_cdecl" | $SED "$delay_single_quote_subst"`' +lt_cv_sys_global_symbol_to_import='`$ECHO "$lt_cv_sys_global_symbol_to_import" | $SED "$delay_single_quote_subst"`' +lt_cv_sys_global_symbol_to_c_name_address='`$ECHO "$lt_cv_sys_global_symbol_to_c_name_address" | $SED "$delay_single_quote_subst"`' +lt_cv_sys_global_symbol_to_c_name_address_lib_prefix='`$ECHO "$lt_cv_sys_global_symbol_to_c_name_address_lib_prefix" | $SED "$delay_single_quote_subst"`' +lt_cv_nm_interface='`$ECHO "$lt_cv_nm_interface" | $SED "$delay_single_quote_subst"`' +nm_file_list_spec='`$ECHO "$nm_file_list_spec" | $SED "$delay_single_quote_subst"`' +lt_sysroot='`$ECHO "$lt_sysroot" | $SED "$delay_single_quote_subst"`' +lt_cv_truncate_bin='`$ECHO "$lt_cv_truncate_bin" | $SED "$delay_single_quote_subst"`' +objdir='`$ECHO "$objdir" | $SED "$delay_single_quote_subst"`' +MAGIC_CMD='`$ECHO "$MAGIC_CMD" | $SED "$delay_single_quote_subst"`' +lt_prog_compiler_no_builtin_flag='`$ECHO "$lt_prog_compiler_no_builtin_flag" | $SED "$delay_single_quote_subst"`' +lt_prog_compiler_pic='`$ECHO "$lt_prog_compiler_pic" | $SED "$delay_single_quote_subst"`' +lt_prog_compiler_wl='`$ECHO "$lt_prog_compiler_wl" | $SED "$delay_single_quote_subst"`' +lt_prog_compiler_static='`$ECHO "$lt_prog_compiler_static" | $SED "$delay_single_quote_subst"`' +lt_cv_prog_compiler_c_o='`$ECHO "$lt_cv_prog_compiler_c_o" | $SED "$delay_single_quote_subst"`' +need_locks='`$ECHO "$need_locks" | $SED "$delay_single_quote_subst"`' +MANIFEST_TOOL='`$ECHO "$MANIFEST_TOOL" | $SED "$delay_single_quote_subst"`' +DSYMUTIL='`$ECHO "$DSYMUTIL" | $SED "$delay_single_quote_subst"`' +NMEDIT='`$ECHO "$NMEDIT" | $SED "$delay_single_quote_subst"`' +LIPO='`$ECHO "$LIPO" | $SED "$delay_single_quote_subst"`' +OTOOL='`$ECHO "$OTOOL" | $SED "$delay_single_quote_subst"`' +OTOOL64='`$ECHO "$OTOOL64" | $SED "$delay_single_quote_subst"`' +libext='`$ECHO "$libext" | $SED "$delay_single_quote_subst"`' +shrext_cmds='`$ECHO "$shrext_cmds" | $SED "$delay_single_quote_subst"`' +extract_expsyms_cmds='`$ECHO "$extract_expsyms_cmds" | $SED "$delay_single_quote_subst"`' +archive_cmds_need_lc='`$ECHO "$archive_cmds_need_lc" | $SED "$delay_single_quote_subst"`' +enable_shared_with_static_runtimes='`$ECHO "$enable_shared_with_static_runtimes" | $SED "$delay_single_quote_subst"`' +export_dynamic_flag_spec='`$ECHO "$export_dynamic_flag_spec" | $SED "$delay_single_quote_subst"`' +whole_archive_flag_spec='`$ECHO "$whole_archive_flag_spec" | $SED "$delay_single_quote_subst"`' +compiler_needs_object='`$ECHO "$compiler_needs_object" | $SED "$delay_single_quote_subst"`' +old_archive_from_new_cmds='`$ECHO "$old_archive_from_new_cmds" | $SED "$delay_single_quote_subst"`' +old_archive_from_expsyms_cmds='`$ECHO "$old_archive_from_expsyms_cmds" | $SED "$delay_single_quote_subst"`' +archive_cmds='`$ECHO "$archive_cmds" | $SED "$delay_single_quote_subst"`' +archive_expsym_cmds='`$ECHO "$archive_expsym_cmds" | $SED "$delay_single_quote_subst"`' +module_cmds='`$ECHO "$module_cmds" | $SED "$delay_single_quote_subst"`' +module_expsym_cmds='`$ECHO "$module_expsym_cmds" | $SED "$delay_single_quote_subst"`' +with_gnu_ld='`$ECHO "$with_gnu_ld" | $SED "$delay_single_quote_subst"`' +allow_undefined_flag='`$ECHO "$allow_undefined_flag" | $SED "$delay_single_quote_subst"`' +no_undefined_flag='`$ECHO "$no_undefined_flag" | $SED "$delay_single_quote_subst"`' +hardcode_libdir_flag_spec='`$ECHO "$hardcode_libdir_flag_spec" | $SED "$delay_single_quote_subst"`' +hardcode_libdir_separator='`$ECHO "$hardcode_libdir_separator" | $SED "$delay_single_quote_subst"`' +hardcode_direct='`$ECHO "$hardcode_direct" | $SED "$delay_single_quote_subst"`' +hardcode_direct_absolute='`$ECHO "$hardcode_direct_absolute" | $SED "$delay_single_quote_subst"`' +hardcode_minus_L='`$ECHO "$hardcode_minus_L" | $SED "$delay_single_quote_subst"`' +hardcode_shlibpath_var='`$ECHO "$hardcode_shlibpath_var" | $SED "$delay_single_quote_subst"`' +hardcode_automatic='`$ECHO "$hardcode_automatic" | $SED "$delay_single_quote_subst"`' +inherit_rpath='`$ECHO "$inherit_rpath" | $SED "$delay_single_quote_subst"`' +link_all_deplibs='`$ECHO "$link_all_deplibs" | $SED "$delay_single_quote_subst"`' +always_export_symbols='`$ECHO "$always_export_symbols" | $SED "$delay_single_quote_subst"`' +export_symbols_cmds='`$ECHO "$export_symbols_cmds" | $SED "$delay_single_quote_subst"`' +exclude_expsyms='`$ECHO "$exclude_expsyms" | $SED "$delay_single_quote_subst"`' +include_expsyms='`$ECHO "$include_expsyms" | $SED "$delay_single_quote_subst"`' +prelink_cmds='`$ECHO "$prelink_cmds" | $SED "$delay_single_quote_subst"`' +postlink_cmds='`$ECHO "$postlink_cmds" | $SED "$delay_single_quote_subst"`' +file_list_spec='`$ECHO "$file_list_spec" | $SED "$delay_single_quote_subst"`' +variables_saved_for_relink='`$ECHO "$variables_saved_for_relink" | $SED "$delay_single_quote_subst"`' +need_lib_prefix='`$ECHO "$need_lib_prefix" | $SED "$delay_single_quote_subst"`' +need_version='`$ECHO "$need_version" | $SED "$delay_single_quote_subst"`' +version_type='`$ECHO "$version_type" | $SED "$delay_single_quote_subst"`' +runpath_var='`$ECHO "$runpath_var" | $SED "$delay_single_quote_subst"`' +shlibpath_var='`$ECHO "$shlibpath_var" | $SED "$delay_single_quote_subst"`' +shlibpath_overrides_runpath='`$ECHO "$shlibpath_overrides_runpath" | $SED "$delay_single_quote_subst"`' +libname_spec='`$ECHO "$libname_spec" | $SED "$delay_single_quote_subst"`' +library_names_spec='`$ECHO "$library_names_spec" | $SED "$delay_single_quote_subst"`' +soname_spec='`$ECHO "$soname_spec" | $SED "$delay_single_quote_subst"`' +install_override_mode='`$ECHO "$install_override_mode" | $SED "$delay_single_quote_subst"`' +postinstall_cmds='`$ECHO "$postinstall_cmds" | $SED "$delay_single_quote_subst"`' +postuninstall_cmds='`$ECHO "$postuninstall_cmds" | $SED "$delay_single_quote_subst"`' +finish_cmds='`$ECHO "$finish_cmds" | $SED "$delay_single_quote_subst"`' +finish_eval='`$ECHO "$finish_eval" | $SED "$delay_single_quote_subst"`' +hardcode_into_libs='`$ECHO "$hardcode_into_libs" | $SED "$delay_single_quote_subst"`' +sys_lib_search_path_spec='`$ECHO "$sys_lib_search_path_spec" | $SED "$delay_single_quote_subst"`' +configure_time_dlsearch_path='`$ECHO "$configure_time_dlsearch_path" | $SED "$delay_single_quote_subst"`' +configure_time_lt_sys_library_path='`$ECHO "$configure_time_lt_sys_library_path" | $SED "$delay_single_quote_subst"`' +hardcode_action='`$ECHO "$hardcode_action" | $SED "$delay_single_quote_subst"`' +enable_dlopen='`$ECHO "$enable_dlopen" | $SED "$delay_single_quote_subst"`' +enable_dlopen_self='`$ECHO "$enable_dlopen_self" | $SED "$delay_single_quote_subst"`' +enable_dlopen_self_static='`$ECHO "$enable_dlopen_self_static" | $SED "$delay_single_quote_subst"`' +old_striplib='`$ECHO "$old_striplib" | $SED "$delay_single_quote_subst"`' +striplib='`$ECHO "$striplib" | $SED "$delay_single_quote_subst"`' +LD_RC='`$ECHO "$LD_RC" | $SED "$delay_single_quote_subst"`' +reload_flag_RC='`$ECHO "$reload_flag_RC" | $SED "$delay_single_quote_subst"`' +reload_cmds_RC='`$ECHO "$reload_cmds_RC" | $SED "$delay_single_quote_subst"`' +old_archive_cmds_RC='`$ECHO "$old_archive_cmds_RC" | $SED "$delay_single_quote_subst"`' +compiler_RC='`$ECHO "$compiler_RC" | $SED "$delay_single_quote_subst"`' +GCC_RC='`$ECHO "$GCC_RC" | $SED "$delay_single_quote_subst"`' +lt_prog_compiler_no_builtin_flag_RC='`$ECHO "$lt_prog_compiler_no_builtin_flag_RC" | $SED "$delay_single_quote_subst"`' +lt_prog_compiler_pic_RC='`$ECHO "$lt_prog_compiler_pic_RC" | $SED "$delay_single_quote_subst"`' +lt_prog_compiler_wl_RC='`$ECHO "$lt_prog_compiler_wl_RC" | $SED "$delay_single_quote_subst"`' +lt_prog_compiler_static_RC='`$ECHO "$lt_prog_compiler_static_RC" | $SED "$delay_single_quote_subst"`' +lt_cv_prog_compiler_c_o_RC='`$ECHO "$lt_cv_prog_compiler_c_o_RC" | $SED "$delay_single_quote_subst"`' +archive_cmds_need_lc_RC='`$ECHO "$archive_cmds_need_lc_RC" | $SED "$delay_single_quote_subst"`' +enable_shared_with_static_runtimes_RC='`$ECHO "$enable_shared_with_static_runtimes_RC" | $SED "$delay_single_quote_subst"`' +export_dynamic_flag_spec_RC='`$ECHO "$export_dynamic_flag_spec_RC" | $SED "$delay_single_quote_subst"`' +whole_archive_flag_spec_RC='`$ECHO "$whole_archive_flag_spec_RC" | $SED "$delay_single_quote_subst"`' +compiler_needs_object_RC='`$ECHO "$compiler_needs_object_RC" | $SED "$delay_single_quote_subst"`' +old_archive_from_new_cmds_RC='`$ECHO "$old_archive_from_new_cmds_RC" | $SED "$delay_single_quote_subst"`' +old_archive_from_expsyms_cmds_RC='`$ECHO "$old_archive_from_expsyms_cmds_RC" | $SED "$delay_single_quote_subst"`' +archive_cmds_RC='`$ECHO "$archive_cmds_RC" | $SED "$delay_single_quote_subst"`' +archive_expsym_cmds_RC='`$ECHO "$archive_expsym_cmds_RC" | $SED "$delay_single_quote_subst"`' +module_cmds_RC='`$ECHO "$module_cmds_RC" | $SED "$delay_single_quote_subst"`' +module_expsym_cmds_RC='`$ECHO "$module_expsym_cmds_RC" | $SED "$delay_single_quote_subst"`' +with_gnu_ld_RC='`$ECHO "$with_gnu_ld_RC" | $SED "$delay_single_quote_subst"`' +allow_undefined_flag_RC='`$ECHO "$allow_undefined_flag_RC" | $SED "$delay_single_quote_subst"`' +no_undefined_flag_RC='`$ECHO "$no_undefined_flag_RC" | $SED "$delay_single_quote_subst"`' +hardcode_libdir_flag_spec_RC='`$ECHO "$hardcode_libdir_flag_spec_RC" | $SED "$delay_single_quote_subst"`' +hardcode_libdir_separator_RC='`$ECHO "$hardcode_libdir_separator_RC" | $SED "$delay_single_quote_subst"`' +hardcode_direct_RC='`$ECHO "$hardcode_direct_RC" | $SED "$delay_single_quote_subst"`' +hardcode_direct_absolute_RC='`$ECHO "$hardcode_direct_absolute_RC" | $SED "$delay_single_quote_subst"`' +hardcode_minus_L_RC='`$ECHO "$hardcode_minus_L_RC" | $SED "$delay_single_quote_subst"`' +hardcode_shlibpath_var_RC='`$ECHO "$hardcode_shlibpath_var_RC" | $SED "$delay_single_quote_subst"`' +hardcode_automatic_RC='`$ECHO "$hardcode_automatic_RC" | $SED "$delay_single_quote_subst"`' +inherit_rpath_RC='`$ECHO "$inherit_rpath_RC" | $SED "$delay_single_quote_subst"`' +link_all_deplibs_RC='`$ECHO "$link_all_deplibs_RC" | $SED "$delay_single_quote_subst"`' +always_export_symbols_RC='`$ECHO "$always_export_symbols_RC" | $SED "$delay_single_quote_subst"`' +export_symbols_cmds_RC='`$ECHO "$export_symbols_cmds_RC" | $SED "$delay_single_quote_subst"`' +exclude_expsyms_RC='`$ECHO "$exclude_expsyms_RC" | $SED "$delay_single_quote_subst"`' +include_expsyms_RC='`$ECHO "$include_expsyms_RC" | $SED "$delay_single_quote_subst"`' +prelink_cmds_RC='`$ECHO "$prelink_cmds_RC" | $SED "$delay_single_quote_subst"`' +postlink_cmds_RC='`$ECHO "$postlink_cmds_RC" | $SED "$delay_single_quote_subst"`' +file_list_spec_RC='`$ECHO "$file_list_spec_RC" | $SED "$delay_single_quote_subst"`' +hardcode_action_RC='`$ECHO "$hardcode_action_RC" | $SED "$delay_single_quote_subst"`' + +LTCC='$LTCC' +LTCFLAGS='$LTCFLAGS' +compiler='$compiler_DEFAULT' + +# A function that is used when there is no print builtin or printf. +func_fallback_echo () +{ + eval 'cat <<_LTECHO_EOF +\$1 +_LTECHO_EOF' +} + +# Quote evaled strings. +for var in AS \ +DLLTOOL \ +OBJDUMP \ +SHELL \ +ECHO \ +PATH_SEPARATOR \ +SED \ +GREP \ +EGREP \ +FGREP \ +LD \ +NM \ +LN_S \ +lt_SP2NL \ +lt_NL2SP \ +reload_flag \ +FILECMD \ +deplibs_check_method \ +file_magic_cmd \ +file_magic_glob \ +want_nocaseglob \ +sharedlib_from_linklib_cmd \ +AR \ +archiver_list_spec \ +STRIP \ +RANLIB \ +CC \ +CFLAGS \ +compiler \ +lt_cv_sys_global_symbol_pipe \ +lt_cv_sys_global_symbol_to_cdecl \ +lt_cv_sys_global_symbol_to_import \ +lt_cv_sys_global_symbol_to_c_name_address \ +lt_cv_sys_global_symbol_to_c_name_address_lib_prefix \ +lt_cv_nm_interface \ +nm_file_list_spec \ +lt_cv_truncate_bin \ +lt_prog_compiler_no_builtin_flag \ +lt_prog_compiler_pic \ +lt_prog_compiler_wl \ +lt_prog_compiler_static \ +lt_cv_prog_compiler_c_o \ +need_locks \ +MANIFEST_TOOL \ +DSYMUTIL \ +NMEDIT \ +LIPO \ +OTOOL \ +OTOOL64 \ +shrext_cmds \ +export_dynamic_flag_spec \ +whole_archive_flag_spec \ +compiler_needs_object \ +with_gnu_ld \ +allow_undefined_flag \ +no_undefined_flag \ +hardcode_libdir_flag_spec \ +hardcode_libdir_separator \ +exclude_expsyms \ +include_expsyms \ +file_list_spec \ +variables_saved_for_relink \ +libname_spec \ +library_names_spec \ +soname_spec \ +install_override_mode \ +finish_eval \ +old_striplib \ +striplib \ +LD_RC \ +reload_flag_RC \ +compiler_RC \ +lt_prog_compiler_no_builtin_flag_RC \ +lt_prog_compiler_pic_RC \ +lt_prog_compiler_wl_RC \ +lt_prog_compiler_static_RC \ +lt_cv_prog_compiler_c_o_RC \ +export_dynamic_flag_spec_RC \ +whole_archive_flag_spec_RC \ +compiler_needs_object_RC \ +with_gnu_ld_RC \ +allow_undefined_flag_RC \ +no_undefined_flag_RC \ +hardcode_libdir_flag_spec_RC \ +hardcode_libdir_separator_RC \ +exclude_expsyms_RC \ +include_expsyms_RC \ +file_list_spec_RC; do + case \`eval \\\\\$ECHO \\\\""\\\\\$\$var"\\\\"\` in + *[\\\\\\\`\\"\\\$]*) + eval "lt_\$var=\\\\\\"\\\`\\\$ECHO \\"\\\$\$var\\" | \\\$SED \\"\\\$sed_quote_subst\\"\\\`\\\\\\"" ## exclude from sc_prohibit_nested_quotes + ;; + *) + eval "lt_\$var=\\\\\\"\\\$\$var\\\\\\"" + ;; + esac +done + +# Double-quote double-evaled strings. +for var in reload_cmds \ +old_postinstall_cmds \ +old_postuninstall_cmds \ +old_archive_cmds \ +extract_expsyms_cmds \ +old_archive_from_new_cmds \ +old_archive_from_expsyms_cmds \ +archive_cmds \ +archive_expsym_cmds \ +module_cmds \ +module_expsym_cmds \ +export_symbols_cmds \ +prelink_cmds \ +postlink_cmds \ +postinstall_cmds \ +postuninstall_cmds \ +finish_cmds \ +sys_lib_search_path_spec \ +configure_time_dlsearch_path \ +configure_time_lt_sys_library_path \ +reload_cmds_RC \ +old_archive_cmds_RC \ +old_archive_from_new_cmds_RC \ +old_archive_from_expsyms_cmds_RC \ +archive_cmds_RC \ +archive_expsym_cmds_RC \ +module_cmds_RC \ +module_expsym_cmds_RC \ +export_symbols_cmds_RC \ +prelink_cmds_RC \ +postlink_cmds_RC; do + case \`eval \\\\\$ECHO \\\\""\\\\\$\$var"\\\\"\` in + *[\\\\\\\`\\"\\\$]*) + eval "lt_\$var=\\\\\\"\\\`\\\$ECHO \\"\\\$\$var\\" | \\\$SED -e \\"\\\$double_quote_subst\\" -e \\"\\\$sed_quote_subst\\" -e \\"\\\$delay_variable_subst\\"\\\`\\\\\\"" ## exclude from sc_prohibit_nested_quotes + ;; + *) + eval "lt_\$var=\\\\\\"\\\$\$var\\\\\\"" + ;; + esac +done + +ac_aux_dir='$ac_aux_dir' + +# See if we are running on zsh, and set the options that allow our +# commands through without removal of \ escapes INIT. +if test -n "\${ZSH_VERSION+set}"; then + setopt NO_GLOB_SUBST +fi + + + PACKAGE='$PACKAGE' + VERSION='$VERSION' + RM='$RM' + ofile='$ofile' + + + + + +FTOPTION_H_SED="$FTOPTION_H_SED" + +_ACEOF + +cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 + +# Handling of arguments. +for ac_config_target in $ac_config_targets +do + case $ac_config_target in + "libtool") CONFIG_COMMANDS="$CONFIG_COMMANDS libtool" ;; + "ftoption.h") CONFIG_FILES="$CONFIG_FILES ftoption.h:${srcdir}/../../include/freetype/config/ftoption.h" ;; + "ftconfig.h") CONFIG_HEADERS="$CONFIG_HEADERS ftconfig.h" ;; + "unix-cc.mk") CONFIG_FILES="$CONFIG_FILES unix-cc.mk:unix-cc.in" ;; + "unix-def.mk") CONFIG_FILES="$CONFIG_FILES unix-def.mk:unix-def.in" ;; + + *) as_fn_error $? "invalid argument: \`$ac_config_target'" "$LINENO" 5;; + esac +done + + +# If the user did not use the arguments to specify the items to instantiate, +# then the envvar interface is used. Set only those that are not. +# We use the long form for the default assignment because of an extremely +# bizarre bug on SunOS 4.1.3. +if $ac_need_defaults; then + test ${CONFIG_FILES+y} || CONFIG_FILES=$config_files + test ${CONFIG_HEADERS+y} || CONFIG_HEADERS=$config_headers + test ${CONFIG_COMMANDS+y} || CONFIG_COMMANDS=$config_commands +fi + +# Have a temporary directory for convenience. Make it in the build tree +# simply because there is no reason against having it here, and in addition, +# creating and moving files from /tmp can sometimes cause problems. +# Hook for its removal unless debugging. +# Note that there is a small window in which the directory will not be cleaned: +# after its creation but before its name has been assigned to `$tmp'. +$debug || +{ + tmp= ac_tmp= + trap 'exit_status=$? + : "${ac_tmp:=$tmp}" + { test ! -d "$ac_tmp" || rm -fr "$ac_tmp"; } && exit $exit_status +' 0 + trap 'as_fn_exit 1' 1 2 13 15 +} +# Create a (secure) tmp directory for tmp files. + +{ + tmp=`(umask 077 && mktemp -d "./confXXXXXX") 2>/dev/null` && + test -d "$tmp" +} || +{ + tmp=./conf$$-$RANDOM + (umask 077 && mkdir "$tmp") +} || as_fn_error $? "cannot create a temporary directory in ." "$LINENO" 5 +ac_tmp=$tmp + +# Set up the scripts for CONFIG_FILES section. +# No need to generate them if there are no CONFIG_FILES. +# This happens for instance with `./config.status config.h'. +if test -n "$CONFIG_FILES"; then + + +ac_cr=`echo X | tr X '\015'` +# On cygwin, bash can eat \r inside `` if the user requested igncr. +# But we know of no other shell where ac_cr would be empty at this +# point, so we can use a bashism as a fallback. +if test "x$ac_cr" = x; then + eval ac_cr=\$\'\\r\' +fi +ac_cs_awk_cr=`$AWK 'BEGIN { print "a\rb" }' /dev/null` +if test "$ac_cs_awk_cr" = "a${ac_cr}b"; then + ac_cs_awk_cr='\\r' +else + ac_cs_awk_cr=$ac_cr +fi + +echo 'BEGIN {' >"$ac_tmp/subs1.awk" && +_ACEOF + + +{ + echo "cat >conf$$subs.awk <<_ACEOF" && + echo "$ac_subst_vars" | sed 's/.*/&!$&$ac_delim/' && + echo "_ACEOF" +} >conf$$subs.sh || + as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5 +ac_delim_num=`echo "$ac_subst_vars" | grep -c '^'` +ac_delim='%!_!# ' +for ac_last_try in false false false false false :; do + . ./conf$$subs.sh || + as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5 + + ac_delim_n=`sed -n "s/.*$ac_delim\$/X/p" conf$$subs.awk | grep -c X` + if test $ac_delim_n = $ac_delim_num; then + break + elif $ac_last_try; then + as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5 + else + ac_delim="$ac_delim!$ac_delim _$ac_delim!! " + fi +done +rm -f conf$$subs.sh + +cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 +cat >>"\$ac_tmp/subs1.awk" <<\\_ACAWK && +_ACEOF +sed -n ' +h +s/^/S["/; s/!.*/"]=/ +p +g +s/^[^!]*!// +:repl +t repl +s/'"$ac_delim"'$// +t delim +:nl +h +s/\(.\{148\}\)..*/\1/ +t more1 +s/["\\]/\\&/g; s/^/"/; s/$/\\n"\\/ +p +n +b repl +:more1 +s/["\\]/\\&/g; s/^/"/; s/$/"\\/ +p +g +s/.\{148\}// +t nl +:delim +h +s/\(.\{148\}\)..*/\1/ +t more2 +s/["\\]/\\&/g; s/^/"/; s/$/"/ +p +b +:more2 +s/["\\]/\\&/g; s/^/"/; s/$/"\\/ +p +g +s/.\{148\}// +t delim +' >$CONFIG_STATUS || ac_write_fail=1 +rm -f conf$$subs.awk +cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 +_ACAWK +cat >>"\$ac_tmp/subs1.awk" <<_ACAWK && + for (key in S) S_is_set[key] = 1 + FS = "" + +} +{ + line = $ 0 + nfields = split(line, field, "@") + substed = 0 + len = length(field[1]) + for (i = 2; i < nfields; i++) { + key = field[i] + keylen = length(key) + if (S_is_set[key]) { + value = S[key] + line = substr(line, 1, len) "" value "" substr(line, len + keylen + 3) + len += length(value) + length(field[++i]) + substed = 1 + } else + len += 1 + keylen + } + + print line +} + +_ACAWK +_ACEOF +cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 +if sed "s/$ac_cr//" < /dev/null > /dev/null 2>&1; then + sed "s/$ac_cr\$//; s/$ac_cr/$ac_cs_awk_cr/g" +else + cat +fi < "$ac_tmp/subs1.awk" > "$ac_tmp/subs.awk" \ + || as_fn_error $? "could not setup config files machinery" "$LINENO" 5 +_ACEOF + +# VPATH may cause trouble with some makes, so we remove sole $(srcdir), +# ${srcdir} and @srcdir@ entries from VPATH if srcdir is ".", strip leading and +# trailing colons and then remove the whole line if VPATH becomes empty +# (actually we leave an empty line to preserve line numbers). +if test "x$srcdir" = x.; then + ac_vpsub='/^[ ]*VPATH[ ]*=[ ]*/{ +h +s/// +s/^/:/ +s/[ ]*$/:/ +s/:\$(srcdir):/:/g +s/:\${srcdir}:/:/g +s/:@srcdir@:/:/g +s/^:*// +s/:*$// +x +s/\(=[ ]*\).*/\1/ +G +s/\n// +s/^[^=]*=[ ]*$// +}' +fi + +cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 +fi # test -n "$CONFIG_FILES" + +# Set up the scripts for CONFIG_HEADERS section. +# No need to generate them if there are no CONFIG_HEADERS. +# This happens for instance with `./config.status Makefile'. +if test -n "$CONFIG_HEADERS"; then +cat >"$ac_tmp/defines.awk" <<\_ACAWK || +BEGIN { +_ACEOF + +# Transform confdefs.h into an awk script `defines.awk', embedded as +# here-document in config.status, that substitutes the proper values into +# config.h.in to produce config.h. + +# Create a delimiter string that does not exist in confdefs.h, to ease +# handling of long lines. +ac_delim='%!_!# ' +for ac_last_try in false false :; do + ac_tt=`sed -n "/$ac_delim/p" confdefs.h` + if test -z "$ac_tt"; then + break + elif $ac_last_try; then + as_fn_error $? "could not make $CONFIG_HEADERS" "$LINENO" 5 + else + ac_delim="$ac_delim!$ac_delim _$ac_delim!! " + fi +done + +# For the awk script, D is an array of macro values keyed by name, +# likewise P contains macro parameters if any. Preserve backslash +# newline sequences. + +ac_word_re=[_$as_cr_Letters][_$as_cr_alnum]* +sed -n ' +s/.\{148\}/&'"$ac_delim"'/g +t rset +:rset +s/^[ ]*#[ ]*define[ ][ ]*/ / +t def +d +:def +s/\\$// +t bsnl +s/["\\]/\\&/g +s/^ \('"$ac_word_re"'\)\(([^()]*)\)[ ]*\(.*\)/P["\1"]="\2"\ +D["\1"]=" \3"/p +s/^ \('"$ac_word_re"'\)[ ]*\(.*\)/D["\1"]=" \2"/p +d +:bsnl +s/["\\]/\\&/g +s/^ \('"$ac_word_re"'\)\(([^()]*)\)[ ]*\(.*\)/P["\1"]="\2"\ +D["\1"]=" \3\\\\\\n"\\/p +t cont +s/^ \('"$ac_word_re"'\)[ ]*\(.*\)/D["\1"]=" \2\\\\\\n"\\/p +t cont +d +:cont +n +s/.\{148\}/&'"$ac_delim"'/g +t clear +:clear +s/\\$// +t bsnlc +s/["\\]/\\&/g; s/^/"/; s/$/"/p +d +:bsnlc +s/["\\]/\\&/g; s/^/"/; s/$/\\\\\\n"\\/p +b cont +' >$CONFIG_STATUS || ac_write_fail=1 + +cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 + for (key in D) D_is_set[key] = 1 + FS = "" +} +/^[\t ]*#[\t ]*(define|undef)[\t ]+$ac_word_re([\t (]|\$)/ { + line = \$ 0 + split(line, arg, " ") + if (arg[1] == "#") { + defundef = arg[2] + mac1 = arg[3] + } else { + defundef = substr(arg[1], 2) + mac1 = arg[2] + } + split(mac1, mac2, "(") #) + macro = mac2[1] + prefix = substr(line, 1, index(line, defundef) - 1) + if (D_is_set[macro]) { + # Preserve the white space surrounding the "#". + print prefix "define", macro P[macro] D[macro] + next + } else { + # Replace #undef with comments. This is necessary, for example, + # in the case of _POSIX_SOURCE, which is predefined and required + # on some systems where configure will not decide to define it. + if (defundef == "undef") { + print "/*", prefix defundef, macro, "*/" + next + } + } +} +{ print } +_ACAWK +_ACEOF +cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 + as_fn_error $? "could not setup config headers machinery" "$LINENO" 5 +fi # test -n "$CONFIG_HEADERS" + + +eval set X " :F $CONFIG_FILES :H $CONFIG_HEADERS :C $CONFIG_COMMANDS" +shift +for ac_tag +do + case $ac_tag in + :[FHLC]) ac_mode=$ac_tag; continue;; + esac + case $ac_mode$ac_tag in + :[FHL]*:*);; + :L* | :C*:*) as_fn_error $? "invalid tag \`$ac_tag'" "$LINENO" 5;; + :[FH]-) ac_tag=-:-;; + :[FH]*) ac_tag=$ac_tag:$ac_tag.in;; + esac + ac_save_IFS=$IFS + IFS=: + set x $ac_tag + IFS=$ac_save_IFS + shift + ac_file=$1 + shift + + case $ac_mode in + :L) ac_source=$1;; + :[FH]) + ac_file_inputs= + for ac_f + do + case $ac_f in + -) ac_f="$ac_tmp/stdin";; + *) # Look for the file first in the build tree, then in the source tree + # (if the path is not absolute). The absolute path cannot be DOS-style, + # because $ac_f cannot contain `:'. + test -f "$ac_f" || + case $ac_f in + [\\/$]*) false;; + *) test -f "$srcdir/$ac_f" && ac_f="$srcdir/$ac_f";; + esac || + as_fn_error 1 "cannot find input file: \`$ac_f'" "$LINENO" 5;; + esac + case $ac_f in *\'*) ac_f=`printf "%s\n" "$ac_f" | sed "s/'/'\\\\\\\\''/g"`;; esac + as_fn_append ac_file_inputs " '$ac_f'" + done + + # Let's still pretend it is `configure' which instantiates (i.e., don't + # use $as_me), people would be surprised to read: + # /* config.h. Generated by config.status. */ + configure_input='Generated from '` + printf "%s\n" "$*" | sed 's|^[^:]*/||;s|:[^:]*/|, |g' + `' by configure.' + if test x"$ac_file" != x-; then + configure_input="$ac_file. $configure_input" + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: creating $ac_file" >&5 +printf "%s\n" "$as_me: creating $ac_file" >&6;} + fi + # Neutralize special characters interpreted by sed in replacement strings. + case $configure_input in #( + *\&* | *\|* | *\\* ) + ac_sed_conf_input=`printf "%s\n" "$configure_input" | + sed 's/[\\\\&|]/\\\\&/g'`;; #( + *) ac_sed_conf_input=$configure_input;; + esac + + case $ac_tag in + *:-:* | *:-) cat >"$ac_tmp/stdin" \ + || as_fn_error $? "could not create $ac_file" "$LINENO" 5 ;; + esac + ;; + esac + + ac_dir=`$as_dirname -- "$ac_file" || +$as_expr X"$ac_file" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ + X"$ac_file" : 'X\(//\)[^/]' \| \ + X"$ac_file" : 'X\(//\)$' \| \ + X"$ac_file" : 'X\(/\)' \| . 2>/dev/null || +printf "%s\n" X"$ac_file" | + sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ + s//\1/ + q + } + /^X\(\/\/\)[^/].*/{ + s//\1/ + q + } + /^X\(\/\/\)$/{ + s//\1/ + q + } + /^X\(\/\).*/{ + s//\1/ + q + } + s/.*/./; q'` + as_dir="$ac_dir"; as_fn_mkdir_p + ac_builddir=. + +case "$ac_dir" in +.) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;; +*) + ac_dir_suffix=/`printf "%s\n" "$ac_dir" | sed 's|^\.[\\/]||'` + # A ".." for each directory in $ac_dir_suffix. + ac_top_builddir_sub=`printf "%s\n" "$ac_dir_suffix" | sed 's|/[^\\/]*|/..|g;s|/||'` + case $ac_top_builddir_sub in + "") ac_top_builddir_sub=. ac_top_build_prefix= ;; + *) ac_top_build_prefix=$ac_top_builddir_sub/ ;; + esac ;; +esac +ac_abs_top_builddir=$ac_pwd +ac_abs_builddir=$ac_pwd$ac_dir_suffix +# for backward compatibility: +ac_top_builddir=$ac_top_build_prefix + +case $srcdir in + .) # We are building in place. + ac_srcdir=. + ac_top_srcdir=$ac_top_builddir_sub + ac_abs_top_srcdir=$ac_pwd ;; + [\\/]* | ?:[\\/]* ) # Absolute name. + ac_srcdir=$srcdir$ac_dir_suffix; + ac_top_srcdir=$srcdir + ac_abs_top_srcdir=$srcdir ;; + *) # Relative name. + ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix + ac_top_srcdir=$ac_top_build_prefix$srcdir + ac_abs_top_srcdir=$ac_pwd/$srcdir ;; +esac +ac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix + + + case $ac_mode in + :F) + # + # CONFIG_FILE + # + + case $INSTALL in + [\\/$]* | ?:[\\/]* ) ac_INSTALL=$INSTALL ;; + *) ac_INSTALL=$ac_top_build_prefix$INSTALL ;; + esac + ac_MKDIR_P=$MKDIR_P + case $MKDIR_P in + [\\/$]* | ?:[\\/]* ) ;; + */*) ac_MKDIR_P=$ac_top_build_prefix$MKDIR_P ;; + esac +_ACEOF + +cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 +# If the template does not know about datarootdir, expand it. +# FIXME: This hack should be removed a few years after 2.60. +ac_datarootdir_hack=; ac_datarootdir_seen= +ac_sed_dataroot=' +/datarootdir/ { + p + q +} +/@datadir@/p +/@docdir@/p +/@infodir@/p +/@localedir@/p +/@mandir@/p' +case `eval "sed -n \"\$ac_sed_dataroot\" $ac_file_inputs"` in +*datarootdir*) ac_datarootdir_seen=yes;; +*@datadir@*|*@docdir@*|*@infodir@*|*@localedir@*|*@mandir@*) + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting" >&5 +printf "%s\n" "$as_me: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting" >&2;} +_ACEOF +cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 + ac_datarootdir_hack=' + s&@datadir@&$datadir&g + s&@docdir@&$docdir&g + s&@infodir@&$infodir&g + s&@localedir@&$localedir&g + s&@mandir@&$mandir&g + s&\\\${datarootdir}&$datarootdir&g' ;; +esac +_ACEOF + +# Neutralize VPATH when `$srcdir' = `.'. +# Shell code in configure.ac might set extrasub. +# FIXME: do we really want to maintain this feature? +cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 +ac_sed_extra="$ac_vpsub +$extrasub +_ACEOF +cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 +:t +/@[a-zA-Z_][a-zA-Z_0-9]*@/!b +s|@configure_input@|$ac_sed_conf_input|;t t +s&@top_builddir@&$ac_top_builddir_sub&;t t +s&@top_build_prefix@&$ac_top_build_prefix&;t t +s&@srcdir@&$ac_srcdir&;t t +s&@abs_srcdir@&$ac_abs_srcdir&;t t +s&@top_srcdir@&$ac_top_srcdir&;t t +s&@abs_top_srcdir@&$ac_abs_top_srcdir&;t t +s&@builddir@&$ac_builddir&;t t +s&@abs_builddir@&$ac_abs_builddir&;t t +s&@abs_top_builddir@&$ac_abs_top_builddir&;t t +s&@INSTALL@&$ac_INSTALL&;t t +s&@MKDIR_P@&$ac_MKDIR_P&;t t +$ac_datarootdir_hack +" +eval sed \"\$ac_sed_extra\" "$ac_file_inputs" | $AWK -f "$ac_tmp/subs.awk" \ + >$ac_tmp/out || as_fn_error $? "could not create $ac_file" "$LINENO" 5 + +test -z "$ac_datarootdir_hack$ac_datarootdir_seen" && + { ac_out=`sed -n '/\${datarootdir}/p' "$ac_tmp/out"`; test -n "$ac_out"; } && + { ac_out=`sed -n '/^[ ]*datarootdir[ ]*:*=/p' \ + "$ac_tmp/out"`; test -z "$ac_out"; } && + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: $ac_file contains a reference to the variable \`datarootdir' +which seems to be undefined. Please make sure it is defined" >&5 +printf "%s\n" "$as_me: WARNING: $ac_file contains a reference to the variable \`datarootdir' +which seems to be undefined. Please make sure it is defined" >&2;} + + rm -f "$ac_tmp/stdin" + case $ac_file in + -) cat "$ac_tmp/out" && rm -f "$ac_tmp/out";; + *) rm -f "$ac_file" && mv "$ac_tmp/out" "$ac_file";; + esac \ + || as_fn_error $? "could not create $ac_file" "$LINENO" 5 + ;; + :H) + # + # CONFIG_HEADER + # + if test x"$ac_file" != x-; then + { + printf "%s\n" "/* $configure_input */" >&1 \ + && eval '$AWK -f "$ac_tmp/defines.awk"' "$ac_file_inputs" + } >"$ac_tmp/config.h" \ + || as_fn_error $? "could not create $ac_file" "$LINENO" 5 + if diff "$ac_file" "$ac_tmp/config.h" >/dev/null 2>&1; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: $ac_file is unchanged" >&5 +printf "%s\n" "$as_me: $ac_file is unchanged" >&6;} + else + rm -f "$ac_file" + mv "$ac_tmp/config.h" "$ac_file" \ + || as_fn_error $? "could not create $ac_file" "$LINENO" 5 + fi + else + printf "%s\n" "/* $configure_input */" >&1 \ + && eval '$AWK -f "$ac_tmp/defines.awk"' "$ac_file_inputs" \ + || as_fn_error $? "could not create -" "$LINENO" 5 + fi + ;; + + :C) { printf "%s\n" "$as_me:${as_lineno-$LINENO}: executing $ac_file commands" >&5 +printf "%s\n" "$as_me: executing $ac_file commands" >&6;} + ;; + esac + + + case $ac_file$ac_mode in + "libtool":C) + + # See if we are running on zsh, and set the options that allow our + # commands through without removal of \ escapes. + if test -n "${ZSH_VERSION+set}"; then + setopt NO_GLOB_SUBST + fi + + cfgfile=${ofile}T + trap "$RM \"$cfgfile\"; exit 1" 1 2 15 + $RM "$cfgfile" + + cat <<_LT_EOF >> "$cfgfile" +#! $SHELL +# Generated automatically by $as_me ($PACKAGE) $VERSION +# NOTE: Changes made to this file will be lost: look at ltmain.sh. + +# Provide generalized library-building support services. +# Written by Gordon Matzigkeit, 1996 + +# Copyright (C) 2014 Free Software Foundation, Inc. +# This is free software; see the source for copying conditions. There is NO +# warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + +# GNU Libtool is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of of the License, or +# (at your option) any later version. +# +# As a special exception to the GNU General Public License, if you +# distribute this file as part of a program or library that is built +# using GNU Libtool, you may include this file under the same +# distribution terms that you use for the rest of that program. +# +# GNU Libtool is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see . + + +# The names of the tagged configurations supported by this script. +available_tags='RC ' + +# Configured defaults for sys_lib_dlsearch_path munging. +: \${LT_SYS_LIBRARY_PATH="$configure_time_lt_sys_library_path"} + +# ### BEGIN LIBTOOL CONFIG + +# Which release of libtool.m4 was used? +macro_version=$macro_version +macro_revision=$macro_revision + +# Assembler program. +AS=$lt_AS + +# DLL creation program. +DLLTOOL=$lt_DLLTOOL + +# Object dumper program. +OBJDUMP=$lt_OBJDUMP + +# Whether or not to build shared libraries. +build_libtool_libs=$enable_shared + +# Whether or not to build static libraries. +build_old_libs=$enable_static + +# What type of objects to build. +pic_mode=$pic_mode + +# Whether or not to optimize for fast installation. +fast_install=$enable_fast_install + +# Shared archive member basename,for filename based shared library versioning on AIX. +shared_archive_member_spec=$shared_archive_member_spec + +# Shell to use when invoking shell scripts. +SHELL=$lt_SHELL + +# An echo program that protects backslashes. +ECHO=$lt_ECHO + +# The PATH separator for the build system. +PATH_SEPARATOR=$lt_PATH_SEPARATOR + +# The host system. +host_alias=$host_alias +host=$host +host_os=$host_os + +# The build system. +build_alias=$build_alias +build=$build +build_os=$build_os + +# A sed program that does not truncate output. +SED=$lt_SED + +# Sed that helps us avoid accidentally triggering echo(1) options like -n. +Xsed="\$SED -e 1s/^X//" + +# A grep program that handles long lines. +GREP=$lt_GREP + +# An ERE matcher. +EGREP=$lt_EGREP + +# A literal string matcher. +FGREP=$lt_FGREP + +# A BSD- or MS-compatible name lister. +NM=$lt_NM + +# Whether we need soft or hard links. +LN_S=$lt_LN_S + +# What is the maximum length of a command? +max_cmd_len=$max_cmd_len + +# Object file suffix (normally "o"). +objext=$ac_objext + +# Executable file suffix (normally ""). +exeext=$exeext + +# whether the shell understands "unset". +lt_unset=$lt_unset + +# turn spaces into newlines. +SP2NL=$lt_lt_SP2NL + +# turn newlines into spaces. +NL2SP=$lt_lt_NL2SP + +# convert \$build file names to \$host format. +to_host_file_cmd=$lt_cv_to_host_file_cmd + +# convert \$build files to toolchain format. +to_tool_file_cmd=$lt_cv_to_tool_file_cmd + +# A file(cmd) program that detects file types. +FILECMD=$lt_FILECMD + +# Method to check whether dependent libraries are shared objects. +deplibs_check_method=$lt_deplibs_check_method + +# Command to use when deplibs_check_method = "file_magic". +file_magic_cmd=$lt_file_magic_cmd + +# How to find potential files when deplibs_check_method = "file_magic". +file_magic_glob=$lt_file_magic_glob + +# Find potential files using nocaseglob when deplibs_check_method = "file_magic". +want_nocaseglob=$lt_want_nocaseglob + +# Command to associate shared and link libraries. +sharedlib_from_linklib_cmd=$lt_sharedlib_from_linklib_cmd + +# The archiver. +AR=$lt_AR + +# Flags to create an archive (by configure). +lt_ar_flags=$lt_ar_flags + +# Flags to create an archive. +AR_FLAGS=\${ARFLAGS-"\$lt_ar_flags"} + +# How to feed a file listing to the archiver. +archiver_list_spec=$lt_archiver_list_spec + +# A symbol stripping program. +STRIP=$lt_STRIP + +# Commands used to install an old-style archive. +RANLIB=$lt_RANLIB +old_postinstall_cmds=$lt_old_postinstall_cmds +old_postuninstall_cmds=$lt_old_postuninstall_cmds + +# Whether to use a lock for old archive extraction. +lock_old_archive_extraction=$lock_old_archive_extraction + +# A C compiler. +LTCC=$lt_CC + +# LTCC compiler flags. +LTCFLAGS=$lt_CFLAGS + +# Take the output of nm and produce a listing of raw symbols and C names. +global_symbol_pipe=$lt_lt_cv_sys_global_symbol_pipe + +# Transform the output of nm in a proper C declaration. +global_symbol_to_cdecl=$lt_lt_cv_sys_global_symbol_to_cdecl + +# Transform the output of nm into a list of symbols to manually relocate. +global_symbol_to_import=$lt_lt_cv_sys_global_symbol_to_import + +# Transform the output of nm in a C name address pair. +global_symbol_to_c_name_address=$lt_lt_cv_sys_global_symbol_to_c_name_address + +# Transform the output of nm in a C name address pair when lib prefix is needed. +global_symbol_to_c_name_address_lib_prefix=$lt_lt_cv_sys_global_symbol_to_c_name_address_lib_prefix + +# The name lister interface. +nm_interface=$lt_lt_cv_nm_interface + +# Specify filename containing input files for \$NM. +nm_file_list_spec=$lt_nm_file_list_spec + +# The root where to search for dependent libraries,and where our libraries should be installed. +lt_sysroot=$lt_sysroot + +# Command to truncate a binary pipe. +lt_truncate_bin=$lt_lt_cv_truncate_bin + +# The name of the directory that contains temporary libtool files. +objdir=$objdir + +# Used to examine libraries when file_magic_cmd begins with "file". +MAGIC_CMD=$MAGIC_CMD + +# Must we lock files when doing compilation? +need_locks=$lt_need_locks + +# Manifest tool. +MANIFEST_TOOL=$lt_MANIFEST_TOOL + +# Tool to manipulate archived DWARF debug symbol files on Mac OS X. +DSYMUTIL=$lt_DSYMUTIL + +# Tool to change global to local symbols on Mac OS X. +NMEDIT=$lt_NMEDIT + +# Tool to manipulate fat objects and archives on Mac OS X. +LIPO=$lt_LIPO + +# ldd/readelf like tool for Mach-O binaries on Mac OS X. +OTOOL=$lt_OTOOL + +# ldd/readelf like tool for 64 bit Mach-O binaries on Mac OS X 10.4. +OTOOL64=$lt_OTOOL64 + +# Old archive suffix (normally "a"). +libext=$libext + +# Shared library suffix (normally ".so"). +shrext_cmds=$lt_shrext_cmds + +# The commands to extract the exported symbol list from a shared archive. +extract_expsyms_cmds=$lt_extract_expsyms_cmds + +# Variables whose values should be saved in libtool wrapper scripts and +# restored at link time. +variables_saved_for_relink=$lt_variables_saved_for_relink + +# Do we need the "lib" prefix for modules? +need_lib_prefix=$need_lib_prefix + +# Do we need a version for libraries? +need_version=$need_version + +# Library versioning type. +version_type=$version_type + +# Shared library runtime path variable. +runpath_var=$runpath_var + +# Shared library path variable. +shlibpath_var=$shlibpath_var + +# Is shlibpath searched before the hard-coded library search path? +shlibpath_overrides_runpath=$shlibpath_overrides_runpath + +# Format of library name prefix. +libname_spec=$lt_libname_spec + +# List of archive names. First name is the real one, the rest are links. +# The last name is the one that the linker finds with -lNAME +library_names_spec=$lt_library_names_spec + +# The coded name of the library, if different from the real name. +soname_spec=$lt_soname_spec + +# Permission mode override for installation of shared libraries. +install_override_mode=$lt_install_override_mode + +# Command to use after installation of a shared archive. +postinstall_cmds=$lt_postinstall_cmds + +# Command to use after uninstallation of a shared archive. +postuninstall_cmds=$lt_postuninstall_cmds + +# Commands used to finish a libtool library installation in a directory. +finish_cmds=$lt_finish_cmds + +# As "finish_cmds", except a single script fragment to be evaled but +# not shown. +finish_eval=$lt_finish_eval + +# Whether we should hardcode library paths into libraries. +hardcode_into_libs=$hardcode_into_libs + +# Compile-time system search path for libraries. +sys_lib_search_path_spec=$lt_sys_lib_search_path_spec + +# Detected run-time system search path for libraries. +sys_lib_dlsearch_path_spec=$lt_configure_time_dlsearch_path + +# Explicit LT_SYS_LIBRARY_PATH set during ./configure time. +configure_time_lt_sys_library_path=$lt_configure_time_lt_sys_library_path + +# Whether dlopen is supported. +dlopen_support=$enable_dlopen + +# Whether dlopen of programs is supported. +dlopen_self=$enable_dlopen_self + +# Whether dlopen of statically linked programs is supported. +dlopen_self_static=$enable_dlopen_self_static + +# Commands to strip libraries. +old_striplib=$lt_old_striplib +striplib=$lt_striplib + + +# The linker used to build libraries. +LD=$lt_LD + +# How to create reloadable object files. +reload_flag=$lt_reload_flag +reload_cmds=$lt_reload_cmds + +# Commands used to build an old-style archive. +old_archive_cmds=$lt_old_archive_cmds + +# A language specific compiler. +CC=$lt_compiler + +# Is the compiler the GNU compiler? +with_gcc=$GCC + +# Compiler flag to turn off builtin functions. +no_builtin_flag=$lt_lt_prog_compiler_no_builtin_flag + +# Additional compiler flags for building library objects. +pic_flag=$lt_lt_prog_compiler_pic + +# How to pass a linker flag through the compiler. +wl=$lt_lt_prog_compiler_wl + +# Compiler flag to prevent dynamic linking. +link_static_flag=$lt_lt_prog_compiler_static + +# Does compiler simultaneously support -c and -o options? +compiler_c_o=$lt_lt_cv_prog_compiler_c_o + +# Whether or not to add -lc for building shared libraries. +build_libtool_need_lc=$archive_cmds_need_lc + +# Whether or not to disallow shared libs when runtime libs are static. +allow_libtool_libs_with_static_runtimes=$enable_shared_with_static_runtimes + +# Compiler flag to allow reflexive dlopens. +export_dynamic_flag_spec=$lt_export_dynamic_flag_spec + +# Compiler flag to generate shared objects directly from archives. +whole_archive_flag_spec=$lt_whole_archive_flag_spec + +# Whether the compiler copes with passing no objects directly. +compiler_needs_object=$lt_compiler_needs_object + +# Create an old-style archive from a shared archive. +old_archive_from_new_cmds=$lt_old_archive_from_new_cmds + +# Create a temporary old-style archive to link instead of a shared archive. +old_archive_from_expsyms_cmds=$lt_old_archive_from_expsyms_cmds + +# Commands used to build a shared archive. +archive_cmds=$lt_archive_cmds +archive_expsym_cmds=$lt_archive_expsym_cmds + +# Commands used to build a loadable module if different from building +# a shared archive. +module_cmds=$lt_module_cmds +module_expsym_cmds=$lt_module_expsym_cmds + +# Whether we are building with GNU ld or not. +with_gnu_ld=$lt_with_gnu_ld + +# Flag that allows shared libraries with undefined symbols to be built. +allow_undefined_flag=$lt_allow_undefined_flag + +# Flag that enforces no undefined symbols. +no_undefined_flag=$lt_no_undefined_flag + +# Flag to hardcode \$libdir into a binary during linking. +# This must work even if \$libdir does not exist +hardcode_libdir_flag_spec=$lt_hardcode_libdir_flag_spec + +# Whether we need a single "-rpath" flag with a separated argument. +hardcode_libdir_separator=$lt_hardcode_libdir_separator + +# Set to "yes" if using DIR/libNAME\$shared_ext during linking hardcodes +# DIR into the resulting binary. +hardcode_direct=$hardcode_direct + +# Set to "yes" if using DIR/libNAME\$shared_ext during linking hardcodes +# DIR into the resulting binary and the resulting library dependency is +# "absolute",i.e impossible to change by setting \$shlibpath_var if the +# library is relocated. +hardcode_direct_absolute=$hardcode_direct_absolute + +# Set to "yes" if using the -LDIR flag during linking hardcodes DIR +# into the resulting binary. +hardcode_minus_L=$hardcode_minus_L + +# Set to "yes" if using SHLIBPATH_VAR=DIR during linking hardcodes DIR +# into the resulting binary. +hardcode_shlibpath_var=$hardcode_shlibpath_var + +# Set to "yes" if building a shared library automatically hardcodes DIR +# into the library and all subsequent libraries and executables linked +# against it. +hardcode_automatic=$hardcode_automatic + +# Set to yes if linker adds runtime paths of dependent libraries +# to runtime path list. +inherit_rpath=$inherit_rpath + +# Whether libtool must link a program against all its dependency libraries. +link_all_deplibs=$link_all_deplibs + +# Set to "yes" if exported symbols are required. +always_export_symbols=$always_export_symbols + +# The commands to list exported symbols. +export_symbols_cmds=$lt_export_symbols_cmds + +# Symbols that should not be listed in the preloaded symbols. +exclude_expsyms=$lt_exclude_expsyms + +# Symbols that must always be exported. +include_expsyms=$lt_include_expsyms + +# Commands necessary for linking programs (against libraries) with templates. +prelink_cmds=$lt_prelink_cmds + +# Commands necessary for finishing linking programs. +postlink_cmds=$lt_postlink_cmds + +# Specify filename containing input files. +file_list_spec=$lt_file_list_spec + +# How to hardcode a shared library path into an executable. +hardcode_action=$hardcode_action + +# ### END LIBTOOL CONFIG + +_LT_EOF + + cat <<'_LT_EOF' >> "$cfgfile" + +# ### BEGIN FUNCTIONS SHARED WITH CONFIGURE + +# func_munge_path_list VARIABLE PATH +# ----------------------------------- +# VARIABLE is name of variable containing _space_ separated list of +# directories to be munged by the contents of PATH, which is string +# having a format: +# "DIR[:DIR]:" +# string "DIR[ DIR]" will be prepended to VARIABLE +# ":DIR[:DIR]" +# string "DIR[ DIR]" will be appended to VARIABLE +# "DIRP[:DIRP]::[DIRA:]DIRA" +# string "DIRP[ DIRP]" will be prepended to VARIABLE and string +# "DIRA[ DIRA]" will be appended to VARIABLE +# "DIR[:DIR]" +# VARIABLE will be replaced by "DIR[ DIR]" +func_munge_path_list () +{ + case x$2 in + x) + ;; + *:) + eval $1=\"`$ECHO $2 | $SED 's/:/ /g'` \$$1\" + ;; + x:*) + eval $1=\"\$$1 `$ECHO $2 | $SED 's/:/ /g'`\" + ;; + *::*) + eval $1=\"\$$1\ `$ECHO $2 | $SED -e 's/.*:://' -e 's/:/ /g'`\" + eval $1=\"`$ECHO $2 | $SED -e 's/::.*//' -e 's/:/ /g'`\ \$$1\" + ;; + *) + eval $1=\"`$ECHO $2 | $SED 's/:/ /g'`\" + ;; + esac +} + + +# Calculate cc_basename. Skip known compiler wrappers and cross-prefix. +func_cc_basename () +{ + for cc_temp in $*""; do + case $cc_temp in + compile | *[\\/]compile | ccache | *[\\/]ccache ) ;; + distcc | *[\\/]distcc | purify | *[\\/]purify ) ;; + \-*) ;; + *) break;; + esac + done + func_cc_basename_result=`$ECHO "$cc_temp" | $SED "s%.*/%%; s%^$host_alias-%%"` +} + + +# ### END FUNCTIONS SHARED WITH CONFIGURE + +_LT_EOF + + case $host_os in + aix3*) + cat <<\_LT_EOF >> "$cfgfile" +# AIX sometimes has problems with the GCC collect2 program. For some +# reason, if we set the COLLECT_NAMES environment variable, the problems +# vanish in a puff of smoke. +if test set != "${COLLECT_NAMES+set}"; then + COLLECT_NAMES= + export COLLECT_NAMES +fi +_LT_EOF + ;; + esac + + + +ltmain=$ac_aux_dir/ltmain.sh + + + # We use sed instead of cat because bash on DJGPP gets confused if + # if finds mixed CR/LF and LF-only lines. Since sed operates in + # text mode, it properly converts lines to CR/LF. This bash problem + # is reportedly fixed, but why not run on old versions too? + $SED '$q' "$ltmain" >> "$cfgfile" \ + || (rm -f "$cfgfile"; exit 1) + + mv -f "$cfgfile" "$ofile" || + (rm -f "$ofile" && cp "$cfgfile" "$ofile" && rm -f "$cfgfile") + chmod +x "$ofile" + + + cat <<_LT_EOF >> "$ofile" + +# ### BEGIN LIBTOOL TAG CONFIG: RC + +# The linker used to build libraries. +LD=$lt_LD_RC + +# How to create reloadable object files. +reload_flag=$lt_reload_flag_RC +reload_cmds=$lt_reload_cmds_RC + +# Commands used to build an old-style archive. +old_archive_cmds=$lt_old_archive_cmds_RC + +# A language specific compiler. +CC=$lt_compiler_RC + +# Is the compiler the GNU compiler? +with_gcc=$GCC_RC + +# Compiler flag to turn off builtin functions. +no_builtin_flag=$lt_lt_prog_compiler_no_builtin_flag_RC + +# Additional compiler flags for building library objects. +pic_flag=$lt_lt_prog_compiler_pic_RC + +# How to pass a linker flag through the compiler. +wl=$lt_lt_prog_compiler_wl_RC + +# Compiler flag to prevent dynamic linking. +link_static_flag=$lt_lt_prog_compiler_static_RC + +# Does compiler simultaneously support -c and -o options? +compiler_c_o=$lt_lt_cv_prog_compiler_c_o_RC + +# Whether or not to add -lc for building shared libraries. +build_libtool_need_lc=$archive_cmds_need_lc_RC + +# Whether or not to disallow shared libs when runtime libs are static. +allow_libtool_libs_with_static_runtimes=$enable_shared_with_static_runtimes_RC + +# Compiler flag to allow reflexive dlopens. +export_dynamic_flag_spec=$lt_export_dynamic_flag_spec_RC + +# Compiler flag to generate shared objects directly from archives. +whole_archive_flag_spec=$lt_whole_archive_flag_spec_RC + +# Whether the compiler copes with passing no objects directly. +compiler_needs_object=$lt_compiler_needs_object_RC + +# Create an old-style archive from a shared archive. +old_archive_from_new_cmds=$lt_old_archive_from_new_cmds_RC + +# Create a temporary old-style archive to link instead of a shared archive. +old_archive_from_expsyms_cmds=$lt_old_archive_from_expsyms_cmds_RC + +# Commands used to build a shared archive. +archive_cmds=$lt_archive_cmds_RC +archive_expsym_cmds=$lt_archive_expsym_cmds_RC + +# Commands used to build a loadable module if different from building +# a shared archive. +module_cmds=$lt_module_cmds_RC +module_expsym_cmds=$lt_module_expsym_cmds_RC + +# Whether we are building with GNU ld or not. +with_gnu_ld=$lt_with_gnu_ld_RC + +# Flag that allows shared libraries with undefined symbols to be built. +allow_undefined_flag=$lt_allow_undefined_flag_RC + +# Flag that enforces no undefined symbols. +no_undefined_flag=$lt_no_undefined_flag_RC + +# Flag to hardcode \$libdir into a binary during linking. +# This must work even if \$libdir does not exist +hardcode_libdir_flag_spec=$lt_hardcode_libdir_flag_spec_RC + +# Whether we need a single "-rpath" flag with a separated argument. +hardcode_libdir_separator=$lt_hardcode_libdir_separator_RC + +# Set to "yes" if using DIR/libNAME\$shared_ext during linking hardcodes +# DIR into the resulting binary. +hardcode_direct=$hardcode_direct_RC + +# Set to "yes" if using DIR/libNAME\$shared_ext during linking hardcodes +# DIR into the resulting binary and the resulting library dependency is +# "absolute",i.e impossible to change by setting \$shlibpath_var if the +# library is relocated. +hardcode_direct_absolute=$hardcode_direct_absolute_RC + +# Set to "yes" if using the -LDIR flag during linking hardcodes DIR +# into the resulting binary. +hardcode_minus_L=$hardcode_minus_L_RC + +# Set to "yes" if using SHLIBPATH_VAR=DIR during linking hardcodes DIR +# into the resulting binary. +hardcode_shlibpath_var=$hardcode_shlibpath_var_RC + +# Set to "yes" if building a shared library automatically hardcodes DIR +# into the library and all subsequent libraries and executables linked +# against it. +hardcode_automatic=$hardcode_automatic_RC + +# Set to yes if linker adds runtime paths of dependent libraries +# to runtime path list. +inherit_rpath=$inherit_rpath_RC + +# Whether libtool must link a program against all its dependency libraries. +link_all_deplibs=$link_all_deplibs_RC + +# Set to "yes" if exported symbols are required. +always_export_symbols=$always_export_symbols_RC + +# The commands to list exported symbols. +export_symbols_cmds=$lt_export_symbols_cmds_RC + +# Symbols that should not be listed in the preloaded symbols. +exclude_expsyms=$lt_exclude_expsyms_RC + +# Symbols that must always be exported. +include_expsyms=$lt_include_expsyms_RC + +# Commands necessary for linking programs (against libraries) with templates. +prelink_cmds=$lt_prelink_cmds_RC + +# Commands necessary for finishing linking programs. +postlink_cmds=$lt_postlink_cmds_RC + +# Specify filename containing input files. +file_list_spec=$lt_file_list_spec_RC + +# How to hardcode a shared library path into an executable. +hardcode_action=$hardcode_action_RC + +# ### END LIBTOOL TAG CONFIG: RC +_LT_EOF + + ;; + "ftoption.h":F) mv ftoption.h ftoption.tmp + eval "sed $FTOPTION_H_SED < ftoption.tmp > ftoption.h" + rm ftoption.tmp ;; + + esac +done # for ac_tag + + +as_fn_exit 0 +_ACEOF +ac_clean_files=$ac_clean_files_save + +test $ac_write_fail = 0 || + as_fn_error $? "write failure creating $CONFIG_STATUS" "$LINENO" 5 + + +# configure is writing to config.log, and then calls config.status. +# config.status does its own redirection, appending to config.log. +# Unfortunately, on DOS this fails, as config.log is still kept open +# by configure, so config.status won't be able to write to it; its +# output is simply discarded. So we exec the FD to /dev/null, +# effectively closing config.log, so it can be properly (re)opened and +# appended to by config.status. When coming back to configure, we +# need to make the FD available again. +if test "$no_create" != yes; then + ac_cs_success=: + ac_config_status_args= + test "$silent" = yes && + ac_config_status_args="$ac_config_status_args --quiet" + exec 5>/dev/null + $SHELL $CONFIG_STATUS $ac_config_status_args || ac_cs_success=false + exec 5>>config.log + # Use ||, not &&, to avoid exiting from the if with $? = 1, which + # would make configure fail if this is the last instruction. + $ac_cs_success || as_fn_exit 1 +fi +if test -n "$ac_unrecognized_opts" && test "$enable_option_checking" != no; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: unrecognized options: $ac_unrecognized_opts" >&5 +printf "%s\n" "$as_me: WARNING: unrecognized options: $ac_unrecognized_opts" >&2;} +fi + + +{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: + +Library configuration: + external zlib: $have_zlib + bzip2: $have_bzip2 + libpng: $have_libpng + harfbuzz: $have_harfbuzz + brotli: $have_brotli + pthread: $have_pthread +" >&5 +printf "%s\n" "$as_me: + +Library configuration: + external zlib: $have_zlib + bzip2: $have_bzip2 + libpng: $have_libpng + harfbuzz: $have_harfbuzz + brotli: $have_brotli + pthread: $have_pthread +" >&6;} + +# Warn if docwriter is not installed + +if test $have_docwriter = no; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: + \`make refdoc' will fail since pip package \`docwriter' is not installed. + To install, run \`$PIP install docwriter', or to use a Python + virtual environment, run \`make refdoc-venv' (requires pip package + \`virtualenv'). These operations require Python >= $PYTHON_MIN_VERSION. + " >&5 +printf "%s\n" "$as_me: WARNING: + \`make refdoc' will fail since pip package \`docwriter' is not installed. + To install, run \`$PIP install docwriter', or to use a Python + virtual environment, run \`make refdoc-venv' (requires pip package + \`virtualenv'). These operations require Python >= $PYTHON_MIN_VERSION. + " >&2;} +fi + +# Warn if pthread is not available + +if test $have_pthread = no; then + { printf "%s\n" "$as_me:${as_lineno-$LINENO}: WARNING: + \`FT_DEBUG_LOGGING' will not work since the \`pthread' library is not + available. This warning can be safely ignored if you don't plan to use + this configuration macro. + " >&5 +printf "%s\n" "$as_me: WARNING: + \`FT_DEBUG_LOGGING' will not work since the \`pthread' library is not + available. This warning can be safely ignored if you don't plan to use + this configuration macro. + " >&2;} +fi + +# end of configure.raw + diff --git a/3rdparty/freetype-2.13.2/builds/unix/configure.ac b/3rdparty/freetype-2.13.2/builds/unix/configure.ac new file mode 100644 index 000000000..5df9d8612 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/configure.ac @@ -0,0 +1,1179 @@ +# This file is part of the FreeType project. +# +# Process this file with autoconf to produce a configure script. +# +# Copyright (C) 2001-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + +AC_INIT([FreeType], [2.13.2], [freetype@nongnu.org], [freetype]) +AC_CONFIG_SRCDIR([ftconfig.h.in]) + + +# Don't forget to update `docs/VERSIONS.TXT'! + +version_info='26:1:20' +AC_SUBST([version_info]) +ft_version=`echo $version_info | tr : .` +AC_SUBST([ft_version]) + + +# checks for system type + +AC_CANONICAL_HOST + + +# checks for programs + +AC_PROG_CC +AC_PROG_CPP +AC_SUBST(EXEEXT) + +PKG_PROG_PKG_CONFIG([0.24]) + +LT_INIT(win32-dll) +AC_CHECK_HEADER([windows.h], [LT_PROG_RC]) + + +# checks for native programs to generate building tool + +if test ${cross_compiling} = yes; then + AC_CHECK_PROG(CC_BUILD, ${build}-gcc, ${build}-gcc) + test -z "${CC_BUILD}" && AC_CHECK_PROG(CC_BUILD, gcc, gcc) + test -z "${CC_BUILD}" && AC_CHECK_PROG(CC_BUILD, cc, cc, , , /usr/ucb/cc) + test -z "${CC_BUILD}" && AC_MSG_ERROR([cannot find native C compiler]) + + AC_MSG_CHECKING([for suffix of native executables]) + rm -f a.* b.* a_out.exe conftest.* + echo > conftest.c "int main(void) { return 0;}" + ${CC_BUILD} conftest.c || AC_MSG_ERROR([native C compiler is not working]) + rm -f conftest.c + if test -x a.out -o -x b.out -o -x conftest; then + EXEEXT_BUILD="" + elif test -x a_out.exe -o -x conftest.exe; then + EXEEXT_BUILD=".exe" + elif test -x conftest.*; then + EXEEXT_BUILD=`echo conftest.* | sed -n '1s/^.*\././'` + fi + rm -f a.* b.* a_out.exe conftest.* + AC_MSG_RESULT($EXEEXT_BUILD) +else + CC_BUILD=${CC} + EXEEXT_BUILD=${EXEEXT} +fi + +AC_SUBST(CC_BUILD) +AC_SUBST(EXEEXT_BUILD) + + +# Since these files will be eventually called from another directory (namely +# from the top level) we make the path of the scripts absolute. +# +# This small code snippet has been taken from automake's `ylwrap' script. + +AC_PROG_INSTALL +case "$INSTALL" in +[[\\/]]* | ?:[[\\/]]*) + ;; +*[[\\/]]*) + INSTALL="`pwd`/$INSTALL" + ;; +esac + +AC_PROG_MKDIR_P +case "$MKDIR_P" in +[[\\/]]* | ?:[[\\/]]*) + ;; +*[[\\/]]*) + MKDIR_P="`pwd`/$MKDIR_P" + ;; +esac + + +# checks for header files + +AC_CHECK_HEADERS([fcntl.h unistd.h]) + + +# checks for typedefs, structures, and compiler characteristics + +AC_C_CONST + +AC_ARG_ENABLE([freetype-config], + AS_HELP_STRING([--enable-freetype-config], [install freetype-config]), + [case "${enableval}" in + yes) enable_freetype_config="TRUE" ;; + no) enable_freetype_config="FALSE" ;; + *) AC_MSG_ERROR([unknown value '${enableval}' passed with --enable-freetype-config]) ;; + esac], [enable_freetype_config="FALSE"]) + +AC_SUBST(INSTALL_FT2_CONFIG, [$enable_freetype_config]) + +# checks for library functions + +AC_SYS_LARGEFILE + +# Here we check whether we can use our mmap file component. +# +# Note that `ftsystem.c` for Windows has its own mmap-like implementation +# not covered by `AC_FUNC_MMAP` and/or `FT_UNMAP_PARAM`. + +AC_ARG_ENABLE([mmap], + AS_HELP_STRING([--disable-mmap], + [do not check mmap() and do not use]), + [enable_mmap="no"], [enable_mmap="yes"]) +if test "x${enable_mmap}" != "xno"; then + case "$host" in + *-*-mingw*) + AC_MSG_CHECKING([for working mmap]) + AC_MSG_RESULT([using MapViewOfFile in Windows]) + FTSYS_SRC='$(TOP_DIR)/builds/windows/ftsystem.c' + ;; + *) + AC_FUNC_MMAP + if test "$ac_cv_func_mmap_fixed_mapped" = "yes"; then + FTSYS_SRC='$(PLATFORM_DIR)/ftsystem.c' + + AC_CHECK_DECLS([munmap], + [], + [], + [ + +#ifdef HAVE_UNISTD_H +#include +#endif +#include + + ]) + + FT_MUNMAP_PARAM + fi + ;; + esac +fi + +if test -z "$FTSYS_SRC"; then + FTSYS_SRC='$(BASE_DIR)/ftsystem.c' +fi +AC_SUBST([FTSYS_SRC]) + + +# get compiler flags right +# +# We try to make the compiler work for C99-strict source. Even if the +# C compiler is gcc and C99 flags are available, some system headers +# might be broken in C99 mode. We have to check whether compilation +# finishes successfully. +# +if test "x$GCC" = xyes; then + XX_CFLAGS="-Wall" + case "$host" in + *-*-mingw*) + XX_ANSIFLAGS="-pedantic" + ;; + *-*-aix*) + XX_ANSIFLAGS="-pedantic" + ;; + *) + XX_ANSIFLAGS="" + + for a in "-pedantic" "-std=c99" + do + AC_MSG_CHECKING([$CC compiler flag ${a} to assure ANSI C99 works correctly]) + orig_CFLAGS="${CFLAGS}" + CFLAGS="${CFLAGS} ${XX_ANSIFLAGS} ${a}" + AC_COMPILE_IFELSE([ + AC_LANG_PROGRAM([ + +#include + + ], + [ + + { + puts( "" ); + return 0; + } + + ])], + [AC_MSG_RESULT([ok, adding to XX_ANSIFLAGS]) + XX_ANSIFLAGS="${XX_ANSIFLAGS} ${a}" + ], + [AC_MSG_RESULT([no])]) + CFLAGS="${orig_CFLAGS}" + done + ;; + esac +else + case "$host" in + *-dec-osf*) + CFLAGS= + XX_CFLAGS="-std1 -g3" + XX_ANSIFLAGS= + ;; + *) + XX_CFLAGS= + XX_ANSIFLAGS= + ;; + esac +fi +AC_SUBST([XX_CFLAGS]) +AC_SUBST([XX_ANSIFLAGS]) + + +# It is recommended that shared libraries hide symbols except those with +# explicit __attribute__((visibility("default"))). +# +found_visibility_flag=no +AC_MSG_CHECKING([for -fvisibility=hidden compiler flag]) +orig_CFLAGS="${CFLAGS}" +CFLAGS="${CFLAGS} -fvisibility=hidden" +AC_LINK_IFELSE([AC_LANG_PROGRAM([], [])], + [found_visibility_flag=yes + AC_MSG_RESULT(yes)], + [CFLAGS="${orig_CFLAGS}" + AC_MSG_RESULT(no)]) + +if test "${found_visibility_flag}" = "no"; then + AC_MSG_CHECKING([for -xldscope=hidden compiler flag]) + orig_CFLAGS="${CFLAGS}" + CFLAGS="${CFLAGS} -xldscope=hidden" + AC_LINK_IFELSE([AC_LANG_PROGRAM([], [])], + [found_visibility_flag=yes + AC_MSG_RESULT(yes)], + [CFLAGS="${orig_CFLAGS}" + AC_MSG_RESULT(no)]) +fi + +# All library tests below try `pkg-config' first. If that fails, a function +# from the library is tested in the traditional autoconf way (zlib, bzip2), +# or a config script is called (libpng). +# +# The `xxx_reqpriv' variables are for the `Requires.private' field in +# `freetype2.pc'. The `xxx_libspriv' variables are for the `Libs.private' +# field in `freetype2.pc' if pkg-config doesn't find a proper .pc file. +# +# The `xxx_libsstaticconf' variables are for the `freetype-config' script. +# +# Note that a call to PKG_CHECK_MODULES(XXX, ...) sets and creates the +# output variables `XXX_CFLAGS' and `XXX_LIBS'. In case one or both are set +# for a library by the user, no entry for this library is added to +# `Requires.private'. Instead, it gets added to `Libs.private' + + +# check for system zlib + +AC_ARG_WITH([zlib], + [AS_HELP_STRING([--with-zlib=@<:@yes|no|auto@:>@], + [use system zlib instead of internal library @<:@default=auto@:>@])], + [], [with_zlib=auto]) + +have_zlib=no +if test x"$with_zlib" = xyes -o x"$with_zlib" = xauto; then + zlib_pkg="zlib" + have_zlib_pkg=no + + if test x"$ZLIB_CFLAGS" = x -a x"$ZLIB_LIBS" = x; then + PKG_CHECK_EXISTS([$zlib_pkg], [have_zlib_pkg=yes]) + fi + PKG_CHECK_MODULES([ZLIB], [$zlib_pkg], + [have_zlib="yes (pkg-config)"], [:]) + + if test $have_zlib_pkg = yes; then + # we have zlib.pc + zlib_reqpriv="$zlib_pkg" + zlib_libspriv= + zlib_libsstaticconf=`$PKG_CONFIG --static --libs "$zlib_pkg"` + else + zlib_reqpriv= + + if test "$have_zlib" != no; then + # ZLIB_CFLAGS and ZLIB_LIBS are set by the user + zlib_libspriv="$ZLIB_LIBS" + zlib_libsstaticconf="$ZLIB_LIBS" + have_zlib="yes (ZLIB_CFLAGS and ZLIB_LIBS)" + else + # fall back to standard autoconf test + AC_CHECK_LIB([z], + [gzsetparams], + [AC_CHECK_HEADER([zlib.h], + [have_zlib="yes (autoconf test)" + zlib_libspriv="-lz" + zlib_libsstaticconf="$zlib_libspriv" + ZLIB_LIBS="$zlib_libspriv"])]) + fi + fi +fi + +if test x"$with_zlib" = xyes -a "$have_zlib" = no; then + AC_MSG_ERROR([external zlib support requested but library not found]) +fi + +SYSTEM_ZLIB= +if test "$have_zlib" != no; then + SYSTEM_ZLIB=yes +fi +AC_SUBST([SYSTEM_ZLIB]) + + +# check for system libbz2 + +AC_ARG_WITH([bzip2], + [AS_HELP_STRING([--with-bzip2=@<:@yes|no|auto@:>@], + [support bzip2 compressed fonts @<:@default=auto@:>@])], + [], [with_bzip2=auto]) + +have_bzip2=no +if test x"$with_bzip2" = xyes -o x"$with_bzip2" = xauto; then + bzip2_pkg="bzip2" + have_bzip2_pkg=no + + if test x"$BZIP2_CFLAGS" = x -a x"$BZIP2_LIBS" = x; then + PKG_CHECK_EXISTS([$bzip2_pkg], [have_bzip2_pkg=yes]) + fi + PKG_CHECK_MODULES([BZIP2], [$bzip2_pkg], + [have_bzip2="yes (pkg-config)"], [:]) + + if test $have_bzip2_pkg = yes; then + # we have bzip2.pc + bzip2_reqpriv="$bzip2_pkg" + bzip2_libspriv= + bzip2_libsstaticconf=`$PKG_CONFIG --static --libs "$bzip2_pkg"` + else + bzip2_reqpriv= + + if test "$have_bzip2" != no; then + # BZIP2_CFLAGS and BZIP2_LIBS are set by the user + bzip2_libspriv="$BZIP2_LIBS" + bzip2_libsstaticconf="$BZIP2_LIBS" + have_bzip2="yes (BZIP2_CFLAGS and BZIP2_LIBS)" + else + # fall back to standard autoconf test + AC_CHECK_LIB([bz2], + [BZ2_bzDecompress], + [AC_CHECK_HEADER([bzlib.h], + [have_bzip2="yes (autoconf test)" + bzip2_libspriv="-lbz2" + bzip2_libsstaticconf="$bzip2_libspriv" + BZIP2_LIBS="$bzip2_libspriv"])]) + fi + fi +fi + +if test x"$with_bzip2" = xyes -a "$have_bzip2" = no; then + AC_MSG_ERROR([bzip2 support requested but library not found]) +fi + + +# check for system libpng + +AC_ARG_WITH([png], + [AS_HELP_STRING([--with-png=@<:@yes|no|auto@:>@], + [support png compressed OpenType embedded bitmaps @<:@default=auto@:>@])], + [], [with_png=auto]) + +have_libpng=no +if test x"$with_png" = xyes -o x"$with_png" = xauto; then + libpng_pkg="libpng" + have_libpng_pkg=no + + if test x"$LIBPNG_CFLAGS" = x -a x"$LIBPNG_LIBS" = x; then + PKG_CHECK_EXISTS([$libpng_pkg], [have_libpng_pkg=yes]) + fi + PKG_CHECK_MODULES([LIBPNG], [$libpng_pkg], + [have_libpng="yes (pkg-config)"], [:]) + + if test $have_libpng_pkg = yes; then + # we have libpng.pc + libpng_reqpriv="$libpng_pkg" + libpng_libspriv= + libpng_libsstaticconf=`$PKG_CONFIG --static --libs "$libpng_pkg"` + else + libpng_reqpriv= + + if test "$have_libpng" != no; then + # LIBPNG_CFLAGS and LIBPNG_LIBS are set by the user + libpng_libspriv="$LIBPNG_LIBS" + libpng_libsstaticconf="$LIBPNG_LIBS" + have_libpng="yes (LIBPNG_CFLAGS and LIBPNG_LIBS)" + else + # fall back to config script + AC_CHECK_PROG(have_libpng, [libpng-config], [yes (libpng-config)], [no]) + if test "$have_libpng" != no; then + LIBPNG_CFLAGS=`libpng-config --cflags` + LIBPNG_LIBS=`libpng-config --ldflags` + libpng_libspriv=`libpng-config --static --ldflags` + libpng_libsstaticconf="$libpng_libspriv" + fi + fi + fi +fi + +if test x"$with_png" = xyes -a "$have_libpng" = no; then + AC_MSG_ERROR([libpng support requested but library not found]) +fi + + +# check for system libharfbuzz + +AC_ARG_WITH([harfbuzz], + [AS_HELP_STRING([--with-harfbuzz=@<:@yes|no|auto@:>@], + [improve auto-hinting of OpenType fonts @<:@default=auto@:>@])], + [], [with_harfbuzz=auto]) + +have_harfbuzz=no +if test x"$with_harfbuzz" = xyes -o x"$with_harfbuzz" = xauto; then + harfbuzz_pkg="harfbuzz >= 2.0.0" + have_harfbuzz_pkg=no + + if test x"$HARFBUZZ_CFLAGS" = x -a x"$HARFBUZZ_LIBS" = x; then + PKG_CHECK_EXISTS([$harfbuzz_pkg], [have_harfbuzz_pkg=yes]) + fi + PKG_CHECK_MODULES([HARFBUZZ], [$harfbuzz_pkg], + [have_harfbuzz="yes (pkg-config)"], [:]) + + if test $have_harfbuzz_pkg = yes; then + # we have harfbuzz.pc + harfbuzz_reqpriv="$harfbuzz_pkg" + harfbuzz_libspriv= + harfbuzz_libsstaticconf=`$PKG_CONFIG --static --libs "$harfbuzz_pkg"` + else + harfbuzz_reqpriv= + + if test "$have_harfbuzz" != no; then + # HARFBUZZ_CFLAGS and HARFBUZZ_LIBS are set by the user + harfbuzz_libspriv="$HARFBUZZ_LIBS" + harfbuzz_libsstaticconf="$HARFBUZZ_LIBS" + have_harfbuzz="yes (HARFBUZZ_CFLAGS and HARFBUZZ_LIBS)" + else + # since HarfBuzz is quite a new library we don't fall back to a + # different test; additionally, it has too many dependencies + : + fi + fi +fi + +if test x"$with_harfbuzz" = xyes -a "$have_harfbuzz" = no; then + AC_MSG_ERROR([harfbuzz support requested but library not found]) +fi + + +# check for system libbrotlidec + +AC_ARG_WITH([brotli], + [AS_HELP_STRING([--with-brotli=@<:@yes|no|auto@:>@], + [support decompression of WOFF2 streams @<:@default=auto@:>@])], + [], [with_brotli=auto]) + +have_brotli=no +if test x"$with_brotli" = xyes -o x"$with_brotli" = xauto; then + brotli_pkg="libbrotlidec" + have_brotli_pkg=no + + if test x"$BROTLI_CFLAGS" = x -a x"$BROTLI_LIBS" = x; then + PKG_CHECK_EXISTS([$brotli_pkg], [have_brotli_pkg=yes]) + fi + PKG_CHECK_MODULES([BROTLI], [$brotli_pkg], + [have_brotli="yes (pkg-config)"], [:]) + + if test $have_brotli_pkg = yes; then + # we have libbrotlidec.pc + brotli_reqpriv="$brotli_pkg" + brotli_libspriv= + brotli_libsstaticconf=`$PKG_CONFIG --static --libs "$brotli_pkg"` + else + brotli_reqpriv= + + if test "$have_brotli" != no; then + # BROTLI_CFLAGS and BROTLI_LIBS are set by the user + brotli_libspriv="$BROTLI_LIBS" + brotli_libsstaticconf="$BROTLI_LIBS" + have_brotli="yes (BROTLI_CFLAGS and BROTLI_LIBS)" + else + # since Brotli is quite a new library we don't fall back to a + # different test + : + fi + fi +fi + +if test x"$with_brotli" = xyes -a "$have_brotli" = no; then + AC_MSG_ERROR([brotli support requested but library not found]) +fi + + +# Checks for the demo programs. +# +# FreeType doesn't need this. However, since the demo program repository +# doesn't come with a `configure` script of its own, we integrate the tests +# here for simplicity. + +# We need `clock_gettime` from 'librt' for the `ftbench` demo program. +# +# The code is modeled after gnulib's file `clock_time.m4`, ignoring +# very old Solaris systems. +LIB_CLOCK_GETTIME= +AC_SEARCH_LIBS([clock_gettime], + [rt], + [test "$ac_cv_search_clock_gettime" = "none required" \ + || LIB_CLOCK_GETTIME=$ac_cv_search_clock_gettime]) + +FT_DEMO_CFLAGS="" +FT_DEMO_LDFLAGS="$LIB_CLOCK_GETTIME" + +# 'librsvg' is needed to demonstrate SVG support. +AC_ARG_WITH([librsvg], + [AS_HELP_STRING([--with-librsvg=@<:@yes|no|auto@:>@], + [support OpenType SVG fonts in FreeType demo programs @<:@default=auto@:>@])], + [], [with_librsvg=auto]) + +have_librsvg=no +if test x"$with_librsvg" = xyes -o x"$with_librsvg" = xauto; then + PKG_CHECK_MODULES([LIBRSVG], [librsvg-2.0 >= 2.46.0], + [have_librsvg="yes (pkg-config)"], [:]) + + if test "$have_librsvg" != no; then + FT_DEMO_CFLAGS="$FT_DEMO_CFLAGS $LIBRSVG_CFLAGS -DHAVE_LIBRSVG" + FT_DEMO_LDFLAGS="$FT_DEMO_LDFLAGS $LIBRSVG_LIBS" + fi +fi + +if test x"$with_librsvg" = xyes -a "$have_librsvg" = no; then + AC_MSG_ERROR([librsvg support requested but library not found]) +fi + +AC_SUBST([FT_DEMO_CFLAGS]) +AC_SUBST([FT_DEMO_LDFLAGS]) + + +# Some options handling SDKs/archs in CFLAGS should be copied +# to LDFLAGS. Apple TechNote 2137 recommends to include these +# options in CFLAGS but not in LDFLAGS. + +save_config_args=$* +set dummy ${CFLAGS} +i=1 +while test $i -le $# +do + c=$1 + + case "${c}" in + -isysroot|-arch) # options taking 1 argument + a=$2 + AC_MSG_CHECKING([whether CFLAGS and LDFLAGS share ${c} ${a}]) + if expr " ${LDFLAGS} " : ".* ${c} *${a}.*" > /dev/null + then + AC_MSG_RESULT([yes]) + else + AC_MSG_RESULT([no, copy to LDFLAGS]) + LDFLAGS="${LDFLAGS} ${c} ${a}" + fi + shift 1 + ;; + -m32|-m64|-march=*|-mcpu=*) # options taking no argument + AC_MSG_CHECKING([whether CFLAGS and LDFLAGS share ${c}]) + if expr " ${LDFLAGS} " : ".* ${c} *${a}.*" > /dev/null + then + AC_MSG_RESULT([yes]) + else + AC_MSG_RESULT([no, copy to LDFLAGS]) + LDFLAGS="${LDFLAGS} ${c}" + fi + ;; + # *) + # AC_MSG_RESULT([${c} is not copied to LDFLAGS]) + # ;; + esac + + shift 1 +done +set ${save_config_args} + + +# Whether to use Mac OS resource-based fonts. + +ftmac_c="" # src/base/ftmac.c should not be included in makefiles by default + +AC_ARG_WITH([old-mac-fonts], + AS_HELP_STRING([--with-old-mac-fonts], + [allow Mac resource-based fonts to be used])) +if test x$with_old_mac_fonts = xyes; then + orig_LDFLAGS="${LDFLAGS}" + AC_MSG_CHECKING([CoreServices & ApplicationServices of Mac OS X]) + ft2_extra_libs="-Wl,-framework,CoreServices -Wl,-framework,ApplicationServices" + LDFLAGS="$LDFLAGS $ft2_extra_libs" + AC_LINK_IFELSE([ + AC_LANG_PROGRAM([ + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + ], + [ + + short res = 0; + + + UseResFile( res ); + + ])], + [AC_MSG_RESULT([ok]) + ftmac_c='ftmac.c' + AC_MSG_CHECKING([whether OS_INLINE macro is ANSI compatible]) + orig_CFLAGS="$CFLAGS -DFT_MACINTOSH" + CFLAGS="$CFLAGS $XX_CFLAGS $XX_ANSIFLAGS" + AC_COMPILE_IFELSE([ + AC_LANG_PROGRAM([ + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + ], + [ + + /* OSHostByteOrder() is typed as OS_INLINE */ + int32_t os_byte_order = OSHostByteOrder(); + + + if ( OSBigEndian != os_byte_order ) + return 1; + + ])], + [AC_MSG_RESULT([ok]) + CFLAGS="$orig_CFLAGS" + CFLAGS="$CFLAGS -DHAVE_ANSI_OS_INLINE=1" + ], + [AC_MSG_RESULT([no, ANSI incompatible]) + CFLAGS="$orig_CFLAGS" + ]) + AC_MSG_CHECKING([type ResourceIndex]) + orig_CFLAGS="$CFLAGS" + CFLAGS="$CFLAGS $XX_CFLAGS $XX_ANSIFLAGS" + AC_COMPILE_IFELSE([ + AC_LANG_PROGRAM([ + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +# include +#endif + + ], + [ + + ResourceIndex i = 0; + return i; + + ])], + [AC_MSG_RESULT([ok]) + CFLAGS="$orig_CFLAGS" + CFLAGS="$CFLAGS -DHAVE_TYPE_RESOURCE_INDEX=1" + ], + [AC_MSG_RESULT([no]) + CFLAGS="$orig_CFLAGS" + CFLAGS="$CFLAGS -DHAVE_TYPE_RESOURCE_INDEX=0" + ])], + [AC_MSG_RESULT([not found]) + ft2_extra_libs="" + LDFLAGS="${orig_LDFLAGS}" + CFLAGS="$CFLAGS -DDARWIN_NO_CARBON"]) +else + case x$host_os in + xdarwin*) + dnl AC_MSG_WARN([host system is MacOS but configured to build without Carbon]) + CFLAGS="$CFLAGS -DDARWIN_NO_CARBON" + ;; + *) + ;; + esac +fi + + +# Whether to use FileManager, which is deprecated since Mac OS X 10.4. + +AC_ARG_WITH([fsspec], + AS_HELP_STRING([--with-fsspec], + [use obsolete FSSpec API of MacOS, if available (default=yes)])) +if test x$with_fsspec = xno; then + CFLAGS="$CFLAGS -DHAVE_FSSPEC=0" +elif test x$with_old_mac_fonts = xyes -a x$with_fsspec != x; then + AC_MSG_CHECKING([FSSpec-based FileManager]) + AC_LINK_IFELSE([ + AC_LANG_PROGRAM([ + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + ], + [ + + FCBPBPtr paramBlock; + short vRefNum; + long dirID; + ConstStr255Param fileName; + FSSpec* spec; + + + /* FSSpec functions: deprecated since Mac OS X 10.4 */ + PBGetFCBInfoSync( paramBlock ); + FSMakeFSSpec( vRefNum, dirID, fileName, spec ); + + ])], + [AC_MSG_RESULT([ok]) + CFLAGS="$CFLAGS -DHAVE_FSSPEC=1"], + [AC_MSG_RESULT([not found]) + CFLAGS="$CFLAGS -DHAVE_FSSPEC=0"]) +fi + + +# Whether to use FileManager in Carbon since MacOS 9.x. + +AC_ARG_WITH([fsref], + AS_HELP_STRING([--with-fsref], + [use Carbon FSRef API of MacOS, if available (default=yes)])) +if test x$with_fsref = xno; then + AC_MSG_WARN([ +*** WARNING + FreeType2 built without FSRef API cannot load + data-fork fonts on MacOS, except of XXX.dfont. + ]) + CFLAGS="$CFLAGS -DHAVE_FSREF=0" +elif test x$with_old_mac_fonts = xyes -a x$with_fsref != x; then + AC_MSG_CHECKING([FSRef-based FileManager]) + AC_LINK_IFELSE([ + AC_LANG_PROGRAM([ + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + ], + [ + + short vRefNum; + long dirID; + ConstStr255Param fileName; + + Boolean* isDirectory; + UInt8* path; + SInt16 desiredRefNum; + SInt16* iterator; + SInt16* actualRefNum; + HFSUniStr255* outForkName; + FSVolumeRefNum volume; + FSCatalogInfoBitmap whichInfo; + FSCatalogInfo* catalogInfo; + FSForkInfo* forkInfo; + FSRef* ref; + +#if HAVE_FSSPEC + FSSpec* spec; +#endif + + /* FSRef functions: no need to check? */ + FSGetForkCBInfo( desiredRefNum, volume, iterator, + actualRefNum, forkInfo, ref, + outForkName ); + FSPathMakeRef( path, ref, isDirectory ); + +#if HAVE_FSSPEC + FSpMakeFSRef ( spec, ref ); + FSGetCatalogInfo( ref, whichInfo, catalogInfo, + outForkName, spec, ref ); +#endif + ])], + [AC_MSG_RESULT([ok]) + CFLAGS="$CFLAGS -DHAVE_FSREF=1"], + [AC_MSG_RESULT([not found]) + CFLAGS="$CFLAGS -DHAVE_FSREF=0"]) +fi + + +# Whether to use QuickDraw API in ToolBox, which is deprecated since +# Mac OS X 10.4. + +AC_ARG_WITH([quickdraw-toolbox], + AS_HELP_STRING([--with-quickdraw-toolbox], + [use MacOS QuickDraw in ToolBox, if available (default=yes)])) +if test x$with_quickdraw_toolbox = xno; then + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_TOOLBOX=0" +elif test x$with_old_mac_fonts = xyes -a x$with_quickdraw_toolbox != x; then + AC_MSG_CHECKING([QuickDraw FontManager functions in ToolBox]) + AC_LINK_IFELSE([ + AC_LANG_PROGRAM([ + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + ], + [ + + Str255 familyName; + SInt16 familyID = 0; + FMInput* fmIn = NULL; + FMOutput* fmOut = NULL; + + + GetFontName( familyID, familyName ); + GetFNum( familyName, &familyID ); + fmOut = FMSwapFont( fmIn ); + + ])], + [AC_MSG_RESULT([ok]) + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_TOOLBOX=1"], + [AC_MSG_RESULT([not found]) + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_TOOLBOX=0"]) +fi + + +# Whether to use QuickDraw API in Carbon, which is deprecated since +# Mac OS X 10.4. + +AC_ARG_WITH([quickdraw-carbon], + AS_HELP_STRING([--with-quickdraw-carbon], + [use MacOS QuickDraw in Carbon, if available (default=yes)])) +if test x$with_quickdraw_carbon = xno; then + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_CARBON=0" +elif test x$with_old_mac_fonts = xyes -a x$with_quickdraw_carbon != x; then + AC_MSG_CHECKING([QuickDraw FontManager functions in Carbon]) + AC_LINK_IFELSE([ + AC_LANG_PROGRAM([ + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + ], + [ + + FMFontFamilyIterator famIter; + FMFontFamily family; + Str255 famNameStr; + FMFontFamilyInstanceIterator instIter; + FMFontStyle style; + FMFontSize size; + FMFont font; + FSSpec* pathSpec; + + + FMCreateFontFamilyIterator( NULL, NULL, kFMUseGlobalScopeOption, + &famIter ); + FMGetNextFontFamily( &famIter, &family ); + FMGetFontFamilyName( family, famNameStr ); + FMCreateFontFamilyInstanceIterator( family, &instIter ); + FMGetNextFontFamilyInstance( &instIter, &font, &style, &size ); + FMDisposeFontFamilyInstanceIterator( &instIter ); + FMDisposeFontFamilyIterator( &famIter ); + FMGetFontContainer( font, pathSpec ); + + ])], + [AC_MSG_RESULT([ok]) + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_CARBON=1"], + [AC_MSG_RESULT([not found]) + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_CARBON=0"]) +fi + + +# Whether to use AppleTypeService since Mac OS X. + +AC_ARG_WITH([ats], + AS_HELP_STRING([--with-ats], + [use AppleTypeService, if available (default=yes)])) +if test x$with_ats = xno; then + CFLAGS="$CFLAGS -DHAVE_ATS=0" +elif test x$with_old_mac_fonts = xyes -a x$with_ats != x; then + AC_MSG_CHECKING([AppleTypeService functions]) + AC_LINK_IFELSE([ + AC_LANG_PROGRAM([ + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + ], + [ + + FSSpec* pathSpec; + + + ATSFontFindFromName( NULL, kATSOptionFlagsUnRestrictedScope ); +#if HAVE_FSSPEC + ATSFontGetFileSpecification( 0, pathSpec ); +#endif + + ])], + [AC_MSG_RESULT([ok]) + CFLAGS="$CFLAGS -DHAVE_ATS=1"], + [AC_MSG_RESULT([not found]) + CFLAGS="$CFLAGS -DHAVE_ATS=0"]) +fi + +case "$CFLAGS" in + *HAVE_FSSPEC* | *HAVE_FSREF* | *HAVE_QUICKDRAW* | *HAVE_ATS* ) + AC_MSG_WARN([ +*** WARNING + FSSpec/FSRef/QuickDraw/ATS options are explicitly given, + thus it is recommended to replace src/base/ftmac.c by builds/mac/ftmac.c. + ]) + CFLAGS="$CFLAGS "'-I$(TOP_DIR)/builds/mac/' + ;; + *) + ;; +esac + +# Check for pthreads + +AX_PTHREAD([have_pthread=yes], [have_pthread=no]) + +# Check for Python and docwriter +PYTHON_MIN_VERSION=3.5 +have_py3=no +have_docwriter=no +PIP=pip + +AC_CHECK_PROGS([PYTHON], [python3 python], [missing]) +if test "x$PYTHON" != "xmissing"; then + AX_PROG_PYTHON_VERSION([$PYTHON_MIN_VERSION], [have_py3=yes], []) + + if test "x$have_py3" = "xyes"; then + PIP="$PYTHON -m $PIP" + AC_MSG_CHECKING([for `docwriter' Python module]) + $PYTHON -m docwriter -h > /dev/null 2>&1 + if test "x$?" = "x0"; then + have_docwriter=yes + AC_MSG_RESULT([yes]) + else + AC_MSG_RESULT([no]) + fi + fi +fi + + +# entries in Requires.private are separated by commas +PKGCONFIG_REQUIRES_PRIVATE="$zlib_reqpriv, \ + $bzip2_reqpriv, \ + $libpng_reqpriv, \ + $harfbuzz_reqpriv, \ + $brotli_reqpriv" +# beautify +PKGCONFIG_REQUIRES_PRIVATE=`echo "$PKGCONFIG_REQUIRES_PRIVATE" \ + | sed -e 's/^ *//' \ + -e 's/ *$//' \ + -e 's/, */,/g' \ + -e 's/,,*/,/g' \ + -e 's/^,*//' \ + -e 's/,*$//' \ + -e 's/,/, /g'` + +PKGCONFIG_LIBS_PRIVATE="$zlib_libspriv \ + $bzip2_libspriv \ + $libpng_libspriv \ + $harfbuzz_libspriv \ + $brotli_libspriv \ + $ft2_extra_libs" +# beautify +PKGCONFIG_LIBS_PRIVATE=`echo "$PKGCONFIG_LIBS_PRIVATE" \ + | sed -e 's/^ *//' \ + -e 's/ *$//' \ + -e 's/ */ /g'` + +LIBSSTATIC_CONFIG="-lfreetype \ + $zlib_libsstaticconf \ + $bzip2_libsstaticconf \ + $libpng_libsstaticconf \ + $harfbuzz_libsstaticconf \ + $brotli_libsstaticconf \ + $ft2_extra_libs" +# remove -L/usr/lib and -L/usr/lib64 since `freetype-config' adds them later +# on if necessary; also beautify +LIBSSTATIC_CONFIG=`echo "$LIBSSTATIC_CONFIG" \ + | sed -e 's|-L */usr/lib64/* | |g' \ + -e 's|-L */usr/lib/* | |g' \ + -e 's/^ *//' \ + -e 's/ *$//' \ + -e 's/ */ /g'` + +# If FreeType gets installed with `--disable-shared', don't use +# 'private' fields. `pkg-config' only looks into `.pc' files and is +# completely agnostic to whether shared libraries are actually present +# or not. As a consequence, the user had to specify `--static' while +# calling `pkg-config', which configure scripts are normally not +# prepared for. + +PKGCONFIG_REQUIRES= +PKGCONFIG_LIBS='-L${libdir} -lfreetype' + +if test $enable_shared = "no"; then + PKGCONFIG_REQUIRES="$PKGCONFIG_REQUIRES $PKGCONFIG_REQUIRES_PRIVATE" + PKGCONFIG_REQUIRES_PRIVATE= + PKGCONFIG_LIBS="$PKGCONFIG_LIBS $PKGCONFIG_LIBS_PRIVATE" + PKGCONFIG_LIBS_PRIVATE= +fi + +AC_SUBST([ftmac_c]) +AC_SUBST([PKGCONFIG_REQUIRES]) +AC_SUBST([PKGCONFIG_LIBS]) +AC_SUBST([PKGCONFIG_REQUIRES_PRIVATE]) +AC_SUBST([PKGCONFIG_LIBS_PRIVATE]) +AC_SUBST([LIBSSTATIC_CONFIG]) + +AC_SUBST([hardcode_libdir_flag_spec]) +AC_SUBST([wl]) +AC_SUBST([build_libtool_libs]) + + +# changing LDFLAGS value should only be done after +# lt_cv_prog_compiler_static_works test + +ftoption_set() +{ + regexp="-e \\\"s|.*#.*def.*$1.*|#define $1|\\\"" + FTOPTION_H_SED="$FTOPTION_H_SED $regexp" +} + +ftoption_unset() +{ + regexp="-e \\\"s|.*#.*def.*$1.*|/* #undef $1 */|\\\"" + FTOPTION_H_SED="$FTOPTION_H_SED $regexp" +} + +if test "$have_zlib" != no; then + CFLAGS="$CFLAGS $ZLIB_CFLAGS" + LDFLAGS="$LDFLAGS $ZLIB_LIBS" + ftoption_set FT_CONFIG_OPTION_SYSTEM_ZLIB +else + ftoption_unset FT_CONFIG_OPTION_SYSTEM_ZLIB +fi +if test "$have_bzip2" != no; then + CFLAGS="$CFLAGS $BZIP2_CFLAGS" + LDFLAGS="$LDFLAGS $BZIP2_LIBS" + ftoption_set FT_CONFIG_OPTION_USE_BZIP2 +else + ftoption_unset FT_CONFIG_OPTION_USE_BZIP2 +fi +if test "$have_libpng" != no; then + CFLAGS="$CFLAGS $LIBPNG_CFLAGS" + LDFLAGS="$LDFLAGS $LIBPNG_LIBS" + ftoption_set FT_CONFIG_OPTION_USE_PNG +else + ftoption_unset FT_CONFIG_OPTION_USE_PNG +fi +if test "$have_harfbuzz" != no; then + CFLAGS="$CFLAGS $HARFBUZZ_CFLAGS" + LDFLAGS="$LDFLAGS $HARFBUZZ_LIBS" + ftoption_set FT_CONFIG_OPTION_USE_HARFBUZZ +else + ftoption_unset FT_CONFIG_OPTION_USE_HARFBUZZ +fi +if test "$have_brotli" != no; then + CFLAGS="$CFLAGS $BROTLI_CFLAGS" + LDFLAGS="$LDFLAGS $BROTLI_LIBS" + ftoption_set FT_CONFIG_OPTION_USE_BROTLI +else + ftoption_unset FT_CONFIG_OPTION_USE_BROTLI +fi + +if test "$have_pthread" != no; then + CFLAGS="$CFLAGS $PTHREAD_CFLAGS" + LDFLAGS="$LDFLAGS $PTHREAD_CFLAGS $PTHREAD_LIBS" +fi + +AC_SUBST([CFLAGS]) +AC_SUBST([LDFLAGS]) + +# We don't want to use a template file for `ftoption.h', since compilation +# should work without calling a configure script also. For this reason, we +# copy the `include/freetype/config/ftoption.h' file to the `unix/builds' +# directory (using a dummy `AC_CONFIG_FILES' call) and apply the just +# constructed $FTOPTION_H_SED regexp (using the post-action of +# `AC_CONFIG_FILES'); this is also the version that gets installed later on. +# +AC_CONFIG_FILES([ftoption.h:${srcdir}/../../include/freetype/config/ftoption.h], + [mv ftoption.h ftoption.tmp + eval "sed $FTOPTION_H_SED < ftoption.tmp > ftoption.h" + rm ftoption.tmp], + [FTOPTION_H_SED="$FTOPTION_H_SED"]) + +AC_CONFIG_HEADERS([ftconfig.h]) + +# create the Unix-specific sub-Makefiles `builds/unix/unix-def.mk' +# and `builds/unix/unix-cc.mk' that will be used by the build system +# +AC_CONFIG_FILES([unix-cc.mk:unix-cc.in + unix-def.mk:unix-def.in]) + +AC_OUTPUT + +AC_MSG_NOTICE([ + +Library configuration: + external zlib: $have_zlib + bzip2: $have_bzip2 + libpng: $have_libpng + harfbuzz: $have_harfbuzz + brotli: $have_brotli + pthread: $have_pthread +]) + +# Warn if docwriter is not installed + +if test $have_docwriter = no; then + AC_MSG_WARN([ + `make refdoc' will fail since pip package `docwriter' is not installed. + To install, run `$PIP install docwriter', or to use a Python + virtual environment, run `make refdoc-venv' (requires pip package + `virtualenv'). These operations require Python >= $PYTHON_MIN_VERSION. + ]) +fi + +# Warn if pthread is not available + +if test $have_pthread = no; then + AC_MSG_WARN([ + `FT_DEBUG_LOGGING' will not work since the `pthread' library is not + available. This warning can be safely ignored if you don't plan to use + this configuration macro. + ]) +fi + +# end of configure.raw diff --git a/3rdparty/freetype-2.13.2/builds/unix/configure.raw b/3rdparty/freetype-2.13.2/builds/unix/configure.raw new file mode 100644 index 000000000..dc7426ee0 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/configure.raw @@ -0,0 +1,1179 @@ +# This file is part of the FreeType project. +# +# Process this file with autoconf to produce a configure script. +# +# Copyright (C) 2001-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + +AC_INIT([FreeType], [@VERSION@], [freetype@nongnu.org], [freetype]) +AC_CONFIG_SRCDIR([ftconfig.h.in]) + + +# Don't forget to update `docs/VERSIONS.TXT'! + +version_info='26:1:20' +AC_SUBST([version_info]) +ft_version=`echo $version_info | tr : .` +AC_SUBST([ft_version]) + + +# checks for system type + +AC_CANONICAL_HOST + + +# checks for programs + +AC_PROG_CC +AC_PROG_CPP +AC_SUBST(EXEEXT) + +PKG_PROG_PKG_CONFIG([0.24]) + +LT_INIT(win32-dll) +AC_CHECK_HEADER([windows.h], [LT_PROG_RC]) + + +# checks for native programs to generate building tool + +if test ${cross_compiling} = yes; then + AC_CHECK_PROG(CC_BUILD, ${build}-gcc, ${build}-gcc) + test -z "${CC_BUILD}" && AC_CHECK_PROG(CC_BUILD, gcc, gcc) + test -z "${CC_BUILD}" && AC_CHECK_PROG(CC_BUILD, cc, cc, , , /usr/ucb/cc) + test -z "${CC_BUILD}" && AC_MSG_ERROR([cannot find native C compiler]) + + AC_MSG_CHECKING([for suffix of native executables]) + rm -f a.* b.* a_out.exe conftest.* + echo > conftest.c "int main(void) { return 0;}" + ${CC_BUILD} conftest.c || AC_MSG_ERROR([native C compiler is not working]) + rm -f conftest.c + if test -x a.out -o -x b.out -o -x conftest; then + EXEEXT_BUILD="" + elif test -x a_out.exe -o -x conftest.exe; then + EXEEXT_BUILD=".exe" + elif test -x conftest.*; then + EXEEXT_BUILD=`echo conftest.* | sed -n '1s/^.*\././'` + fi + rm -f a.* b.* a_out.exe conftest.* + AC_MSG_RESULT($EXEEXT_BUILD) +else + CC_BUILD=${CC} + EXEEXT_BUILD=${EXEEXT} +fi + +AC_SUBST(CC_BUILD) +AC_SUBST(EXEEXT_BUILD) + + +# Since these files will be eventually called from another directory (namely +# from the top level) we make the path of the scripts absolute. +# +# This small code snippet has been taken from automake's `ylwrap' script. + +AC_PROG_INSTALL +case "$INSTALL" in +[[\\/]]* | ?:[[\\/]]*) + ;; +*[[\\/]]*) + INSTALL="`pwd`/$INSTALL" + ;; +esac + +AC_PROG_MKDIR_P +case "$MKDIR_P" in +[[\\/]]* | ?:[[\\/]]*) + ;; +*[[\\/]]*) + MKDIR_P="`pwd`/$MKDIR_P" + ;; +esac + + +# checks for header files + +AC_CHECK_HEADERS([fcntl.h unistd.h]) + + +# checks for typedefs, structures, and compiler characteristics + +AC_C_CONST + +AC_ARG_ENABLE([freetype-config], + AS_HELP_STRING([--enable-freetype-config], [install freetype-config]), + [case "${enableval}" in + yes) enable_freetype_config="TRUE" ;; + no) enable_freetype_config="FALSE" ;; + *) AC_MSG_ERROR([unknown value '${enableval}' passed with --enable-freetype-config]) ;; + esac], [enable_freetype_config="FALSE"]) + +AC_SUBST(INSTALL_FT2_CONFIG, [$enable_freetype_config]) + +# checks for library functions + +AC_SYS_LARGEFILE + +# Here we check whether we can use our mmap file component. +# +# Note that `ftsystem.c` for Windows has its own mmap-like implementation +# not covered by `AC_FUNC_MMAP` and/or `FT_UNMAP_PARAM`. + +AC_ARG_ENABLE([mmap], + AS_HELP_STRING([--disable-mmap], + [do not check mmap() and do not use]), + [enable_mmap="no"], [enable_mmap="yes"]) +if test "x${enable_mmap}" != "xno"; then + case "$host" in + *-*-mingw*) + AC_MSG_CHECKING([for working mmap]) + AC_MSG_RESULT([using MapViewOfFile in Windows]) + FTSYS_SRC='$(TOP_DIR)/builds/windows/ftsystem.c' + ;; + *) + AC_FUNC_MMAP + if test "$ac_cv_func_mmap_fixed_mapped" = "yes"; then + FTSYS_SRC='$(PLATFORM_DIR)/ftsystem.c' + + AC_CHECK_DECLS([munmap], + [], + [], + [ + +#ifdef HAVE_UNISTD_H +#include +#endif +#include + + ]) + + FT_MUNMAP_PARAM + fi + ;; + esac +fi + +if test -z "$FTSYS_SRC"; then + FTSYS_SRC='$(BASE_DIR)/ftsystem.c' +fi +AC_SUBST([FTSYS_SRC]) + + +# get compiler flags right +# +# We try to make the compiler work for C99-strict source. Even if the +# C compiler is gcc and C99 flags are available, some system headers +# might be broken in C99 mode. We have to check whether compilation +# finishes successfully. +# +if test "x$GCC" = xyes; then + XX_CFLAGS="-Wall" + case "$host" in + *-*-mingw*) + XX_ANSIFLAGS="-pedantic" + ;; + *-*-aix*) + XX_ANSIFLAGS="-pedantic" + ;; + *) + XX_ANSIFLAGS="" + + for a in "-pedantic" "-std=c99" + do + AC_MSG_CHECKING([$CC compiler flag ${a} to assure ANSI C99 works correctly]) + orig_CFLAGS="${CFLAGS}" + CFLAGS="${CFLAGS} ${XX_ANSIFLAGS} ${a}" + AC_COMPILE_IFELSE([ + AC_LANG_PROGRAM([ + +#include + + ], + [ + + { + puts( "" ); + return 0; + } + + ])], + [AC_MSG_RESULT([ok, adding to XX_ANSIFLAGS]) + XX_ANSIFLAGS="${XX_ANSIFLAGS} ${a}" + ], + [AC_MSG_RESULT([no])]) + CFLAGS="${orig_CFLAGS}" + done + ;; + esac +else + case "$host" in + *-dec-osf*) + CFLAGS= + XX_CFLAGS="-std1 -g3" + XX_ANSIFLAGS= + ;; + *) + XX_CFLAGS= + XX_ANSIFLAGS= + ;; + esac +fi +AC_SUBST([XX_CFLAGS]) +AC_SUBST([XX_ANSIFLAGS]) + + +# It is recommended that shared libraries hide symbols except those with +# explicit __attribute__((visibility("default"))). +# +found_visibility_flag=no +AC_MSG_CHECKING([for -fvisibility=hidden compiler flag]) +orig_CFLAGS="${CFLAGS}" +CFLAGS="${CFLAGS} -fvisibility=hidden" +AC_LINK_IFELSE([AC_LANG_PROGRAM([], [])], + [found_visibility_flag=yes + AC_MSG_RESULT(yes)], + [CFLAGS="${orig_CFLAGS}" + AC_MSG_RESULT(no)]) + +if test "${found_visibility_flag}" = "no"; then + AC_MSG_CHECKING([for -xldscope=hidden compiler flag]) + orig_CFLAGS="${CFLAGS}" + CFLAGS="${CFLAGS} -xldscope=hidden" + AC_LINK_IFELSE([AC_LANG_PROGRAM([], [])], + [found_visibility_flag=yes + AC_MSG_RESULT(yes)], + [CFLAGS="${orig_CFLAGS}" + AC_MSG_RESULT(no)]) +fi + +# All library tests below try `pkg-config' first. If that fails, a function +# from the library is tested in the traditional autoconf way (zlib, bzip2), +# or a config script is called (libpng). +# +# The `xxx_reqpriv' variables are for the `Requires.private' field in +# `freetype2.pc'. The `xxx_libspriv' variables are for the `Libs.private' +# field in `freetype2.pc' if pkg-config doesn't find a proper .pc file. +# +# The `xxx_libsstaticconf' variables are for the `freetype-config' script. +# +# Note that a call to PKG_CHECK_MODULES(XXX, ...) sets and creates the +# output variables `XXX_CFLAGS' and `XXX_LIBS'. In case one or both are set +# for a library by the user, no entry for this library is added to +# `Requires.private'. Instead, it gets added to `Libs.private' + + +# check for system zlib + +AC_ARG_WITH([zlib], + [AS_HELP_STRING([--with-zlib=@<:@yes|no|auto@:>@], + [use system zlib instead of internal library @<:@default=auto@:>@])], + [], [with_zlib=auto]) + +have_zlib=no +if test x"$with_zlib" = xyes -o x"$with_zlib" = xauto; then + zlib_pkg="zlib" + have_zlib_pkg=no + + if test x"$ZLIB_CFLAGS" = x -a x"$ZLIB_LIBS" = x; then + PKG_CHECK_EXISTS([$zlib_pkg], [have_zlib_pkg=yes]) + fi + PKG_CHECK_MODULES([ZLIB], [$zlib_pkg], + [have_zlib="yes (pkg-config)"], [:]) + + if test $have_zlib_pkg = yes; then + # we have zlib.pc + zlib_reqpriv="$zlib_pkg" + zlib_libspriv= + zlib_libsstaticconf=`$PKG_CONFIG --static --libs "$zlib_pkg"` + else + zlib_reqpriv= + + if test "$have_zlib" != no; then + # ZLIB_CFLAGS and ZLIB_LIBS are set by the user + zlib_libspriv="$ZLIB_LIBS" + zlib_libsstaticconf="$ZLIB_LIBS" + have_zlib="yes (ZLIB_CFLAGS and ZLIB_LIBS)" + else + # fall back to standard autoconf test + AC_CHECK_LIB([z], + [gzsetparams], + [AC_CHECK_HEADER([zlib.h], + [have_zlib="yes (autoconf test)" + zlib_libspriv="-lz" + zlib_libsstaticconf="$zlib_libspriv" + ZLIB_LIBS="$zlib_libspriv"])]) + fi + fi +fi + +if test x"$with_zlib" = xyes -a "$have_zlib" = no; then + AC_MSG_ERROR([external zlib support requested but library not found]) +fi + +SYSTEM_ZLIB= +if test "$have_zlib" != no; then + SYSTEM_ZLIB=yes +fi +AC_SUBST([SYSTEM_ZLIB]) + + +# check for system libbz2 + +AC_ARG_WITH([bzip2], + [AS_HELP_STRING([--with-bzip2=@<:@yes|no|auto@:>@], + [support bzip2 compressed fonts @<:@default=auto@:>@])], + [], [with_bzip2=auto]) + +have_bzip2=no +if test x"$with_bzip2" = xyes -o x"$with_bzip2" = xauto; then + bzip2_pkg="bzip2" + have_bzip2_pkg=no + + if test x"$BZIP2_CFLAGS" = x -a x"$BZIP2_LIBS" = x; then + PKG_CHECK_EXISTS([$bzip2_pkg], [have_bzip2_pkg=yes]) + fi + PKG_CHECK_MODULES([BZIP2], [$bzip2_pkg], + [have_bzip2="yes (pkg-config)"], [:]) + + if test $have_bzip2_pkg = yes; then + # we have bzip2.pc + bzip2_reqpriv="$bzip2_pkg" + bzip2_libspriv= + bzip2_libsstaticconf=`$PKG_CONFIG --static --libs "$bzip2_pkg"` + else + bzip2_reqpriv= + + if test "$have_bzip2" != no; then + # BZIP2_CFLAGS and BZIP2_LIBS are set by the user + bzip2_libspriv="$BZIP2_LIBS" + bzip2_libsstaticconf="$BZIP2_LIBS" + have_bzip2="yes (BZIP2_CFLAGS and BZIP2_LIBS)" + else + # fall back to standard autoconf test + AC_CHECK_LIB([bz2], + [BZ2_bzDecompress], + [AC_CHECK_HEADER([bzlib.h], + [have_bzip2="yes (autoconf test)" + bzip2_libspriv="-lbz2" + bzip2_libsstaticconf="$bzip2_libspriv" + BZIP2_LIBS="$bzip2_libspriv"])]) + fi + fi +fi + +if test x"$with_bzip2" = xyes -a "$have_bzip2" = no; then + AC_MSG_ERROR([bzip2 support requested but library not found]) +fi + + +# check for system libpng + +AC_ARG_WITH([png], + [AS_HELP_STRING([--with-png=@<:@yes|no|auto@:>@], + [support png compressed OpenType embedded bitmaps @<:@default=auto@:>@])], + [], [with_png=auto]) + +have_libpng=no +if test x"$with_png" = xyes -o x"$with_png" = xauto; then + libpng_pkg="libpng" + have_libpng_pkg=no + + if test x"$LIBPNG_CFLAGS" = x -a x"$LIBPNG_LIBS" = x; then + PKG_CHECK_EXISTS([$libpng_pkg], [have_libpng_pkg=yes]) + fi + PKG_CHECK_MODULES([LIBPNG], [$libpng_pkg], + [have_libpng="yes (pkg-config)"], [:]) + + if test $have_libpng_pkg = yes; then + # we have libpng.pc + libpng_reqpriv="$libpng_pkg" + libpng_libspriv= + libpng_libsstaticconf=`$PKG_CONFIG --static --libs "$libpng_pkg"` + else + libpng_reqpriv= + + if test "$have_libpng" != no; then + # LIBPNG_CFLAGS and LIBPNG_LIBS are set by the user + libpng_libspriv="$LIBPNG_LIBS" + libpng_libsstaticconf="$LIBPNG_LIBS" + have_libpng="yes (LIBPNG_CFLAGS and LIBPNG_LIBS)" + else + # fall back to config script + AC_CHECK_PROG(have_libpng, [libpng-config], [yes (libpng-config)], [no]) + if test "$have_libpng" != no; then + LIBPNG_CFLAGS=`libpng-config --cflags` + LIBPNG_LIBS=`libpng-config --ldflags` + libpng_libspriv=`libpng-config --static --ldflags` + libpng_libsstaticconf="$libpng_libspriv" + fi + fi + fi +fi + +if test x"$with_png" = xyes -a "$have_libpng" = no; then + AC_MSG_ERROR([libpng support requested but library not found]) +fi + + +# check for system libharfbuzz + +AC_ARG_WITH([harfbuzz], + [AS_HELP_STRING([--with-harfbuzz=@<:@yes|no|auto@:>@], + [improve auto-hinting of OpenType fonts @<:@default=auto@:>@])], + [], [with_harfbuzz=auto]) + +have_harfbuzz=no +if test x"$with_harfbuzz" = xyes -o x"$with_harfbuzz" = xauto; then + harfbuzz_pkg="harfbuzz >= 2.0.0" + have_harfbuzz_pkg=no + + if test x"$HARFBUZZ_CFLAGS" = x -a x"$HARFBUZZ_LIBS" = x; then + PKG_CHECK_EXISTS([$harfbuzz_pkg], [have_harfbuzz_pkg=yes]) + fi + PKG_CHECK_MODULES([HARFBUZZ], [$harfbuzz_pkg], + [have_harfbuzz="yes (pkg-config)"], [:]) + + if test $have_harfbuzz_pkg = yes; then + # we have harfbuzz.pc + harfbuzz_reqpriv="$harfbuzz_pkg" + harfbuzz_libspriv= + harfbuzz_libsstaticconf=`$PKG_CONFIG --static --libs "$harfbuzz_pkg"` + else + harfbuzz_reqpriv= + + if test "$have_harfbuzz" != no; then + # HARFBUZZ_CFLAGS and HARFBUZZ_LIBS are set by the user + harfbuzz_libspriv="$HARFBUZZ_LIBS" + harfbuzz_libsstaticconf="$HARFBUZZ_LIBS" + have_harfbuzz="yes (HARFBUZZ_CFLAGS and HARFBUZZ_LIBS)" + else + # since HarfBuzz is quite a new library we don't fall back to a + # different test; additionally, it has too many dependencies + : + fi + fi +fi + +if test x"$with_harfbuzz" = xyes -a "$have_harfbuzz" = no; then + AC_MSG_ERROR([harfbuzz support requested but library not found]) +fi + + +# check for system libbrotlidec + +AC_ARG_WITH([brotli], + [AS_HELP_STRING([--with-brotli=@<:@yes|no|auto@:>@], + [support decompression of WOFF2 streams @<:@default=auto@:>@])], + [], [with_brotli=auto]) + +have_brotli=no +if test x"$with_brotli" = xyes -o x"$with_brotli" = xauto; then + brotli_pkg="libbrotlidec" + have_brotli_pkg=no + + if test x"$BROTLI_CFLAGS" = x -a x"$BROTLI_LIBS" = x; then + PKG_CHECK_EXISTS([$brotli_pkg], [have_brotli_pkg=yes]) + fi + PKG_CHECK_MODULES([BROTLI], [$brotli_pkg], + [have_brotli="yes (pkg-config)"], [:]) + + if test $have_brotli_pkg = yes; then + # we have libbrotlidec.pc + brotli_reqpriv="$brotli_pkg" + brotli_libspriv= + brotli_libsstaticconf=`$PKG_CONFIG --static --libs "$brotli_pkg"` + else + brotli_reqpriv= + + if test "$have_brotli" != no; then + # BROTLI_CFLAGS and BROTLI_LIBS are set by the user + brotli_libspriv="$BROTLI_LIBS" + brotli_libsstaticconf="$BROTLI_LIBS" + have_brotli="yes (BROTLI_CFLAGS and BROTLI_LIBS)" + else + # since Brotli is quite a new library we don't fall back to a + # different test + : + fi + fi +fi + +if test x"$with_brotli" = xyes -a "$have_brotli" = no; then + AC_MSG_ERROR([brotli support requested but library not found]) +fi + + +# Checks for the demo programs. +# +# FreeType doesn't need this. However, since the demo program repository +# doesn't come with a `configure` script of its own, we integrate the tests +# here for simplicity. + +# We need `clock_gettime` from 'librt' for the `ftbench` demo program. +# +# The code is modeled after gnulib's file `clock_time.m4`, ignoring +# very old Solaris systems. +LIB_CLOCK_GETTIME= +AC_SEARCH_LIBS([clock_gettime], + [rt], + [test "$ac_cv_search_clock_gettime" = "none required" \ + || LIB_CLOCK_GETTIME=$ac_cv_search_clock_gettime]) + +FT_DEMO_CFLAGS="" +FT_DEMO_LDFLAGS="$LIB_CLOCK_GETTIME" + +# 'librsvg' is needed to demonstrate SVG support. +AC_ARG_WITH([librsvg], + [AS_HELP_STRING([--with-librsvg=@<:@yes|no|auto@:>@], + [support OpenType SVG fonts in FreeType demo programs @<:@default=auto@:>@])], + [], [with_librsvg=auto]) + +have_librsvg=no +if test x"$with_librsvg" = xyes -o x"$with_librsvg" = xauto; then + PKG_CHECK_MODULES([LIBRSVG], [librsvg-2.0 >= 2.46.0], + [have_librsvg="yes (pkg-config)"], [:]) + + if test "$have_librsvg" != no; then + FT_DEMO_CFLAGS="$FT_DEMO_CFLAGS $LIBRSVG_CFLAGS -DHAVE_LIBRSVG" + FT_DEMO_LDFLAGS="$FT_DEMO_LDFLAGS $LIBRSVG_LIBS" + fi +fi + +if test x"$with_librsvg" = xyes -a "$have_librsvg" = no; then + AC_MSG_ERROR([librsvg support requested but library not found]) +fi + +AC_SUBST([FT_DEMO_CFLAGS]) +AC_SUBST([FT_DEMO_LDFLAGS]) + + +# Some options handling SDKs/archs in CFLAGS should be copied +# to LDFLAGS. Apple TechNote 2137 recommends to include these +# options in CFLAGS but not in LDFLAGS. + +save_config_args=$* +set dummy ${CFLAGS} +i=1 +while test $i -le $# +do + c=$1 + + case "${c}" in + -isysroot|-arch) # options taking 1 argument + a=$2 + AC_MSG_CHECKING([whether CFLAGS and LDFLAGS share ${c} ${a}]) + if expr " ${LDFLAGS} " : ".* ${c} *${a}.*" > /dev/null + then + AC_MSG_RESULT([yes]) + else + AC_MSG_RESULT([no, copy to LDFLAGS]) + LDFLAGS="${LDFLAGS} ${c} ${a}" + fi + shift 1 + ;; + -m32|-m64|-march=*|-mcpu=*) # options taking no argument + AC_MSG_CHECKING([whether CFLAGS and LDFLAGS share ${c}]) + if expr " ${LDFLAGS} " : ".* ${c} *${a}.*" > /dev/null + then + AC_MSG_RESULT([yes]) + else + AC_MSG_RESULT([no, copy to LDFLAGS]) + LDFLAGS="${LDFLAGS} ${c}" + fi + ;; + # *) + # AC_MSG_RESULT([${c} is not copied to LDFLAGS]) + # ;; + esac + + shift 1 +done +set ${save_config_args} + + +# Whether to use Mac OS resource-based fonts. + +ftmac_c="" # src/base/ftmac.c should not be included in makefiles by default + +AC_ARG_WITH([old-mac-fonts], + AS_HELP_STRING([--with-old-mac-fonts], + [allow Mac resource-based fonts to be used])) +if test x$with_old_mac_fonts = xyes; then + orig_LDFLAGS="${LDFLAGS}" + AC_MSG_CHECKING([CoreServices & ApplicationServices of Mac OS X]) + ft2_extra_libs="-Wl,-framework,CoreServices -Wl,-framework,ApplicationServices" + LDFLAGS="$LDFLAGS $ft2_extra_libs" + AC_LINK_IFELSE([ + AC_LANG_PROGRAM([ + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + ], + [ + + short res = 0; + + + UseResFile( res ); + + ])], + [AC_MSG_RESULT([ok]) + ftmac_c='ftmac.c' + AC_MSG_CHECKING([whether OS_INLINE macro is ANSI compatible]) + orig_CFLAGS="$CFLAGS -DFT_MACINTOSH" + CFLAGS="$CFLAGS $XX_CFLAGS $XX_ANSIFLAGS" + AC_COMPILE_IFELSE([ + AC_LANG_PROGRAM([ + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + ], + [ + + /* OSHostByteOrder() is typed as OS_INLINE */ + int32_t os_byte_order = OSHostByteOrder(); + + + if ( OSBigEndian != os_byte_order ) + return 1; + + ])], + [AC_MSG_RESULT([ok]) + CFLAGS="$orig_CFLAGS" + CFLAGS="$CFLAGS -DHAVE_ANSI_OS_INLINE=1" + ], + [AC_MSG_RESULT([no, ANSI incompatible]) + CFLAGS="$orig_CFLAGS" + ]) + AC_MSG_CHECKING([type ResourceIndex]) + orig_CFLAGS="$CFLAGS" + CFLAGS="$CFLAGS $XX_CFLAGS $XX_ANSIFLAGS" + AC_COMPILE_IFELSE([ + AC_LANG_PROGRAM([ + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +# include +#endif + + ], + [ + + ResourceIndex i = 0; + return i; + + ])], + [AC_MSG_RESULT([ok]) + CFLAGS="$orig_CFLAGS" + CFLAGS="$CFLAGS -DHAVE_TYPE_RESOURCE_INDEX=1" + ], + [AC_MSG_RESULT([no]) + CFLAGS="$orig_CFLAGS" + CFLAGS="$CFLAGS -DHAVE_TYPE_RESOURCE_INDEX=0" + ])], + [AC_MSG_RESULT([not found]) + ft2_extra_libs="" + LDFLAGS="${orig_LDFLAGS}" + CFLAGS="$CFLAGS -DDARWIN_NO_CARBON"]) +else + case x$host_os in + xdarwin*) + dnl AC_MSG_WARN([host system is MacOS but configured to build without Carbon]) + CFLAGS="$CFLAGS -DDARWIN_NO_CARBON" + ;; + *) + ;; + esac +fi + + +# Whether to use FileManager, which is deprecated since Mac OS X 10.4. + +AC_ARG_WITH([fsspec], + AS_HELP_STRING([--with-fsspec], + [use obsolete FSSpec API of MacOS, if available (default=yes)])) +if test x$with_fsspec = xno; then + CFLAGS="$CFLAGS -DHAVE_FSSPEC=0" +elif test x$with_old_mac_fonts = xyes -a x$with_fsspec != x; then + AC_MSG_CHECKING([FSSpec-based FileManager]) + AC_LINK_IFELSE([ + AC_LANG_PROGRAM([ + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + ], + [ + + FCBPBPtr paramBlock; + short vRefNum; + long dirID; + ConstStr255Param fileName; + FSSpec* spec; + + + /* FSSpec functions: deprecated since Mac OS X 10.4 */ + PBGetFCBInfoSync( paramBlock ); + FSMakeFSSpec( vRefNum, dirID, fileName, spec ); + + ])], + [AC_MSG_RESULT([ok]) + CFLAGS="$CFLAGS -DHAVE_FSSPEC=1"], + [AC_MSG_RESULT([not found]) + CFLAGS="$CFLAGS -DHAVE_FSSPEC=0"]) +fi + + +# Whether to use FileManager in Carbon since MacOS 9.x. + +AC_ARG_WITH([fsref], + AS_HELP_STRING([--with-fsref], + [use Carbon FSRef API of MacOS, if available (default=yes)])) +if test x$with_fsref = xno; then + AC_MSG_WARN([ +*** WARNING + FreeType2 built without FSRef API cannot load + data-fork fonts on MacOS, except of XXX.dfont. + ]) + CFLAGS="$CFLAGS -DHAVE_FSREF=0" +elif test x$with_old_mac_fonts = xyes -a x$with_fsref != x; then + AC_MSG_CHECKING([FSRef-based FileManager]) + AC_LINK_IFELSE([ + AC_LANG_PROGRAM([ + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + ], + [ + + short vRefNum; + long dirID; + ConstStr255Param fileName; + + Boolean* isDirectory; + UInt8* path; + SInt16 desiredRefNum; + SInt16* iterator; + SInt16* actualRefNum; + HFSUniStr255* outForkName; + FSVolumeRefNum volume; + FSCatalogInfoBitmap whichInfo; + FSCatalogInfo* catalogInfo; + FSForkInfo* forkInfo; + FSRef* ref; + +#if HAVE_FSSPEC + FSSpec* spec; +#endif + + /* FSRef functions: no need to check? */ + FSGetForkCBInfo( desiredRefNum, volume, iterator, + actualRefNum, forkInfo, ref, + outForkName ); + FSPathMakeRef( path, ref, isDirectory ); + +#if HAVE_FSSPEC + FSpMakeFSRef ( spec, ref ); + FSGetCatalogInfo( ref, whichInfo, catalogInfo, + outForkName, spec, ref ); +#endif + ])], + [AC_MSG_RESULT([ok]) + CFLAGS="$CFLAGS -DHAVE_FSREF=1"], + [AC_MSG_RESULT([not found]) + CFLAGS="$CFLAGS -DHAVE_FSREF=0"]) +fi + + +# Whether to use QuickDraw API in ToolBox, which is deprecated since +# Mac OS X 10.4. + +AC_ARG_WITH([quickdraw-toolbox], + AS_HELP_STRING([--with-quickdraw-toolbox], + [use MacOS QuickDraw in ToolBox, if available (default=yes)])) +if test x$with_quickdraw_toolbox = xno; then + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_TOOLBOX=0" +elif test x$with_old_mac_fonts = xyes -a x$with_quickdraw_toolbox != x; then + AC_MSG_CHECKING([QuickDraw FontManager functions in ToolBox]) + AC_LINK_IFELSE([ + AC_LANG_PROGRAM([ + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + ], + [ + + Str255 familyName; + SInt16 familyID = 0; + FMInput* fmIn = NULL; + FMOutput* fmOut = NULL; + + + GetFontName( familyID, familyName ); + GetFNum( familyName, &familyID ); + fmOut = FMSwapFont( fmIn ); + + ])], + [AC_MSG_RESULT([ok]) + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_TOOLBOX=1"], + [AC_MSG_RESULT([not found]) + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_TOOLBOX=0"]) +fi + + +# Whether to use QuickDraw API in Carbon, which is deprecated since +# Mac OS X 10.4. + +AC_ARG_WITH([quickdraw-carbon], + AS_HELP_STRING([--with-quickdraw-carbon], + [use MacOS QuickDraw in Carbon, if available (default=yes)])) +if test x$with_quickdraw_carbon = xno; then + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_CARBON=0" +elif test x$with_old_mac_fonts = xyes -a x$with_quickdraw_carbon != x; then + AC_MSG_CHECKING([QuickDraw FontManager functions in Carbon]) + AC_LINK_IFELSE([ + AC_LANG_PROGRAM([ + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + ], + [ + + FMFontFamilyIterator famIter; + FMFontFamily family; + Str255 famNameStr; + FMFontFamilyInstanceIterator instIter; + FMFontStyle style; + FMFontSize size; + FMFont font; + FSSpec* pathSpec; + + + FMCreateFontFamilyIterator( NULL, NULL, kFMUseGlobalScopeOption, + &famIter ); + FMGetNextFontFamily( &famIter, &family ); + FMGetFontFamilyName( family, famNameStr ); + FMCreateFontFamilyInstanceIterator( family, &instIter ); + FMGetNextFontFamilyInstance( &instIter, &font, &style, &size ); + FMDisposeFontFamilyInstanceIterator( &instIter ); + FMDisposeFontFamilyIterator( &famIter ); + FMGetFontContainer( font, pathSpec ); + + ])], + [AC_MSG_RESULT([ok]) + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_CARBON=1"], + [AC_MSG_RESULT([not found]) + CFLAGS="$CFLAGS -DHAVE_QUICKDRAW_CARBON=0"]) +fi + + +# Whether to use AppleTypeService since Mac OS X. + +AC_ARG_WITH([ats], + AS_HELP_STRING([--with-ats], + [use AppleTypeService, if available (default=yes)])) +if test x$with_ats = xno; then + CFLAGS="$CFLAGS -DHAVE_ATS=0" +elif test x$with_old_mac_fonts = xyes -a x$with_ats != x; then + AC_MSG_CHECKING([AppleTypeService functions]) + AC_LINK_IFELSE([ + AC_LANG_PROGRAM([ + +#if defined(__GNUC__) && defined(__APPLE_CC__) +# include +# include +#else +# include +# include +#endif + + ], + [ + + FSSpec* pathSpec; + + + ATSFontFindFromName( NULL, kATSOptionFlagsUnRestrictedScope ); +#if HAVE_FSSPEC + ATSFontGetFileSpecification( 0, pathSpec ); +#endif + + ])], + [AC_MSG_RESULT([ok]) + CFLAGS="$CFLAGS -DHAVE_ATS=1"], + [AC_MSG_RESULT([not found]) + CFLAGS="$CFLAGS -DHAVE_ATS=0"]) +fi + +case "$CFLAGS" in + *HAVE_FSSPEC* | *HAVE_FSREF* | *HAVE_QUICKDRAW* | *HAVE_ATS* ) + AC_MSG_WARN([ +*** WARNING + FSSpec/FSRef/QuickDraw/ATS options are explicitly given, + thus it is recommended to replace src/base/ftmac.c by builds/mac/ftmac.c. + ]) + CFLAGS="$CFLAGS "'-I$(TOP_DIR)/builds/mac/' + ;; + *) + ;; +esac + +# Check for pthreads + +AX_PTHREAD([have_pthread=yes], [have_pthread=no]) + +# Check for Python and docwriter +PYTHON_MIN_VERSION=3.5 +have_py3=no +have_docwriter=no +PIP=pip + +AC_CHECK_PROGS([PYTHON], [python3 python], [missing]) +if test "x$PYTHON" != "xmissing"; then + AX_PROG_PYTHON_VERSION([$PYTHON_MIN_VERSION], [have_py3=yes], []) + + if test "x$have_py3" = "xyes"; then + PIP="$PYTHON -m $PIP" + AC_MSG_CHECKING([for `docwriter' Python module]) + $PYTHON -m docwriter -h > /dev/null 2>&1 + if test "x$?" = "x0"; then + have_docwriter=yes + AC_MSG_RESULT([yes]) + else + AC_MSG_RESULT([no]) + fi + fi +fi + + +# entries in Requires.private are separated by commas +PKGCONFIG_REQUIRES_PRIVATE="$zlib_reqpriv, \ + $bzip2_reqpriv, \ + $libpng_reqpriv, \ + $harfbuzz_reqpriv, \ + $brotli_reqpriv" +# beautify +PKGCONFIG_REQUIRES_PRIVATE=`echo "$PKGCONFIG_REQUIRES_PRIVATE" \ + | sed -e 's/^ *//' \ + -e 's/ *$//' \ + -e 's/, */,/g' \ + -e 's/,,*/,/g' \ + -e 's/^,*//' \ + -e 's/,*$//' \ + -e 's/,/, /g'` + +PKGCONFIG_LIBS_PRIVATE="$zlib_libspriv \ + $bzip2_libspriv \ + $libpng_libspriv \ + $harfbuzz_libspriv \ + $brotli_libspriv \ + $ft2_extra_libs" +# beautify +PKGCONFIG_LIBS_PRIVATE=`echo "$PKGCONFIG_LIBS_PRIVATE" \ + | sed -e 's/^ *//' \ + -e 's/ *$//' \ + -e 's/ */ /g'` + +LIBSSTATIC_CONFIG="-lfreetype \ + $zlib_libsstaticconf \ + $bzip2_libsstaticconf \ + $libpng_libsstaticconf \ + $harfbuzz_libsstaticconf \ + $brotli_libsstaticconf \ + $ft2_extra_libs" +# remove -L/usr/lib and -L/usr/lib64 since `freetype-config' adds them later +# on if necessary; also beautify +LIBSSTATIC_CONFIG=`echo "$LIBSSTATIC_CONFIG" \ + | sed -e 's|-L */usr/lib64/* | |g' \ + -e 's|-L */usr/lib/* | |g' \ + -e 's/^ *//' \ + -e 's/ *$//' \ + -e 's/ */ /g'` + +# If FreeType gets installed with `--disable-shared', don't use +# 'private' fields. `pkg-config' only looks into `.pc' files and is +# completely agnostic to whether shared libraries are actually present +# or not. As a consequence, the user had to specify `--static' while +# calling `pkg-config', which configure scripts are normally not +# prepared for. + +PKGCONFIG_REQUIRES= +PKGCONFIG_LIBS='-L${libdir} -lfreetype' + +if test $enable_shared = "no"; then + PKGCONFIG_REQUIRES="$PKGCONFIG_REQUIRES $PKGCONFIG_REQUIRES_PRIVATE" + PKGCONFIG_REQUIRES_PRIVATE= + PKGCONFIG_LIBS="$PKGCONFIG_LIBS $PKGCONFIG_LIBS_PRIVATE" + PKGCONFIG_LIBS_PRIVATE= +fi + +AC_SUBST([ftmac_c]) +AC_SUBST([PKGCONFIG_REQUIRES]) +AC_SUBST([PKGCONFIG_LIBS]) +AC_SUBST([PKGCONFIG_REQUIRES_PRIVATE]) +AC_SUBST([PKGCONFIG_LIBS_PRIVATE]) +AC_SUBST([LIBSSTATIC_CONFIG]) + +AC_SUBST([hardcode_libdir_flag_spec]) +AC_SUBST([wl]) +AC_SUBST([build_libtool_libs]) + + +# changing LDFLAGS value should only be done after +# lt_cv_prog_compiler_static_works test + +ftoption_set() +{ + regexp="-e \\\"s|.*#.*def.*$1.*|#define $1|\\\"" + FTOPTION_H_SED="$FTOPTION_H_SED $regexp" +} + +ftoption_unset() +{ + regexp="-e \\\"s|.*#.*def.*$1.*|/* #undef $1 */|\\\"" + FTOPTION_H_SED="$FTOPTION_H_SED $regexp" +} + +if test "$have_zlib" != no; then + CFLAGS="$CFLAGS $ZLIB_CFLAGS" + LDFLAGS="$LDFLAGS $ZLIB_LIBS" + ftoption_set FT_CONFIG_OPTION_SYSTEM_ZLIB +else + ftoption_unset FT_CONFIG_OPTION_SYSTEM_ZLIB +fi +if test "$have_bzip2" != no; then + CFLAGS="$CFLAGS $BZIP2_CFLAGS" + LDFLAGS="$LDFLAGS $BZIP2_LIBS" + ftoption_set FT_CONFIG_OPTION_USE_BZIP2 +else + ftoption_unset FT_CONFIG_OPTION_USE_BZIP2 +fi +if test "$have_libpng" != no; then + CFLAGS="$CFLAGS $LIBPNG_CFLAGS" + LDFLAGS="$LDFLAGS $LIBPNG_LIBS" + ftoption_set FT_CONFIG_OPTION_USE_PNG +else + ftoption_unset FT_CONFIG_OPTION_USE_PNG +fi +if test "$have_harfbuzz" != no; then + CFLAGS="$CFLAGS $HARFBUZZ_CFLAGS" + LDFLAGS="$LDFLAGS $HARFBUZZ_LIBS" + ftoption_set FT_CONFIG_OPTION_USE_HARFBUZZ +else + ftoption_unset FT_CONFIG_OPTION_USE_HARFBUZZ +fi +if test "$have_brotli" != no; then + CFLAGS="$CFLAGS $BROTLI_CFLAGS" + LDFLAGS="$LDFLAGS $BROTLI_LIBS" + ftoption_set FT_CONFIG_OPTION_USE_BROTLI +else + ftoption_unset FT_CONFIG_OPTION_USE_BROTLI +fi + +if test "$have_pthread" != no; then + CFLAGS="$CFLAGS $PTHREAD_CFLAGS" + LDFLAGS="$LDFLAGS $PTHREAD_CFLAGS $PTHREAD_LIBS" +fi + +AC_SUBST([CFLAGS]) +AC_SUBST([LDFLAGS]) + +# We don't want to use a template file for `ftoption.h', since compilation +# should work without calling a configure script also. For this reason, we +# copy the `include/freetype/config/ftoption.h' file to the `unix/builds' +# directory (using a dummy `AC_CONFIG_FILES' call) and apply the just +# constructed $FTOPTION_H_SED regexp (using the post-action of +# `AC_CONFIG_FILES'); this is also the version that gets installed later on. +# +AC_CONFIG_FILES([ftoption.h:${srcdir}/../../include/freetype/config/ftoption.h], + [mv ftoption.h ftoption.tmp + eval "sed $FTOPTION_H_SED < ftoption.tmp > ftoption.h" + rm ftoption.tmp], + [FTOPTION_H_SED="$FTOPTION_H_SED"]) + +AC_CONFIG_HEADERS([ftconfig.h]) + +# create the Unix-specific sub-Makefiles `builds/unix/unix-def.mk' +# and `builds/unix/unix-cc.mk' that will be used by the build system +# +AC_CONFIG_FILES([unix-cc.mk:unix-cc.in + unix-def.mk:unix-def.in]) + +AC_OUTPUT + +AC_MSG_NOTICE([ + +Library configuration: + external zlib: $have_zlib + bzip2: $have_bzip2 + libpng: $have_libpng + harfbuzz: $have_harfbuzz + brotli: $have_brotli + pthread: $have_pthread +]) + +# Warn if docwriter is not installed + +if test $have_docwriter = no; then + AC_MSG_WARN([ + `make refdoc' will fail since pip package `docwriter' is not installed. + To install, run `$PIP install docwriter', or to use a Python + virtual environment, run `make refdoc-venv' (requires pip package + `virtualenv'). These operations require Python >= $PYTHON_MIN_VERSION. + ]) +fi + +# Warn if pthread is not available + +if test $have_pthread = no; then + AC_MSG_WARN([ + `FT_DEBUG_LOGGING' will not work since the `pthread' library is not + available. This warning can be safely ignored if you don't plan to use + this configuration macro. + ]) +fi + +# end of configure.raw diff --git a/3rdparty/freetype-2.13.2/builds/unix/detect.mk b/3rdparty/freetype-2.13.2/builds/unix/detect.mk new file mode 100644 index 000000000..6b87013d5 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/detect.mk @@ -0,0 +1,99 @@ +# +# FreeType 2 configuration file to detect a UNIX host platform. +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + +.PHONY: setup + +ifeq ($(PLATFORM),ansi) + + # Note: this test is duplicated in "builds/toplevel.mk". + # + is_unix := $(strip $(wildcard /sbin/init) \ + $(wildcard /usr/sbin/init) \ + $(wildcard /dev/null) \ + $(wildcard /hurd/auth)) + ifneq ($(is_unix),) + + PLATFORM := unix + + endif # test is_unix +endif # test PLATFORM ansi + +ifeq ($(PLATFORM),unix) + COPY := cp + DELETE := rm -f + CAT := cat + + # If `devel' is the requested target, we use a special configuration + # file named `unix-dev.mk'. It disables optimization and libtool. + # + ifneq ($(findstring devel,$(MAKECMDGOALS)),) + CONFIG_FILE := unix-dev.mk + CC := gcc + + .PHONY: devel + devel: setup + @: + else + + # If `lcc' is the requested target, we use a special configuration + # file named `unix-lcc.mk'. It disables libtool for LCC. + # + ifneq ($(findstring lcc,$(MAKECMDGOALS)),) + CONFIG_FILE := unix-lcc.mk + CC := lcc + + .PHONY: lcc + lcc: setup + @: + else + + # If a Unix platform is detected, the configure script is called and + # `unix-def.mk' together with `unix-cc.mk' is created. + # + # Arguments to `configure' should be in the CFG variable. Example: + # + # make CFG="--prefix=/usr --disable-static" + # + # If you need to set CFLAGS or LDFLAGS, do it here also. + # + # Feel free to add support for other platform specific compilers in + # this directory (e.g. solaris.mk + changes here to detect the + # platform). + # + CONFIG_FILE := unix.mk + must_configure := 1 + + .PHONY: unix + unix: setup + @: + endif + endif + + have_Makefile := $(wildcard $(OBJ_DIR)/Makefile) + + setup: std_setup + ifdef must_configure + ifneq ($(have_Makefile),) + # we are building FT2 not in the src tree + $(TOP_DIR)/builds/unix/configure $(value CFG) + else + cd builds/unix; \ + ./configure $(value CFG) + endif + endif + +endif # test PLATFORM unix + + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/unix/freetype-config.in b/3rdparty/freetype-2.13.2/builds/unix/freetype-config.in new file mode 100644 index 000000000..58561126f --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/freetype-config.in @@ -0,0 +1,211 @@ +#! /bin/sh +# +# Copyright (C) 2000-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + +LC_ALL=C +export LC_ALL + + +# if `pkg-config' is available, use values from `freetype2.pc' +%PKG_CONFIG% --atleast-pkgconfig-version 0.24 >/dev/null 2>&1 +if test $? -eq 0 ; then + # note that option `--variable' is not affected by the + # PKG_CONFIG_SYSROOT_DIR environment variable + if test "x$SYSROOT" != "x" ; then + PKG_CONFIG_SYSROOT_DIR="$SYSROOT" + export PKG_CONFIG_SYSROOT_DIR + fi + + prefix=`%PKG_CONFIG% --variable prefix freetype2` + exec_prefix=`%PKG_CONFIG% --variable exec_prefix freetype2` + + includedir=`%PKG_CONFIG% --variable includedir freetype2` + libdir=`%PKG_CONFIG% --variable libdir freetype2` + + version=`%PKG_CONFIG% --modversion freetype2` + + cflags=`%PKG_CONFIG% --cflags freetype2` + dynamic_libs=`%PKG_CONFIG% --libs freetype2` + static_libs=`%PKG_CONFIG% --static --libs freetype2` +else + prefix="%prefix%" + exec_prefix="%exec_prefix%" + + includedir="%includedir%" + libdir="%libdir%" + + version=%ft_version% + + cflags="-I${SYSROOT}$includedir/freetype2" + dynamic_libs="-lfreetype" + static_libs="%LIBSSTATIC_CONFIG%" + if test "${SYSROOT}$libdir" != "/usr/lib" && + test "${SYSROOT}$libdir" != "/usr/lib64" ; then + libs_L="-L${SYSROOT}$libdir" + fi +fi + +orig_prefix=$prefix +orig_exec_prefix=$exec_prefix + +orig_includedir=$includedir +orig_libdir=$libdir + +include_suffix=`echo $includedir | sed "s|$prefix||"` +lib_suffix=`echo $libdir | sed "s|$exec_prefix||"` + + +usage() +{ + cat <&2 +fi + + +while test $# -gt 0 ; do + case "$1" in + -*=*) + optarg=`echo "$1" | sed 's/[-_a-zA-Z0-9]*=//'` + ;; + *) + optarg= + ;; + esac + + case $1 in + --prefix=*) + prefix=$optarg + local_prefix=yes + ;; + --prefix) + echo_prefix=yes + ;; + --exec-prefix=*) + exec_prefix=$optarg + exec_prefix_set=yes + local_prefix=yes + ;; + --exec-prefix) + echo_exec_prefix=yes + ;; + --version) + echo_version=yes + break + ;; + --ftversion) + echo_ft_version=yes + ;; + --cflags) + echo_cflags=yes + ;; + --libs) + echo_libs=yes + ;; + --libtool) + echo_libtool=yes + ;; + --static) + show_static=yes + ;; + --help) + usage 0 + ;; + *) + usage 1 1>&2 + ;; + esac + shift +done + + +if test "$local_prefix" = "yes" ; then + if test "$exec_prefix_set" != "yes" ; then + exec_prefix=$prefix + fi +fi + +if test "$local_prefix" = "yes" ; then + includedir=${prefix}${include_suffix} + if test "$exec_prefix_set" = "yes" ; then + libdir=${exec_prefix}${lib_suffix} + else + libdir=${prefix}${lib_suffix} + fi +fi + + +if test "$echo_version" = "yes" ; then + echo $version +fi + +if test "$echo_prefix" = "yes" ; then + echo ${SYSROOT}$prefix +fi + +if test "$echo_exec_prefix" = "yes" ; then + echo ${SYSROOT}$exec_prefix +fi + +if test "$echo_ft_version" = "yes" ; then + major=`grep define ${SYSROOT}$includedir/freetype2/freetype/freetype.h \ + | grep FREETYPE_MAJOR \ + | sed 's/.*[ ]\([0-9][0-9]*\).*/\1/'` + minor=`grep define ${SYSROOT}$includedir/freetype2/freetype/freetype.h \ + | grep FREETYPE_MINOR \ + | sed 's/.*[ ]\([0-9][0-9]*\).*/\1/'` + patch=`grep define ${SYSROOT}$includedir/freetype2/freetype/freetype.h \ + | grep FREETYPE_PATCH \ + | sed 's/.*[ ]\([0-9][0-9]*\).*/\1/'` + echo $major.$minor.$patch +fi + +if test "$echo_cflags" = "yes" ; then + echo $cflags | sed "s|$orig_includedir/freetype2|$includedir/freetype2|" +fi + +if test "$echo_libs" = "yes" ; then + if test "$show_static" = "yes" ; then + libs="$libs_L $static_libs" + else + libs="$libs_L $dynamic_libs" + fi + echo $libs | sed "s|$orig_libdir|$libdir|" +fi + +if test "$echo_libtool" = "yes" ; then + echo ${SYSROOT}$libdir/libfreetype.la +fi + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/unix/freetype2.in b/3rdparty/freetype-2.13.2/builds/unix/freetype2.in new file mode 100644 index 000000000..fe389f4b6 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/freetype2.in @@ -0,0 +1,14 @@ +prefix=%prefix% +exec_prefix=%exec_prefix% +libdir=%libdir% +includedir=%includedir% + +Name: FreeType 2 +URL: https://freetype.org +Description: A free, high-quality, and portable font engine. +Version: %ft_version% +Requires: %PKGCONFIG_REQUIRES% +Requires.private: %PKGCONFIG_REQUIRES_PRIVATE% +Libs: %PKGCONFIG_LIBS% +Libs.private: %PKGCONFIG_LIBS_PRIVATE% +Cflags: -I${includedir}/freetype2 diff --git a/3rdparty/freetype-2.13.2/builds/unix/freetype2.m4 b/3rdparty/freetype-2.13.2/builds/unix/freetype2.m4 new file mode 100644 index 000000000..09ead4304 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/freetype2.m4 @@ -0,0 +1,194 @@ +# Configure paths for FreeType2 +# Marcelo Magallon 2001-10-26, based on `gtk.m4` by Owen Taylor +# +# Copyright (C) 2001-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. +# +# As a special exception to the FreeType project license, this file may be +# distributed as part of a program that contains a configuration script +# generated by Autoconf, under the same distribution terms as the rest of +# that program. +# +# serial 7 + +# AC_CHECK_FT2([MINIMUM-VERSION [, ACTION-IF-FOUND [, ACTION-IF-NOT-FOUND]]]) +# Test for FreeType 2, and define FT2_CFLAGS and FT2_LIBS. +# MINIMUM-VERSION is what libtool reports; the default is '7.0.1' (this is +# FreeType 2.0.4). +# +# To make this code work with older autoconf versions, `AS_HELP_STRING` is +# not quoted. +# +AC_DEFUN([AC_CHECK_FT2], + [# Get the cflags and libraries from the freetype-config script + # + AC_ARG_WITH([ft-prefix], + AS_HELP_STRING([--with-ft-prefix=PREFIX], + [Prefix where FreeType is installed (optional)]), + [ft_config_prefix="$withval"], + [ft_config_prefix=""]) + + AC_ARG_WITH([ft-exec-prefix], + AS_HELP_STRING([--with-ft-exec-prefix=PREFIX], + [Exec prefix where FreeType is installed (optional)]), + [ft_config_exec_prefix="$withval"], + [ft_config_exec_prefix=""]) + + AC_ARG_ENABLE([freetypetest], + AS_HELP_STRING([--disable-freetypetest], + [Do not try to compile and run a test FreeType program]), + [], + [enable_fttest=yes]) + + if test x$ft_config_exec_prefix != x ; then + ft_config_args="$ft_config_args --exec-prefix=$ft_config_exec_prefix" + if test x${FT2_CONFIG+set} != xset ; then + FT2_CONFIG=$ft_config_exec_prefix/bin/freetype-config + fi + fi + + if test x$ft_config_prefix != x ; then + ft_config_args="$ft_config_args --prefix=$ft_config_prefix" + if test x${FT2_CONFIG+set} != xset ; then + FT2_CONFIG=$ft_config_prefix/bin/freetype-config + fi + fi + + if test "x$FT2_CONFIG" = x ; then + AC_PATH_TOOL([FT2_CONFIG], [freetype-config], [no]) + fi + + min_ft_version=m4_if([$1], [], [7.0.1], [$1]) + AC_MSG_CHECKING([for FreeType -- version >= $min_ft_version]) + no_ft="" + if test "$FT2_CONFIG" = "no" ; then + no_ft=yes + else + FT2_CFLAGS=`$FT2_CONFIG $ft_config_args --cflags` + FT2_LIBS=`$FT2_CONFIG $ft_config_args --libs` + ft_config_major_version=`$FT2_CONFIG $ft_config_args --version | \ + sed 's/\([[0-9]]*\).\([[0-9]]*\).\([[0-9]]*\)/\1/'` + ft_config_minor_version=`$FT2_CONFIG $ft_config_args --version | \ + sed 's/\([[0-9]]*\).\([[0-9]]*\).\([[0-9]]*\)/\2/'` + ft_config_micro_version=`$FT2_CONFIG $ft_config_args --version | \ + sed 's/\([[0-9]]*\).\([[0-9]]*\).\([[0-9]]*\)/\3/'` + ft_min_major_version=`echo $min_ft_version | \ + sed 's/\([[0-9]]*\).\([[0-9]]*\).\([[0-9]]*\)/\1/'` + ft_min_minor_version=`echo $min_ft_version | \ + sed 's/\([[0-9]]*\).\([[0-9]]*\).\([[0-9]]*\)/\2/'` + ft_min_micro_version=`echo $min_ft_version | \ + sed 's/\([[0-9]]*\).\([[0-9]]*\).\([[0-9]]*\)/\3/'` + if test x$enable_fttest = xyes ; then + ft_config_is_lt="" + if test $ft_config_major_version -lt $ft_min_major_version ; then + ft_config_is_lt=yes + else + if test $ft_config_major_version -eq $ft_min_major_version ; then + if test $ft_config_minor_version -lt $ft_min_minor_version ; then + ft_config_is_lt=yes + else + if test $ft_config_minor_version -eq $ft_min_minor_version ; then + if test $ft_config_micro_version -lt $ft_min_micro_version ; then + ft_config_is_lt=yes + fi + fi + fi + fi + fi + if test x$ft_config_is_lt = xyes ; then + no_ft=yes + else + ac_save_CFLAGS="$CFLAGS" + ac_save_LIBS="$LIBS" + CFLAGS="$CFLAGS $FT2_CFLAGS" + LIBS="$FT2_LIBS $LIBS" + + # + # Sanity checks for the results of freetype-config to some extent. + # + AC_RUN_IFELSE([ + AC_LANG_SOURCE([[ + +#include +#include +#include +#include + +int +main(void) +{ + FT_Library library; + FT_Error error; + + error = FT_Init_FreeType(&library); + + if (error) + return 1; + else + { + FT_Done_FreeType(library); + return 0; + } +} + + ]]) + ], + [], + [no_ft=yes], + [echo $ECHO_N "cross compiling; assuming OK... $ECHO_C"]) + + CFLAGS="$ac_save_CFLAGS" + LIBS="$ac_save_LIBS" + fi # test $ft_config_version -lt $ft_min_version + fi # test x$enable_fttest = xyes + fi # test "$FT2_CONFIG" = "no" + + if test x$no_ft = x ; then + AC_MSG_RESULT([yes]) + m4_if([$2], [], [:], [$2]) + else + AC_MSG_RESULT([no]) + if test "$FT2_CONFIG" = "no" ; then + AC_MSG_WARN([ + + The freetype-config script installed by FreeType 2 could not be found. + If FreeType 2 was installed in PREFIX, make sure PREFIX/bin is in + your path, or set the FT2_CONFIG environment variable to the + full path to freetype-config. + ]) + else + if test x$ft_config_is_lt = xyes ; then + AC_MSG_WARN([ + + Your installed version of the FreeType 2 library is too old. + If you have different versions of FreeType 2, make sure that + correct values for --with-ft-prefix or --with-ft-exec-prefix + are used, or set the FT2_CONFIG environment variable to the + full path to freetype-config. + ]) + else + AC_MSG_WARN([ + + The FreeType test program failed to run. If your system uses + shared libraries and they are installed outside the normal + system library path, make sure the variable LD_LIBRARY_PATH + (or whatever is appropriate for your system) is correctly set. + ]) + fi + fi + + FT2_CFLAGS="" + FT2_LIBS="" + m4_if([$3], [], [:], [$3]) + fi + + AC_SUBST([FT2_CFLAGS]) + AC_SUBST([FT2_LIBS])]) + +# end of freetype2.m4 diff --git a/3rdparty/freetype-2.13.2/builds/unix/ft-munmap.m4 b/3rdparty/freetype-2.13.2/builds/unix/ft-munmap.m4 new file mode 100644 index 000000000..a0fcf3580 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/ft-munmap.m4 @@ -0,0 +1,32 @@ +## FreeType specific autoconf tests +# +# Copyright (C) 2002-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + +# serial 2 + +AC_DEFUN([FT_MUNMAP_PARAM], + [AC_MSG_CHECKING([for munmap's first parameter type]) + AC_COMPILE_IFELSE([ + AC_LANG_SOURCE([[ + +#include +#include +int munmap(void *, size_t); + + ]]) + ], + [AC_MSG_RESULT([void *]) + AC_DEFINE([MUNMAP_USES_VOIDP], + [], + [Define to 1 if the first argument of munmap is of type void *])], + [AC_MSG_RESULT([char *])]) + ]) + +# end of ft-munmap.m4 diff --git a/3rdparty/freetype-2.13.2/builds/unix/ftconfig.h.in b/3rdparty/freetype-2.13.2/builds/unix/ftconfig.h.in new file mode 100644 index 000000000..3dac56126 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/ftconfig.h.in @@ -0,0 +1,52 @@ +/**************************************************************************** + * + * ftconfig.h.in + * + * UNIX-specific configuration file (specification only). + * + * Copyright (C) 1996-2023 by + * David Turner, Robert Wilhelm, and Werner Lemberg. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + + /************************************************************************** + * + * This header file contains a number of macro definitions that are used by + * the rest of the engine. Most of the macros here are automatically + * determined at compile time, and you should not need to change it to port + * FreeType, except to compile the library with a non-ANSI compiler. + * + * Note however that if some specific modifications are needed, we advise + * you to place a modified copy in your build directory. + * + * The build directory is usually `builds/`, and contains + * system-specific files that are always included first when building the + * library. + * + */ + +#ifndef FTCONFIG_H_ +#define FTCONFIG_H_ + +#include +#include FT_CONFIG_OPTIONS_H +#include FT_CONFIG_STANDARD_LIBRARY_H + +#undef HAVE_UNISTD_H +#undef HAVE_FCNTL_H + +#include +#include +#include + +#endif /* FTCONFIG_H_ */ + + +/* END */ diff --git a/3rdparty/freetype-2.13.2/builds/unix/ftsystem.c b/3rdparty/freetype-2.13.2/builds/unix/ftsystem.c new file mode 100644 index 000000000..5927215df --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/ftsystem.c @@ -0,0 +1,436 @@ +/**************************************************************************** + * + * ftsystem.c + * + * Unix-specific FreeType low-level system interface (body). + * + * Copyright (C) 1996-2023 by + * David Turner, Robert Wilhelm, and Werner Lemberg. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + +#include + /* we use our special ftconfig.h file, not the standard one */ +#include FT_CONFIG_CONFIG_H +#include +#include +#include +#include +#include + + /* memory-mapping includes and definitions */ +#ifdef HAVE_UNISTD_H +#include +#endif + +#include +#ifndef MAP_FILE +#define MAP_FILE 0x00 +#endif + +#ifdef MUNMAP_USES_VOIDP +#define MUNMAP_ARG_CAST void * +#else +#define MUNMAP_ARG_CAST char * +#endif + +#ifdef NEED_MUNMAP_DECL + +#ifdef __cplusplus + extern "C" +#else + extern +#endif + int + munmap( char* addr, + int len ); + +#define MUNMAP_ARG_CAST char * + +#endif /* NEED_DECLARATION_MUNMAP */ + + +#include +#include + +#ifdef HAVE_FCNTL_H +#include +#endif + +#include +#include +#include +#include + + + /************************************************************************** + * + * MEMORY MANAGEMENT INTERFACE + * + */ + + + /************************************************************************** + * + * It is not necessary to do any error checking for the + * allocation-related functions. This will be done by the higher level + * routines like ft_mem_alloc() or ft_mem_realloc(). + * + */ + + + /************************************************************************** + * + * @Function: + * ft_alloc + * + * @Description: + * The memory allocation function. + * + * @Input: + * memory :: + * A pointer to the memory object. + * + * size :: + * The requested size in bytes. + * + * @Return: + * The address of newly allocated block. + */ + FT_CALLBACK_DEF( void* ) + ft_alloc( FT_Memory memory, + long size ) + { + FT_UNUSED( memory ); + + return malloc( size ); + } + + + /************************************************************************** + * + * @Function: + * ft_realloc + * + * @Description: + * The memory reallocation function. + * + * @Input: + * memory :: + * A pointer to the memory object. + * + * cur_size :: + * The current size of the allocated memory block. + * + * new_size :: + * The newly requested size in bytes. + * + * block :: + * The current address of the block in memory. + * + * @Return: + * The address of the reallocated memory block. + */ + FT_CALLBACK_DEF( void* ) + ft_realloc( FT_Memory memory, + long cur_size, + long new_size, + void* block ) + { + FT_UNUSED( memory ); + FT_UNUSED( cur_size ); + + return realloc( block, new_size ); + } + + + /************************************************************************** + * + * @Function: + * ft_free + * + * @Description: + * The memory release function. + * + * @Input: + * memory :: + * A pointer to the memory object. + * + * block :: + * The address of block in memory to be freed. + */ + FT_CALLBACK_DEF( void ) + ft_free( FT_Memory memory, + void* block ) + { + FT_UNUSED( memory ); + + free( block ); + } + + + /************************************************************************** + * + * RESOURCE MANAGEMENT INTERFACE + * + */ + + + /************************************************************************** + * + * The macro FT_COMPONENT is used in trace mode. It is an implicit + * parameter of the FT_TRACE() and FT_ERROR() macros, used to print/log + * messages during execution. + */ +#undef FT_COMPONENT +#define FT_COMPONENT io + + /* We use the macro STREAM_FILE for convenience to extract the */ + /* system-specific stream handle from a given FreeType stream object */ +#define STREAM_FILE( stream ) ( (FILE*)stream->descriptor.pointer ) + + + /************************************************************************** + * + * @Function: + * ft_close_stream_by_munmap + * + * @Description: + * The function to close a stream which is opened by mmap. + * + * @Input: + * stream :: A pointer to the stream object. + */ + FT_CALLBACK_DEF( void ) + ft_close_stream_by_munmap( FT_Stream stream ) + { + munmap( (MUNMAP_ARG_CAST)stream->descriptor.pointer, stream->size ); + + stream->descriptor.pointer = NULL; + stream->size = 0; + stream->base = NULL; + } + + + /************************************************************************** + * + * @Function: + * ft_close_stream_by_free + * + * @Description: + * The function to close a stream which is created by ft_alloc. + * + * @Input: + * stream :: A pointer to the stream object. + */ + FT_CALLBACK_DEF( void ) + ft_close_stream_by_free( FT_Stream stream ) + { + ft_free( stream->memory, stream->descriptor.pointer ); + + stream->descriptor.pointer = NULL; + stream->size = 0; + stream->base = NULL; + } + + + /* documentation is in ftobjs.h */ + + FT_BASE_DEF( FT_Error ) + FT_Stream_Open( FT_Stream stream, + const char* filepathname ) + { + int file; + struct stat stat_buf; + + + if ( !stream ) + return FT_THROW( Invalid_Stream_Handle ); + + /* open the file */ + file = open( filepathname, O_RDONLY ); + if ( file < 0 ) + { + FT_ERROR(( "FT_Stream_Open:" )); + FT_ERROR(( " could not open `%s'\n", filepathname )); + return FT_THROW( Cannot_Open_Resource ); + } + + /* Here we ensure that a "fork" will _not_ duplicate */ + /* our opened input streams on Unix. This is critical */ + /* since it avoids some (possible) access control */ + /* issues and cleans up the kernel file table a bit. */ + /* */ +#ifdef F_SETFD +#ifdef FD_CLOEXEC + (void)fcntl( file, F_SETFD, FD_CLOEXEC ); +#else + (void)fcntl( file, F_SETFD, 1 ); +#endif /* FD_CLOEXEC */ +#endif /* F_SETFD */ + + if ( fstat( file, &stat_buf ) < 0 ) + { + FT_ERROR(( "FT_Stream_Open:" )); + FT_ERROR(( " could not `fstat' file `%s'\n", filepathname )); + goto Fail_Map; + } + + /* XXX: TODO -- real 64bit platform support */ + /* */ + /* `stream->size' is typedef'd to unsigned long (in `ftsystem.h'); */ + /* `stat_buf.st_size', however, is usually typedef'd to off_t */ + /* (in sys/stat.h). */ + /* On some platforms, the former is 32bit and the latter is 64bit. */ + /* To avoid overflow caused by fonts in huge files larger than */ + /* 2GB, do a test. Temporary fix proposed by Sean McBride. */ + /* */ + if ( stat_buf.st_size > LONG_MAX ) + { + FT_ERROR(( "FT_Stream_Open: file is too big\n" )); + goto Fail_Map; + } + else if ( stat_buf.st_size == 0 ) + { + FT_ERROR(( "FT_Stream_Open: zero-length file\n" )); + goto Fail_Map; + } + + /* This cast potentially truncates a 64bit to 32bit! */ + stream->size = (unsigned long)stat_buf.st_size; + stream->pos = 0; + stream->base = (unsigned char *)mmap( NULL, + stream->size, + PROT_READ, + MAP_FILE | MAP_PRIVATE, + file, + 0 ); + + if ( stream->base != MAP_FAILED ) + stream->close = ft_close_stream_by_munmap; + else + { + ssize_t total_read_count; + + + FT_ERROR(( "FT_Stream_Open:" )); + FT_ERROR(( " could not `mmap' file `%s'\n", filepathname )); + + stream->base = (unsigned char*)ft_alloc( stream->memory, stream->size ); + + if ( !stream->base ) + { + FT_ERROR(( "FT_Stream_Open:" )); + FT_ERROR(( " could not `alloc' memory\n" )); + goto Fail_Map; + } + + total_read_count = 0; + do + { + ssize_t read_count; + + + read_count = read( file, + stream->base + total_read_count, + stream->size - total_read_count ); + + if ( read_count <= 0 ) + { + if ( read_count == -1 && errno == EINTR ) + continue; + + FT_ERROR(( "FT_Stream_Open:" )); + FT_ERROR(( " error while `read'ing file `%s'\n", filepathname )); + goto Fail_Read; + } + + total_read_count += read_count; + + } while ( (unsigned long)total_read_count != stream->size ); + + stream->close = ft_close_stream_by_free; + } + + close( file ); + + stream->descriptor.pointer = stream->base; + stream->pathname.pointer = (char*)filepathname; + + stream->read = NULL; + + FT_TRACE1(( "FT_Stream_Open:" )); + FT_TRACE1(( " opened `%s' (%ld bytes) successfully\n", + filepathname, stream->size )); + + return FT_Err_Ok; + + Fail_Read: + ft_free( stream->memory, stream->base ); + + Fail_Map: + close( file ); + + stream->base = NULL; + stream->size = 0; + stream->pos = 0; + + return FT_THROW( Cannot_Open_Stream ); + } + + +#ifdef FT_DEBUG_MEMORY + + extern FT_Int + ft_mem_debug_init( FT_Memory memory ); + + extern void + ft_mem_debug_done( FT_Memory memory ); + +#endif + + + /* documentation is in ftobjs.h */ + + FT_BASE_DEF( FT_Memory ) + FT_New_Memory( void ) + { + FT_Memory memory; + + + memory = (FT_Memory)malloc( sizeof ( *memory ) ); + if ( memory ) + { + memory->user = NULL; + memory->alloc = ft_alloc; + memory->realloc = ft_realloc; + memory->free = ft_free; +#ifdef FT_DEBUG_MEMORY + ft_mem_debug_init( memory ); +#endif + } + + return memory; + } + + + /* documentation is in ftobjs.h */ + + FT_BASE_DEF( void ) + FT_Done_Memory( FT_Memory memory ) + { +#ifdef FT_DEBUG_MEMORY + ft_mem_debug_done( memory ); +#endif + memory->free( memory, memory ); + } + + +/* END */ diff --git a/3rdparty/freetype-2.13.2/builds/unix/install-sh b/3rdparty/freetype-2.13.2/builds/unix/install-sh new file mode 100644 index 000000000..ec298b537 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/install-sh @@ -0,0 +1,541 @@ +#!/bin/sh +# install - install a program, script, or datafile + +scriptversion=2020-11-14.01; # UTC + +# This originates from X11R5 (mit/util/scripts/install.sh), which was +# later released in X11R6 (xc/config/util/install.sh) with the +# following copyright and license. +# +# Copyright (C) 1994 X Consortium +# +# 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 +# X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN +# AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNEC- +# TION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +# +# Except as contained in this notice, the name of the X Consortium shall not +# be used in advertising or otherwise to promote the sale, use or other deal- +# ings in this Software without prior written authorization from the X Consor- +# tium. +# +# +# FSF changes to this file are in the public domain. +# +# Calling this script install-sh is preferred over install.sh, to prevent +# 'make' implicit rules from creating a file called install from it +# when there is no Makefile. +# +# This script is compatible with the BSD install script, but was written +# from scratch. + +tab=' ' +nl=' +' +IFS=" $tab$nl" + +# Set DOITPROG to "echo" to test this script. + +doit=${DOITPROG-} +doit_exec=${doit:-exec} + +# Put in absolute file names if you don't have them in your path; +# or use environment vars. + +chgrpprog=${CHGRPPROG-chgrp} +chmodprog=${CHMODPROG-chmod} +chownprog=${CHOWNPROG-chown} +cmpprog=${CMPPROG-cmp} +cpprog=${CPPROG-cp} +mkdirprog=${MKDIRPROG-mkdir} +mvprog=${MVPROG-mv} +rmprog=${RMPROG-rm} +stripprog=${STRIPPROG-strip} + +posix_mkdir= + +# Desired mode of installed file. +mode=0755 + +# Create dirs (including intermediate dirs) using mode 755. +# This is like GNU 'install' as of coreutils 8.32 (2020). +mkdir_umask=22 + +backupsuffix= +chgrpcmd= +chmodcmd=$chmodprog +chowncmd= +mvcmd=$mvprog +rmcmd="$rmprog -f" +stripcmd= + +src= +dst= +dir_arg= +dst_arg= + +copy_on_change=false +is_target_a_directory=possibly + +usage="\ +Usage: $0 [OPTION]... [-T] SRCFILE DSTFILE + or: $0 [OPTION]... SRCFILES... DIRECTORY + or: $0 [OPTION]... -t DIRECTORY SRCFILES... + or: $0 [OPTION]... -d DIRECTORIES... + +In the 1st form, copy SRCFILE to DSTFILE. +In the 2nd and 3rd, copy all SRCFILES to DIRECTORY. +In the 4th, create DIRECTORIES. + +Options: + --help display this help and exit. + --version display version info and exit. + + -c (ignored) + -C install only if different (preserve data modification time) + -d create directories instead of installing files. + -g GROUP $chgrpprog installed files to GROUP. + -m MODE $chmodprog installed files to MODE. + -o USER $chownprog installed files to USER. + -p pass -p to $cpprog. + -s $stripprog installed files. + -S SUFFIX attempt to back up existing files, with suffix SUFFIX. + -t DIRECTORY install into DIRECTORY. + -T report an error if DSTFILE is a directory. + +Environment variables override the default commands: + CHGRPPROG CHMODPROG CHOWNPROG CMPPROG CPPROG MKDIRPROG MVPROG + RMPROG STRIPPROG + +By default, rm is invoked with -f; when overridden with RMPROG, +it's up to you to specify -f if you want it. + +If -S is not specified, no backups are attempted. + +Email bug reports to bug-automake@gnu.org. +Automake home page: https://www.gnu.org/software/automake/ +" + +while test $# -ne 0; do + case $1 in + -c) ;; + + -C) copy_on_change=true;; + + -d) dir_arg=true;; + + -g) chgrpcmd="$chgrpprog $2" + shift;; + + --help) echo "$usage"; exit $?;; + + -m) mode=$2 + case $mode in + *' '* | *"$tab"* | *"$nl"* | *'*'* | *'?'* | *'['*) + echo "$0: invalid mode: $mode" >&2 + exit 1;; + esac + shift;; + + -o) chowncmd="$chownprog $2" + shift;; + + -p) cpprog="$cpprog -p";; + + -s) stripcmd=$stripprog;; + + -S) backupsuffix="$2" + shift;; + + -t) + is_target_a_directory=always + dst_arg=$2 + # Protect names problematic for 'test' and other utilities. + case $dst_arg in + -* | [=\(\)!]) dst_arg=./$dst_arg;; + esac + shift;; + + -T) is_target_a_directory=never;; + + --version) echo "$0 $scriptversion"; exit $?;; + + --) shift + break;; + + -*) echo "$0: invalid option: $1" >&2 + exit 1;; + + *) break;; + esac + shift +done + +# We allow the use of options -d and -T together, by making -d +# take the precedence; this is for compatibility with GNU install. + +if test -n "$dir_arg"; then + if test -n "$dst_arg"; then + echo "$0: target directory not allowed when installing a directory." >&2 + exit 1 + fi +fi + +if test $# -ne 0 && test -z "$dir_arg$dst_arg"; then + # When -d is used, all remaining arguments are directories to create. + # When -t is used, the destination is already specified. + # Otherwise, the last argument is the destination. Remove it from $@. + for arg + do + if test -n "$dst_arg"; then + # $@ is not empty: it contains at least $arg. + set fnord "$@" "$dst_arg" + shift # fnord + fi + shift # arg + dst_arg=$arg + # Protect names problematic for 'test' and other utilities. + case $dst_arg in + -* | [=\(\)!]) dst_arg=./$dst_arg;; + esac + done +fi + +if test $# -eq 0; then + if test -z "$dir_arg"; then + echo "$0: no input file specified." >&2 + exit 1 + fi + # It's OK to call 'install-sh -d' without argument. + # This can happen when creating conditional directories. + exit 0 +fi + +if test -z "$dir_arg"; then + if test $# -gt 1 || test "$is_target_a_directory" = always; then + if test ! -d "$dst_arg"; then + echo "$0: $dst_arg: Is not a directory." >&2 + exit 1 + fi + fi +fi + +if test -z "$dir_arg"; then + do_exit='(exit $ret); exit $ret' + trap "ret=129; $do_exit" 1 + trap "ret=130; $do_exit" 2 + trap "ret=141; $do_exit" 13 + trap "ret=143; $do_exit" 15 + + # Set umask so as not to create temps with too-generous modes. + # However, 'strip' requires both read and write access to temps. + case $mode in + # Optimize common cases. + *644) cp_umask=133;; + *755) cp_umask=22;; + + *[0-7]) + if test -z "$stripcmd"; then + u_plus_rw= + else + u_plus_rw='% 200' + fi + cp_umask=`expr '(' 777 - $mode % 1000 ')' $u_plus_rw`;; + *) + if test -z "$stripcmd"; then + u_plus_rw= + else + u_plus_rw=,u+rw + fi + cp_umask=$mode$u_plus_rw;; + esac +fi + +for src +do + # Protect names problematic for 'test' and other utilities. + case $src in + -* | [=\(\)!]) src=./$src;; + esac + + if test -n "$dir_arg"; then + dst=$src + dstdir=$dst + test -d "$dstdir" + dstdir_status=$? + # Don't chown directories that already exist. + if test $dstdir_status = 0; then + chowncmd="" + fi + else + + # Waiting for this to be detected by the "$cpprog $src $dsttmp" command + # might cause directories to be created, which would be especially bad + # if $src (and thus $dsttmp) contains '*'. + if test ! -f "$src" && test ! -d "$src"; then + echo "$0: $src does not exist." >&2 + exit 1 + fi + + if test -z "$dst_arg"; then + echo "$0: no destination specified." >&2 + exit 1 + fi + dst=$dst_arg + + # If destination is a directory, append the input filename. + if test -d "$dst"; then + if test "$is_target_a_directory" = never; then + echo "$0: $dst_arg: Is a directory" >&2 + exit 1 + fi + dstdir=$dst + dstbase=`basename "$src"` + case $dst in + */) dst=$dst$dstbase;; + *) dst=$dst/$dstbase;; + esac + dstdir_status=0 + else + dstdir=`dirname "$dst"` + test -d "$dstdir" + dstdir_status=$? + fi + fi + + case $dstdir in + */) dstdirslash=$dstdir;; + *) dstdirslash=$dstdir/;; + esac + + obsolete_mkdir_used=false + + if test $dstdir_status != 0; then + case $posix_mkdir in + '') + # With -d, create the new directory with the user-specified mode. + # Otherwise, rely on $mkdir_umask. + if test -n "$dir_arg"; then + mkdir_mode=-m$mode + else + mkdir_mode= + fi + + posix_mkdir=false + # The $RANDOM variable is not portable (e.g., dash). Use it + # here however when possible just to lower collision chance. + tmpdir=${TMPDIR-/tmp}/ins$RANDOM-$$ + + trap ' + ret=$? + rmdir "$tmpdir/a/b" "$tmpdir/a" "$tmpdir" 2>/dev/null + exit $ret + ' 0 + + # Because "mkdir -p" follows existing symlinks and we likely work + # directly in world-writeable /tmp, make sure that the '$tmpdir' + # directory is successfully created first before we actually test + # 'mkdir -p'. + if (umask $mkdir_umask && + $mkdirprog $mkdir_mode "$tmpdir" && + exec $mkdirprog $mkdir_mode -p -- "$tmpdir/a/b") >/dev/null 2>&1 + then + if test -z "$dir_arg" || { + # Check for POSIX incompatibilities with -m. + # HP-UX 11.23 and IRIX 6.5 mkdir -m -p sets group- or + # other-writable bit of parent directory when it shouldn't. + # FreeBSD 6.1 mkdir -m -p sets mode of existing directory. + test_tmpdir="$tmpdir/a" + ls_ld_tmpdir=`ls -ld "$test_tmpdir"` + case $ls_ld_tmpdir in + d????-?r-*) different_mode=700;; + d????-?--*) different_mode=755;; + *) false;; + esac && + $mkdirprog -m$different_mode -p -- "$test_tmpdir" && { + ls_ld_tmpdir_1=`ls -ld "$test_tmpdir"` + test "$ls_ld_tmpdir" = "$ls_ld_tmpdir_1" + } + } + then posix_mkdir=: + fi + rmdir "$tmpdir/a/b" "$tmpdir/a" "$tmpdir" + else + # Remove any dirs left behind by ancient mkdir implementations. + rmdir ./$mkdir_mode ./-p ./-- "$tmpdir" 2>/dev/null + fi + trap '' 0;; + esac + + if + $posix_mkdir && ( + umask $mkdir_umask && + $doit_exec $mkdirprog $mkdir_mode -p -- "$dstdir" + ) + then : + else + + # mkdir does not conform to POSIX, + # or it failed possibly due to a race condition. Create the + # directory the slow way, step by step, checking for races as we go. + + case $dstdir in + /*) prefix='/';; + [-=\(\)!]*) prefix='./';; + *) prefix='';; + esac + + oIFS=$IFS + IFS=/ + set -f + set fnord $dstdir + shift + set +f + IFS=$oIFS + + prefixes= + + for d + do + test X"$d" = X && continue + + prefix=$prefix$d + if test -d "$prefix"; then + prefixes= + else + if $posix_mkdir; then + (umask $mkdir_umask && + $doit_exec $mkdirprog $mkdir_mode -p -- "$dstdir") && break + # Don't fail if two instances are running concurrently. + test -d "$prefix" || exit 1 + else + case $prefix in + *\'*) qprefix=`echo "$prefix" | sed "s/'/'\\\\\\\\''/g"`;; + *) qprefix=$prefix;; + esac + prefixes="$prefixes '$qprefix'" + fi + fi + prefix=$prefix/ + done + + if test -n "$prefixes"; then + # Don't fail if two instances are running concurrently. + (umask $mkdir_umask && + eval "\$doit_exec \$mkdirprog $prefixes") || + test -d "$dstdir" || exit 1 + obsolete_mkdir_used=true + fi + fi + fi + + if test -n "$dir_arg"; then + { test -z "$chowncmd" || $doit $chowncmd "$dst"; } && + { test -z "$chgrpcmd" || $doit $chgrpcmd "$dst"; } && + { test "$obsolete_mkdir_used$chowncmd$chgrpcmd" = false || + test -z "$chmodcmd" || $doit $chmodcmd $mode "$dst"; } || exit 1 + else + + # Make a couple of temp file names in the proper directory. + dsttmp=${dstdirslash}_inst.$$_ + rmtmp=${dstdirslash}_rm.$$_ + + # Trap to clean up those temp files at exit. + trap 'ret=$?; rm -f "$dsttmp" "$rmtmp" && exit $ret' 0 + + # Copy the file name to the temp name. + (umask $cp_umask && + { test -z "$stripcmd" || { + # Create $dsttmp read-write so that cp doesn't create it read-only, + # which would cause strip to fail. + if test -z "$doit"; then + : >"$dsttmp" # No need to fork-exec 'touch'. + else + $doit touch "$dsttmp" + fi + } + } && + $doit_exec $cpprog "$src" "$dsttmp") && + + # and set any options; do chmod last to preserve setuid bits. + # + # If any of these fail, we abort the whole thing. If we want to + # ignore errors from any of these, just make sure not to ignore + # errors from the above "$doit $cpprog $src $dsttmp" command. + # + { test -z "$chowncmd" || $doit $chowncmd "$dsttmp"; } && + { test -z "$chgrpcmd" || $doit $chgrpcmd "$dsttmp"; } && + { test -z "$stripcmd" || $doit $stripcmd "$dsttmp"; } && + { test -z "$chmodcmd" || $doit $chmodcmd $mode "$dsttmp"; } && + + # If -C, don't bother to copy if it wouldn't change the file. + if $copy_on_change && + old=`LC_ALL=C ls -dlL "$dst" 2>/dev/null` && + new=`LC_ALL=C ls -dlL "$dsttmp" 2>/dev/null` && + set -f && + set X $old && old=:$2:$4:$5:$6 && + set X $new && new=:$2:$4:$5:$6 && + set +f && + test "$old" = "$new" && + $cmpprog "$dst" "$dsttmp" >/dev/null 2>&1 + then + rm -f "$dsttmp" + else + # If $backupsuffix is set, and the file being installed + # already exists, attempt a backup. Don't worry if it fails, + # e.g., if mv doesn't support -f. + if test -n "$backupsuffix" && test -f "$dst"; then + $doit $mvcmd -f "$dst" "$dst$backupsuffix" 2>/dev/null + fi + + # Rename the file to the real destination. + $doit $mvcmd -f "$dsttmp" "$dst" 2>/dev/null || + + # The rename failed, perhaps because mv can't rename something else + # to itself, or perhaps because mv is so ancient that it does not + # support -f. + { + # Now remove or move aside any old file at destination location. + # We try this two ways since rm can't unlink itself on some + # systems and the destination file might be busy for other + # reasons. In this case, the final cleanup might fail but the new + # file should still install successfully. + { + test ! -f "$dst" || + $doit $rmcmd "$dst" 2>/dev/null || + { $doit $mvcmd -f "$dst" "$rmtmp" 2>/dev/null && + { $doit $rmcmd "$rmtmp" 2>/dev/null; :; } + } || + { echo "$0: cannot unlink or rename $dst" >&2 + (exit 1); exit 1 + } + } && + + # Now rename the file to the real destination. + $doit $mvcmd "$dsttmp" "$dst" + } + fi || exit 1 + + trap '' 0 + fi +done + +# Local variables: +# eval: (add-hook 'before-save-hook 'time-stamp) +# time-stamp-start: "scriptversion=" +# time-stamp-format: "%:y-%02m-%02d.%02H" +# time-stamp-time-zone: "UTC0" +# time-stamp-end: "; # UTC" +# End: diff --git a/3rdparty/freetype-2.13.2/builds/unix/install.mk b/3rdparty/freetype-2.13.2/builds/unix/install.mk new file mode 100644 index 000000000..2f1729b71 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/install.mk @@ -0,0 +1,102 @@ +# +# FreeType 2 installation instructions for Unix systems +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + +# If you say +# +# make install DESTDIR=/tmp/somewhere/ +# +# don't forget the final backslash (this command is mainly for package +# maintainers). + + +.PHONY: install uninstall check + +# Unix installation and deinstallation targets. +# +# Note that we remove any data found in `$(includedir)/freetype2' before +# installing new files to avoid interferences with files installed by +# previous FreeType versions (which use slightly different locations). +# +# We also remove `$(includedir)/ft2build.h' for the same reason. +# +# Note that some header files get handled twice for simplicity; a special, +# configured version overwrites the generic one. +# +install: $(PROJECT_LIBRARY) + -$(DELDIR) $(DESTDIR)$(includedir)/freetype2 + -$(DELETE) $(DESTDIR)$(includedir)/ft2build.h + $(MKINSTALLDIRS) $(DESTDIR)$(libdir) \ + $(DESTDIR)$(libdir)/pkgconfig \ + $(DESTDIR)$(includedir)/freetype2/freetype/config \ + $(DESTDIR)$(datadir)/aclocal +ifeq ($(INSTALL_FT2_CONFIG),TRUE) + $(MKINSTALLDIRS) $(DESTDIR)$(bindir) \ + $(DESTDIR)$(mandir)/man1 +endif + $(LIBTOOL) --mode=install $(INSTALL) \ + $(PROJECT_LIBRARY) $(DESTDIR)$(libdir) + -for P in $(PUBLIC_H) ; do \ + $(INSTALL_DATA) \ + $$P $(DESTDIR)$(includedir)/freetype2/freetype ; \ + done + -for P in $(CONFIG_H) ; do \ + $(INSTALL_DATA) \ + $$P $(DESTDIR)$(includedir)/freetype2/freetype/config ; \ + done + $(INSTALL_DATA) $(TOP_DIR)/include/ft2build.h \ + $(DESTDIR)$(includedir)/freetype2/ft2build.h + $(INSTALL_DATA) $(OBJ_BUILD)/ftconfig.h \ + $(DESTDIR)$(includedir)/freetype2/freetype/config/ftconfig.h + $(INSTALL_DATA) $(OBJ_DIR)/ftmodule.h \ + $(DESTDIR)$(includedir)/freetype2/freetype/config/ftmodule.h + $(INSTALL_DATA) $(OBJ_BUILD)/ftoption.h \ + $(DESTDIR)$(includedir)/freetype2/freetype/config/ftoption.h + $(INSTALL_SCRIPT) -m 644 $(PLATFORM_DIR)/freetype2.m4 \ + $(DESTDIR)$(datadir)/aclocal/freetype2.m4 + $(INSTALL_SCRIPT) -m 644 $(OBJ_BUILD)/freetype2.pc \ + $(DESTDIR)$(libdir)/pkgconfig/freetype2.pc +ifeq ($(INSTALL_FT2_CONFIG),TRUE) + $(INSTALL_SCRIPT) -m 755 $(OBJ_BUILD)/freetype-config \ + $(DESTDIR)$(bindir)/freetype-config + $(INSTALL_DATA) $(TOP_DIR)/docs/freetype-config.1 \ + $(DESTDIR)$(mandir)/man1/freetype-config.1 +endif + + +uninstall: + -$(LIBTOOL) --mode=uninstall $(RM) $(DESTDIR)$(libdir)/$(LIBRARY).$A + -$(DELDIR) $(DESTDIR)$(includedir)/freetype2 + -$(DELETE) $(DESTDIR)$(bindir)/freetype-config + -$(DELETE) $(DESTDIR)$(datadir)/aclocal/freetype2.m4 + -$(DELETE) $(DESTDIR)$(libdir)/pkgconfig/freetype2.pc + -$(DELETE) $(DESTDIR)$(mandir)/man1/freetype-config.1 + + +check: + $(info There is no validation suite for this package.) + + +.PHONY: clean_project_unix distclean_project_unix + +# Unix cleaning and distclean rules. +# +clean_project_unix: + -$(LIBTOOL) --mode=clean $(RM) $(OBJECTS_LIST) + -$(DELETE) $(CLEAN) + +distclean_project_unix: clean_project_unix + -$(LIBTOOL) --mode=clean $(RM) $(PROJECT_LIBRARY) + -$(DELETE) *.orig *~ core *.core $(DISTCLEAN) + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/unix/ltmain.sh b/3rdparty/freetype-2.13.2/builds/unix/ltmain.sh new file mode 100644 index 000000000..2a50d7f6f --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/ltmain.sh @@ -0,0 +1,11436 @@ +#! /usr/bin/env sh +## DO NOT EDIT - This file generated from ./build-aux/ltmain.in +## by inline-source v2019-02-19.15 + +# libtool (GNU libtool) 2.4.7 +# Provide generalized library-building support services. +# Written by Gordon Matzigkeit , 1996 + +# Copyright (C) 1996-2019, 2021-2022 Free Software Foundation, Inc. +# This is free software; see the source for copying conditions. There is NO +# warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + +# GNU Libtool is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# As a special exception to the GNU General Public License, +# if you distribute this file as part of a program or library that +# is built using GNU Libtool, you may include this file under the +# same distribution terms that you use for the rest of that program. +# +# GNU Libtool is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see . + + +PROGRAM=libtool +PACKAGE=libtool +VERSION=2.4.7 +package_revision=2.4.7 + + +## ------ ## +## Usage. ## +## ------ ## + +# Run './libtool --help' for help with using this script from the +# command line. + + +## ------------------------------- ## +## User overridable command paths. ## +## ------------------------------- ## + +# After configure completes, it has a better idea of some of the +# shell tools we need than the defaults used by the functions shared +# with bootstrap, so set those here where they can still be over- +# ridden by the user, but otherwise take precedence. + +: ${AUTOCONF="autoconf"} +: ${AUTOMAKE="automake"} + + +## -------------------------- ## +## Source external libraries. ## +## -------------------------- ## + +# Much of our low-level functionality needs to be sourced from external +# libraries, which are installed to $pkgauxdir. + +# Set a version string for this script. +scriptversion=2019-02-19.15; # UTC + +# General shell script boiler plate, and helper functions. +# Written by Gary V. Vaughan, 2004 + +# This is free software. There is NO warranty; not even for +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. +# +# Copyright (C) 2004-2019, 2021 Bootstrap Authors +# +# This file is dual licensed under the terms of the MIT license +# , and GPL version 2 or later +# . You must apply one of +# these licenses when using or redistributing this software or any of +# the files within it. See the URLs above, or the file `LICENSE` +# included in the Bootstrap distribution for the full license texts. + +# Please report bugs or propose patches to: +# + + +## ------ ## +## Usage. ## +## ------ ## + +# Evaluate this file near the top of your script to gain access to +# the functions and variables defined here: +# +# . `echo "$0" | ${SED-sed} 's|[^/]*$||'`/build-aux/funclib.sh +# +# If you need to override any of the default environment variable +# settings, do that before evaluating this file. + + +## -------------------- ## +## Shell normalisation. ## +## -------------------- ## + +# Some shells need a little help to be as Bourne compatible as possible. +# Before doing anything else, make sure all that help has been provided! + +DUALCASE=1; export DUALCASE # for MKS sh +if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then : + emulate sh + NULLCMD=: + # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which + # is contrary to our usage. Disable this feature. + alias -g '${1+"$@"}'='"$@"' + setopt NO_GLOB_SUBST +else + case `(set -o) 2>/dev/null` in *posix*) set -o posix ;; esac +fi + +# NLS nuisances: We save the old values in case they are required later. +_G_user_locale= +_G_safe_locale= +for _G_var in LANG LANGUAGE LC_ALL LC_CTYPE LC_COLLATE LC_MESSAGES +do + eval "if test set = \"\${$_G_var+set}\"; then + save_$_G_var=\$$_G_var + $_G_var=C + export $_G_var + _G_user_locale=\"$_G_var=\\\$save_\$_G_var; \$_G_user_locale\" + _G_safe_locale=\"$_G_var=C; \$_G_safe_locale\" + fi" +done +# These NLS vars are set unconditionally (bootstrap issue #24). Unset those +# in case the environment reset is needed later and the $save_* variant is not +# defined (see the code above). +LC_ALL=C +LANGUAGE=C +export LANGUAGE LC_ALL + +# Make sure IFS has a sensible default +sp=' ' +nl=' +' +IFS="$sp $nl" + +# There are apparently some retarded systems that use ';' as a PATH separator! +if test "${PATH_SEPARATOR+set}" != set; then + PATH_SEPARATOR=: + (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && { + (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 || + PATH_SEPARATOR=';' + } +fi + + +# func_unset VAR +# -------------- +# Portably unset VAR. +# In some shells, an 'unset VAR' statement leaves a non-zero return +# status if VAR is already unset, which might be problematic if the +# statement is used at the end of a function (thus poisoning its return +# value) or when 'set -e' is active (causing even a spurious abort of +# the script in this case). +func_unset () +{ + { eval $1=; (eval unset $1) >/dev/null 2>&1 && eval unset $1 || : ; } +} + + +# Make sure CDPATH doesn't cause `cd` commands to output the target dir. +func_unset CDPATH + +# Make sure ${,E,F}GREP behave sanely. +func_unset GREP_OPTIONS + + +## ------------------------- ## +## Locate command utilities. ## +## ------------------------- ## + + +# func_executable_p FILE +# ---------------------- +# Check that FILE is an executable regular file. +func_executable_p () +{ + test -f "$1" && test -x "$1" +} + + +# func_path_progs PROGS_LIST CHECK_FUNC [PATH] +# -------------------------------------------- +# Search for either a program that responds to --version with output +# containing "GNU", or else returned by CHECK_FUNC otherwise, by +# trying all the directories in PATH with each of the elements of +# PROGS_LIST. +# +# CHECK_FUNC should accept the path to a candidate program, and +# set $func_check_prog_result if it truncates its output less than +# $_G_path_prog_max characters. +func_path_progs () +{ + _G_progs_list=$1 + _G_check_func=$2 + _G_PATH=${3-"$PATH"} + + _G_path_prog_max=0 + _G_path_prog_found=false + _G_save_IFS=$IFS; IFS=${PATH_SEPARATOR-:} + for _G_dir in $_G_PATH; do + IFS=$_G_save_IFS + test -z "$_G_dir" && _G_dir=. + for _G_prog_name in $_G_progs_list; do + for _exeext in '' .EXE; do + _G_path_prog=$_G_dir/$_G_prog_name$_exeext + func_executable_p "$_G_path_prog" || continue + case `"$_G_path_prog" --version 2>&1` in + *GNU*) func_path_progs_result=$_G_path_prog _G_path_prog_found=: ;; + *) $_G_check_func $_G_path_prog + func_path_progs_result=$func_check_prog_result + ;; + esac + $_G_path_prog_found && break 3 + done + done + done + IFS=$_G_save_IFS + test -z "$func_path_progs_result" && { + echo "no acceptable sed could be found in \$PATH" >&2 + exit 1 + } +} + + +# We want to be able to use the functions in this file before configure +# has figured out where the best binaries are kept, which means we have +# to search for them ourselves - except when the results are already set +# where we skip the searches. + +# Unless the user overrides by setting SED, search the path for either GNU +# sed, or the sed that truncates its output the least. +test -z "$SED" && { + _G_sed_script=s/aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa/bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb/ + for _G_i in 1 2 3 4 5 6 7; do + _G_sed_script=$_G_sed_script$nl$_G_sed_script + done + echo "$_G_sed_script" 2>/dev/null | sed 99q >conftest.sed + _G_sed_script= + + func_check_prog_sed () + { + _G_path_prog=$1 + + _G_count=0 + printf 0123456789 >conftest.in + while : + do + cat conftest.in conftest.in >conftest.tmp + mv conftest.tmp conftest.in + cp conftest.in conftest.nl + echo '' >> conftest.nl + "$_G_path_prog" -f conftest.sed conftest.out 2>/dev/null || break + diff conftest.out conftest.nl >/dev/null 2>&1 || break + _G_count=`expr $_G_count + 1` + if test "$_G_count" -gt "$_G_path_prog_max"; then + # Best one so far, save it but keep looking for a better one + func_check_prog_result=$_G_path_prog + _G_path_prog_max=$_G_count + fi + # 10*(2^10) chars as input seems more than enough + test 10 -lt "$_G_count" && break + done + rm -f conftest.in conftest.tmp conftest.nl conftest.out + } + + func_path_progs "sed gsed" func_check_prog_sed "$PATH:/usr/xpg4/bin" + rm -f conftest.sed + SED=$func_path_progs_result +} + + +# Unless the user overrides by setting GREP, search the path for either GNU +# grep, or the grep that truncates its output the least. +test -z "$GREP" && { + func_check_prog_grep () + { + _G_path_prog=$1 + + _G_count=0 + _G_path_prog_max=0 + printf 0123456789 >conftest.in + while : + do + cat conftest.in conftest.in >conftest.tmp + mv conftest.tmp conftest.in + cp conftest.in conftest.nl + echo 'GREP' >> conftest.nl + "$_G_path_prog" -e 'GREP$' -e '-(cannot match)-' conftest.out 2>/dev/null || break + diff conftest.out conftest.nl >/dev/null 2>&1 || break + _G_count=`expr $_G_count + 1` + if test "$_G_count" -gt "$_G_path_prog_max"; then + # Best one so far, save it but keep looking for a better one + func_check_prog_result=$_G_path_prog + _G_path_prog_max=$_G_count + fi + # 10*(2^10) chars as input seems more than enough + test 10 -lt "$_G_count" && break + done + rm -f conftest.in conftest.tmp conftest.nl conftest.out + } + + func_path_progs "grep ggrep" func_check_prog_grep "$PATH:/usr/xpg4/bin" + GREP=$func_path_progs_result +} + + +## ------------------------------- ## +## User overridable command paths. ## +## ------------------------------- ## + +# All uppercase variable names are used for environment variables. These +# variables can be overridden by the user before calling a script that +# uses them if a suitable command of that name is not already available +# in the command search PATH. + +: ${CP="cp -f"} +: ${ECHO="printf %s\n"} +: ${EGREP="$GREP -E"} +: ${FGREP="$GREP -F"} +: ${LN_S="ln -s"} +: ${MAKE="make"} +: ${MKDIR="mkdir"} +: ${MV="mv -f"} +: ${RM="rm -f"} +: ${SHELL="${CONFIG_SHELL-/bin/sh}"} + + +## -------------------- ## +## Useful sed snippets. ## +## -------------------- ## + +sed_dirname='s|/[^/]*$||' +sed_basename='s|^.*/||' + +# Sed substitution that helps us do robust quoting. It backslashifies +# metacharacters that are still active within double-quoted strings. +sed_quote_subst='s|\([`"$\\]\)|\\\1|g' + +# Same as above, but do not quote variable references. +sed_double_quote_subst='s/\(["`\\]\)/\\\1/g' + +# Sed substitution that turns a string into a regex matching for the +# string literally. +sed_make_literal_regex='s|[].[^$\\*\/]|\\&|g' + +# Sed substitution that converts a w32 file name or path +# that contains forward slashes, into one that contains +# (escaped) backslashes. A very naive implementation. +sed_naive_backslashify='s|\\\\*|\\|g;s|/|\\|g;s|\\|\\\\|g' + +# Re-'\' parameter expansions in output of sed_double_quote_subst that +# were '\'-ed in input to the same. If an odd number of '\' preceded a +# '$' in input to sed_double_quote_subst, that '$' was protected from +# expansion. Since each input '\' is now two '\'s, look for any number +# of runs of four '\'s followed by two '\'s and then a '$'. '\' that '$'. +_G_bs='\\' +_G_bs2='\\\\' +_G_bs4='\\\\\\\\' +_G_dollar='\$' +sed_double_backslash="\ + s/$_G_bs4/&\\ +/g + s/^$_G_bs2$_G_dollar/$_G_bs&/ + s/\\([^$_G_bs]\\)$_G_bs2$_G_dollar/\\1$_G_bs2$_G_bs$_G_dollar/g + s/\n//g" + +# require_check_ifs_backslash +# --------------------------- +# Check if we can use backslash as IFS='\' separator, and set +# $check_ifs_backshlash_broken to ':' or 'false'. +require_check_ifs_backslash=func_require_check_ifs_backslash +func_require_check_ifs_backslash () +{ + _G_save_IFS=$IFS + IFS='\' + _G_check_ifs_backshlash='a\\b' + for _G_i in $_G_check_ifs_backshlash + do + case $_G_i in + a) + check_ifs_backshlash_broken=false + ;; + '') + break + ;; + *) + check_ifs_backshlash_broken=: + break + ;; + esac + done + IFS=$_G_save_IFS + require_check_ifs_backslash=: +} + + +## ----------------- ## +## Global variables. ## +## ----------------- ## + +# Except for the global variables explicitly listed below, the following +# functions in the '^func_' namespace, and the '^require_' namespace +# variables initialised in the 'Resource management' section, sourcing +# this file will not pollute your global namespace with anything +# else. There's no portable way to scope variables in Bourne shell +# though, so actually running these functions will sometimes place +# results into a variable named after the function, and often use +# temporary variables in the '^_G_' namespace. If you are careful to +# avoid using those namespaces casually in your sourcing script, things +# should continue to work as you expect. And, of course, you can freely +# overwrite any of the functions or variables defined here before +# calling anything to customize them. + +EXIT_SUCCESS=0 +EXIT_FAILURE=1 +EXIT_MISMATCH=63 # $? = 63 is used to indicate version mismatch to missing. +EXIT_SKIP=77 # $? = 77 is used to indicate a skipped test to automake. + +# Allow overriding, eg assuming that you follow the convention of +# putting '$debug_cmd' at the start of all your functions, you can get +# bash to show function call trace with: +# +# debug_cmd='eval echo "${FUNCNAME[0]} $*" >&2' bash your-script-name +debug_cmd=${debug_cmd-":"} +exit_cmd=: + +# By convention, finish your script with: +# +# exit $exit_status +# +# so that you can set exit_status to non-zero if you want to indicate +# something went wrong during execution without actually bailing out at +# the point of failure. +exit_status=$EXIT_SUCCESS + +# Work around backward compatibility issue on IRIX 6.5. On IRIX 6.4+, sh +# is ksh but when the shell is invoked as "sh" and the current value of +# the _XPG environment variable is not equal to 1 (one), the special +# positional parameter $0, within a function call, is the name of the +# function. +progpath=$0 + +# The name of this program. +progname=`$ECHO "$progpath" |$SED "$sed_basename"` + +# Make sure we have an absolute progpath for reexecution: +case $progpath in + [\\/]*|[A-Za-z]:\\*) ;; + *[\\/]*) + progdir=`$ECHO "$progpath" |$SED "$sed_dirname"` + progdir=`cd "$progdir" && pwd` + progpath=$progdir/$progname + ;; + *) + _G_IFS=$IFS + IFS=${PATH_SEPARATOR-:} + for progdir in $PATH; do + IFS=$_G_IFS + test -x "$progdir/$progname" && break + done + IFS=$_G_IFS + test -n "$progdir" || progdir=`pwd` + progpath=$progdir/$progname + ;; +esac + + +## ----------------- ## +## Standard options. ## +## ----------------- ## + +# The following options affect the operation of the functions defined +# below, and should be set appropriately depending on run-time para- +# meters passed on the command line. + +opt_dry_run=false +opt_quiet=false +opt_verbose=false + +# Categories 'all' and 'none' are always available. Append any others +# you will pass as the first argument to func_warning from your own +# code. +warning_categories= + +# By default, display warnings according to 'opt_warning_types'. Set +# 'warning_func' to ':' to elide all warnings, or func_fatal_error to +# treat the next displayed warning as a fatal error. +warning_func=func_warn_and_continue + +# Set to 'all' to display all warnings, 'none' to suppress all +# warnings, or a space delimited list of some subset of +# 'warning_categories' to display only the listed warnings. +opt_warning_types=all + + +## -------------------- ## +## Resource management. ## +## -------------------- ## + +# This section contains definitions for functions that each ensure a +# particular resource (a file, or a non-empty configuration variable for +# example) is available, and if appropriate to extract default values +# from pertinent package files. Call them using their associated +# 'require_*' variable to ensure that they are executed, at most, once. +# +# It's entirely deliberate that calling these functions can set +# variables that don't obey the namespace limitations obeyed by the rest +# of this file, in order that that they be as useful as possible to +# callers. + + +# require_term_colors +# ------------------- +# Allow display of bold text on terminals that support it. +require_term_colors=func_require_term_colors +func_require_term_colors () +{ + $debug_cmd + + test -t 1 && { + # COLORTERM and USE_ANSI_COLORS environment variables take + # precedence, because most terminfo databases neglect to describe + # whether color sequences are supported. + test -n "${COLORTERM+set}" && : ${USE_ANSI_COLORS="1"} + + if test 1 = "$USE_ANSI_COLORS"; then + # Standard ANSI escape sequences + tc_reset='' + tc_bold=''; tc_standout='' + tc_red=''; tc_green='' + tc_blue=''; tc_cyan='' + else + # Otherwise trust the terminfo database after all. + test -n "`tput sgr0 2>/dev/null`" && { + tc_reset=`tput sgr0` + test -n "`tput bold 2>/dev/null`" && tc_bold=`tput bold` + tc_standout=$tc_bold + test -n "`tput smso 2>/dev/null`" && tc_standout=`tput smso` + test -n "`tput setaf 1 2>/dev/null`" && tc_red=`tput setaf 1` + test -n "`tput setaf 2 2>/dev/null`" && tc_green=`tput setaf 2` + test -n "`tput setaf 4 2>/dev/null`" && tc_blue=`tput setaf 4` + test -n "`tput setaf 5 2>/dev/null`" && tc_cyan=`tput setaf 5` + } + fi + } + + require_term_colors=: +} + + +## ----------------- ## +## Function library. ## +## ----------------- ## + +# This section contains a variety of useful functions to call in your +# scripts. Take note of the portable wrappers for features provided by +# some modern shells, which will fall back to slower equivalents on +# less featureful shells. + + +# func_append VAR VALUE +# --------------------- +# Append VALUE onto the existing contents of VAR. + + # We should try to minimise forks, especially on Windows where they are + # unreasonably slow, so skip the feature probes when bash or zsh are + # being used: + if test set = "${BASH_VERSION+set}${ZSH_VERSION+set}"; then + : ${_G_HAVE_ARITH_OP="yes"} + : ${_G_HAVE_XSI_OPS="yes"} + # The += operator was introduced in bash 3.1 + case $BASH_VERSION in + [12].* | 3.0 | 3.0*) ;; + *) + : ${_G_HAVE_PLUSEQ_OP="yes"} + ;; + esac + fi + + # _G_HAVE_PLUSEQ_OP + # Can be empty, in which case the shell is probed, "yes" if += is + # useable or anything else if it does not work. + test -z "$_G_HAVE_PLUSEQ_OP" \ + && (eval 'x=a; x+=" b"; test "a b" = "$x"') 2>/dev/null \ + && _G_HAVE_PLUSEQ_OP=yes + +if test yes = "$_G_HAVE_PLUSEQ_OP" +then + # This is an XSI compatible shell, allowing a faster implementation... + eval 'func_append () + { + $debug_cmd + + eval "$1+=\$2" + }' +else + # ...otherwise fall back to using expr, which is often a shell builtin. + func_append () + { + $debug_cmd + + eval "$1=\$$1\$2" + } +fi + + +# func_append_quoted VAR VALUE +# ---------------------------- +# Quote VALUE and append to the end of shell variable VAR, separated +# by a space. +if test yes = "$_G_HAVE_PLUSEQ_OP"; then + eval 'func_append_quoted () + { + $debug_cmd + + func_quote_arg pretty "$2" + eval "$1+=\\ \$func_quote_arg_result" + }' +else + func_append_quoted () + { + $debug_cmd + + func_quote_arg pretty "$2" + eval "$1=\$$1\\ \$func_quote_arg_result" + } +fi + + +# func_append_uniq VAR VALUE +# -------------------------- +# Append unique VALUE onto the existing contents of VAR, assuming +# entries are delimited by the first character of VALUE. For example: +# +# func_append_uniq options " --another-option option-argument" +# +# will only append to $options if " --another-option option-argument " +# is not already present somewhere in $options already (note spaces at +# each end implied by leading space in second argument). +func_append_uniq () +{ + $debug_cmd + + eval _G_current_value='`$ECHO $'$1'`' + _G_delim=`expr "$2" : '\(.\)'` + + case $_G_delim$_G_current_value$_G_delim in + *"$2$_G_delim"*) ;; + *) func_append "$@" ;; + esac +} + + +# func_arith TERM... +# ------------------ +# Set func_arith_result to the result of evaluating TERMs. + test -z "$_G_HAVE_ARITH_OP" \ + && (eval 'test 2 = $(( 1 + 1 ))') 2>/dev/null \ + && _G_HAVE_ARITH_OP=yes + +if test yes = "$_G_HAVE_ARITH_OP"; then + eval 'func_arith () + { + $debug_cmd + + func_arith_result=$(( $* )) + }' +else + func_arith () + { + $debug_cmd + + func_arith_result=`expr "$@"` + } +fi + + +# func_basename FILE +# ------------------ +# Set func_basename_result to FILE with everything up to and including +# the last / stripped. +if test yes = "$_G_HAVE_XSI_OPS"; then + # If this shell supports suffix pattern removal, then use it to avoid + # forking. Hide the definitions single quotes in case the shell chokes + # on unsupported syntax... + _b='func_basename_result=${1##*/}' + _d='case $1 in + */*) func_dirname_result=${1%/*}$2 ;; + * ) func_dirname_result=$3 ;; + esac' + +else + # ...otherwise fall back to using sed. + _b='func_basename_result=`$ECHO "$1" |$SED "$sed_basename"`' + _d='func_dirname_result=`$ECHO "$1" |$SED "$sed_dirname"` + if test "X$func_dirname_result" = "X$1"; then + func_dirname_result=$3 + else + func_append func_dirname_result "$2" + fi' +fi + +eval 'func_basename () +{ + $debug_cmd + + '"$_b"' +}' + + +# func_dirname FILE APPEND NONDIR_REPLACEMENT +# ------------------------------------------- +# Compute the dirname of FILE. If nonempty, add APPEND to the result, +# otherwise set result to NONDIR_REPLACEMENT. +eval 'func_dirname () +{ + $debug_cmd + + '"$_d"' +}' + + +# func_dirname_and_basename FILE APPEND NONDIR_REPLACEMENT +# -------------------------------------------------------- +# Perform func_basename and func_dirname in a single function +# call: +# dirname: Compute the dirname of FILE. If nonempty, +# add APPEND to the result, otherwise set result +# to NONDIR_REPLACEMENT. +# value returned in "$func_dirname_result" +# basename: Compute filename of FILE. +# value retuned in "$func_basename_result" +# For efficiency, we do not delegate to the functions above but instead +# duplicate the functionality here. +eval 'func_dirname_and_basename () +{ + $debug_cmd + + '"$_b"' + '"$_d"' +}' + + +# func_echo ARG... +# ---------------- +# Echo program name prefixed message. +func_echo () +{ + $debug_cmd + + _G_message=$* + + func_echo_IFS=$IFS + IFS=$nl + for _G_line in $_G_message; do + IFS=$func_echo_IFS + $ECHO "$progname: $_G_line" + done + IFS=$func_echo_IFS +} + + +# func_echo_all ARG... +# -------------------- +# Invoke $ECHO with all args, space-separated. +func_echo_all () +{ + $ECHO "$*" +} + + +# func_echo_infix_1 INFIX ARG... +# ------------------------------ +# Echo program name, followed by INFIX on the first line, with any +# additional lines not showing INFIX. +func_echo_infix_1 () +{ + $debug_cmd + + $require_term_colors + + _G_infix=$1; shift + _G_indent=$_G_infix + _G_prefix="$progname: $_G_infix: " + _G_message=$* + + # Strip color escape sequences before counting printable length + for _G_tc in "$tc_reset" "$tc_bold" "$tc_standout" "$tc_red" "$tc_green" "$tc_blue" "$tc_cyan" + do + test -n "$_G_tc" && { + _G_esc_tc=`$ECHO "$_G_tc" | $SED "$sed_make_literal_regex"` + _G_indent=`$ECHO "$_G_indent" | $SED "s|$_G_esc_tc||g"` + } + done + _G_indent="$progname: "`echo "$_G_indent" | $SED 's|.| |g'`" " ## exclude from sc_prohibit_nested_quotes + + func_echo_infix_1_IFS=$IFS + IFS=$nl + for _G_line in $_G_message; do + IFS=$func_echo_infix_1_IFS + $ECHO "$_G_prefix$tc_bold$_G_line$tc_reset" >&2 + _G_prefix=$_G_indent + done + IFS=$func_echo_infix_1_IFS +} + + +# func_error ARG... +# ----------------- +# Echo program name prefixed message to standard error. +func_error () +{ + $debug_cmd + + $require_term_colors + + func_echo_infix_1 " $tc_standout${tc_red}error$tc_reset" "$*" >&2 +} + + +# func_fatal_error ARG... +# ----------------------- +# Echo program name prefixed message to standard error, and exit. +func_fatal_error () +{ + $debug_cmd + + func_error "$*" + exit $EXIT_FAILURE +} + + +# func_grep EXPRESSION FILENAME +# ----------------------------- +# Check whether EXPRESSION matches any line of FILENAME, without output. +func_grep () +{ + $debug_cmd + + $GREP "$1" "$2" >/dev/null 2>&1 +} + + +# func_len STRING +# --------------- +# Set func_len_result to the length of STRING. STRING may not +# start with a hyphen. + test -z "$_G_HAVE_XSI_OPS" \ + && (eval 'x=a/b/c; + test 5aa/bb/cc = "${#x}${x%%/*}${x%/*}${x#*/}${x##*/}"') 2>/dev/null \ + && _G_HAVE_XSI_OPS=yes + +if test yes = "$_G_HAVE_XSI_OPS"; then + eval 'func_len () + { + $debug_cmd + + func_len_result=${#1} + }' +else + func_len () + { + $debug_cmd + + func_len_result=`expr "$1" : ".*" 2>/dev/null || echo $max_cmd_len` + } +fi + + +# func_mkdir_p DIRECTORY-PATH +# --------------------------- +# Make sure the entire path to DIRECTORY-PATH is available. +func_mkdir_p () +{ + $debug_cmd + + _G_directory_path=$1 + _G_dir_list= + + if test -n "$_G_directory_path" && test : != "$opt_dry_run"; then + + # Protect directory names starting with '-' + case $_G_directory_path in + -*) _G_directory_path=./$_G_directory_path ;; + esac + + # While some portion of DIR does not yet exist... + while test ! -d "$_G_directory_path"; do + # ...make a list in topmost first order. Use a colon delimited + # list incase some portion of path contains whitespace. + _G_dir_list=$_G_directory_path:$_G_dir_list + + # If the last portion added has no slash in it, the list is done + case $_G_directory_path in */*) ;; *) break ;; esac + + # ...otherwise throw away the child directory and loop + _G_directory_path=`$ECHO "$_G_directory_path" | $SED -e "$sed_dirname"` + done + _G_dir_list=`$ECHO "$_G_dir_list" | $SED 's|:*$||'` + + func_mkdir_p_IFS=$IFS; IFS=: + for _G_dir in $_G_dir_list; do + IFS=$func_mkdir_p_IFS + # mkdir can fail with a 'File exist' error if two processes + # try to create one of the directories concurrently. Don't + # stop in that case! + $MKDIR "$_G_dir" 2>/dev/null || : + done + IFS=$func_mkdir_p_IFS + + # Bail out if we (or some other process) failed to create a directory. + test -d "$_G_directory_path" || \ + func_fatal_error "Failed to create '$1'" + fi +} + + +# func_mktempdir [BASENAME] +# ------------------------- +# Make a temporary directory that won't clash with other running +# libtool processes, and avoids race conditions if possible. If +# given, BASENAME is the basename for that directory. +func_mktempdir () +{ + $debug_cmd + + _G_template=${TMPDIR-/tmp}/${1-$progname} + + if test : = "$opt_dry_run"; then + # Return a directory name, but don't create it in dry-run mode + _G_tmpdir=$_G_template-$$ + else + + # If mktemp works, use that first and foremost + _G_tmpdir=`mktemp -d "$_G_template-XXXXXXXX" 2>/dev/null` + + if test ! -d "$_G_tmpdir"; then + # Failing that, at least try and use $RANDOM to avoid a race + _G_tmpdir=$_G_template-${RANDOM-0}$$ + + func_mktempdir_umask=`umask` + umask 0077 + $MKDIR "$_G_tmpdir" + umask $func_mktempdir_umask + fi + + # If we're not in dry-run mode, bomb out on failure + test -d "$_G_tmpdir" || \ + func_fatal_error "cannot create temporary directory '$_G_tmpdir'" + fi + + $ECHO "$_G_tmpdir" +} + + +# func_normal_abspath PATH +# ------------------------ +# Remove doubled-up and trailing slashes, "." path components, +# and cancel out any ".." path components in PATH after making +# it an absolute path. +func_normal_abspath () +{ + $debug_cmd + + # These SED scripts presuppose an absolute path with a trailing slash. + _G_pathcar='s|^/\([^/]*\).*$|\1|' + _G_pathcdr='s|^/[^/]*||' + _G_removedotparts=':dotsl + s|/\./|/|g + t dotsl + s|/\.$|/|' + _G_collapseslashes='s|/\{1,\}|/|g' + _G_finalslash='s|/*$|/|' + + # Start from root dir and reassemble the path. + func_normal_abspath_result= + func_normal_abspath_tpath=$1 + func_normal_abspath_altnamespace= + case $func_normal_abspath_tpath in + "") + # Empty path, that just means $cwd. + func_stripname '' '/' "`pwd`" + func_normal_abspath_result=$func_stripname_result + return + ;; + # The next three entries are used to spot a run of precisely + # two leading slashes without using negated character classes; + # we take advantage of case's first-match behaviour. + ///*) + # Unusual form of absolute path, do nothing. + ;; + //*) + # Not necessarily an ordinary path; POSIX reserves leading '//' + # and for example Cygwin uses it to access remote file shares + # over CIFS/SMB, so we conserve a leading double slash if found. + func_normal_abspath_altnamespace=/ + ;; + /*) + # Absolute path, do nothing. + ;; + *) + # Relative path, prepend $cwd. + func_normal_abspath_tpath=`pwd`/$func_normal_abspath_tpath + ;; + esac + + # Cancel out all the simple stuff to save iterations. We also want + # the path to end with a slash for ease of parsing, so make sure + # there is one (and only one) here. + func_normal_abspath_tpath=`$ECHO "$func_normal_abspath_tpath" | $SED \ + -e "$_G_removedotparts" -e "$_G_collapseslashes" -e "$_G_finalslash"` + while :; do + # Processed it all yet? + if test / = "$func_normal_abspath_tpath"; then + # If we ascended to the root using ".." the result may be empty now. + if test -z "$func_normal_abspath_result"; then + func_normal_abspath_result=/ + fi + break + fi + func_normal_abspath_tcomponent=`$ECHO "$func_normal_abspath_tpath" | $SED \ + -e "$_G_pathcar"` + func_normal_abspath_tpath=`$ECHO "$func_normal_abspath_tpath" | $SED \ + -e "$_G_pathcdr"` + # Figure out what to do with it + case $func_normal_abspath_tcomponent in + "") + # Trailing empty path component, ignore it. + ;; + ..) + # Parent dir; strip last assembled component from result. + func_dirname "$func_normal_abspath_result" + func_normal_abspath_result=$func_dirname_result + ;; + *) + # Actual path component, append it. + func_append func_normal_abspath_result "/$func_normal_abspath_tcomponent" + ;; + esac + done + # Restore leading double-slash if one was found on entry. + func_normal_abspath_result=$func_normal_abspath_altnamespace$func_normal_abspath_result +} + + +# func_notquiet ARG... +# -------------------- +# Echo program name prefixed message only when not in quiet mode. +func_notquiet () +{ + $debug_cmd + + $opt_quiet || func_echo ${1+"$@"} + + # A bug in bash halts the script if the last line of a function + # fails when set -e is in force, so we need another command to + # work around that: + : +} + + +# func_relative_path SRCDIR DSTDIR +# -------------------------------- +# Set func_relative_path_result to the relative path from SRCDIR to DSTDIR. +func_relative_path () +{ + $debug_cmd + + func_relative_path_result= + func_normal_abspath "$1" + func_relative_path_tlibdir=$func_normal_abspath_result + func_normal_abspath "$2" + func_relative_path_tbindir=$func_normal_abspath_result + + # Ascend the tree starting from libdir + while :; do + # check if we have found a prefix of bindir + case $func_relative_path_tbindir in + $func_relative_path_tlibdir) + # found an exact match + func_relative_path_tcancelled= + break + ;; + $func_relative_path_tlibdir*) + # found a matching prefix + func_stripname "$func_relative_path_tlibdir" '' "$func_relative_path_tbindir" + func_relative_path_tcancelled=$func_stripname_result + if test -z "$func_relative_path_result"; then + func_relative_path_result=. + fi + break + ;; + *) + func_dirname $func_relative_path_tlibdir + func_relative_path_tlibdir=$func_dirname_result + if test -z "$func_relative_path_tlibdir"; then + # Have to descend all the way to the root! + func_relative_path_result=../$func_relative_path_result + func_relative_path_tcancelled=$func_relative_path_tbindir + break + fi + func_relative_path_result=../$func_relative_path_result + ;; + esac + done + + # Now calculate path; take care to avoid doubling-up slashes. + func_stripname '' '/' "$func_relative_path_result" + func_relative_path_result=$func_stripname_result + func_stripname '/' '/' "$func_relative_path_tcancelled" + if test -n "$func_stripname_result"; then + func_append func_relative_path_result "/$func_stripname_result" + fi + + # Normalisation. If bindir is libdir, return '.' else relative path. + if test -n "$func_relative_path_result"; then + func_stripname './' '' "$func_relative_path_result" + func_relative_path_result=$func_stripname_result + fi + + test -n "$func_relative_path_result" || func_relative_path_result=. + + : +} + + +# func_quote_portable EVAL ARG +# ---------------------------- +# Internal function to portably implement func_quote_arg. Note that we still +# keep attention to performance here so we as much as possible try to avoid +# calling sed binary (so far O(N) complexity as long as func_append is O(1)). +func_quote_portable () +{ + $debug_cmd + + $require_check_ifs_backslash + + func_quote_portable_result=$2 + + # one-time-loop (easy break) + while true + do + if $1; then + func_quote_portable_result=`$ECHO "$2" | $SED \ + -e "$sed_double_quote_subst" -e "$sed_double_backslash"` + break + fi + + # Quote for eval. + case $func_quote_portable_result in + *[\\\`\"\$]*) + # Fallback to sed for $func_check_bs_ifs_broken=:, or when the string + # contains the shell wildcard characters. + case $check_ifs_backshlash_broken$func_quote_portable_result in + :*|*[\[\*\?]*) + func_quote_portable_result=`$ECHO "$func_quote_portable_result" \ + | $SED "$sed_quote_subst"` + break + ;; + esac + + func_quote_portable_old_IFS=$IFS + for _G_char in '\' '`' '"' '$' + do + # STATE($1) PREV($2) SEPARATOR($3) + set start "" "" + func_quote_portable_result=dummy"$_G_char$func_quote_portable_result$_G_char"dummy + IFS=$_G_char + for _G_part in $func_quote_portable_result + do + case $1 in + quote) + func_append func_quote_portable_result "$3$2" + set quote "$_G_part" "\\$_G_char" + ;; + start) + set first "" "" + func_quote_portable_result= + ;; + first) + set quote "$_G_part" "" + ;; + esac + done + done + IFS=$func_quote_portable_old_IFS + ;; + *) ;; + esac + break + done + + func_quote_portable_unquoted_result=$func_quote_portable_result + case $func_quote_portable_result in + # double-quote args containing shell metacharacters to delay + # word splitting, command substitution and variable expansion + # for a subsequent eval. + # many bourne shells cannot handle close brackets correctly + # in scan sets, so we specify it separately. + *[\[\~\#\^\&\*\(\)\{\}\|\;\<\>\?\'\ \ ]*|*]*|"") + func_quote_portable_result=\"$func_quote_portable_result\" + ;; + esac +} + + +# func_quotefast_eval ARG +# ----------------------- +# Quote one ARG (internal). This is equivalent to 'func_quote_arg eval ARG', +# but optimized for speed. Result is stored in $func_quotefast_eval. +if test xyes = `(x=; printf -v x %q yes; echo x"$x") 2>/dev/null`; then + printf -v _GL_test_printf_tilde %q '~' + if test '\~' = "$_GL_test_printf_tilde"; then + func_quotefast_eval () + { + printf -v func_quotefast_eval_result %q "$1" + } + else + # Broken older Bash implementations. Make those faster too if possible. + func_quotefast_eval () + { + case $1 in + '~'*) + func_quote_portable false "$1" + func_quotefast_eval_result=$func_quote_portable_result + ;; + *) + printf -v func_quotefast_eval_result %q "$1" + ;; + esac + } + fi +else + func_quotefast_eval () + { + func_quote_portable false "$1" + func_quotefast_eval_result=$func_quote_portable_result + } +fi + + +# func_quote_arg MODEs ARG +# ------------------------ +# Quote one ARG to be evaled later. MODEs argument may contain zero or more +# specifiers listed below separated by ',' character. This function returns two +# values: +# i) func_quote_arg_result +# double-quoted (when needed), suitable for a subsequent eval +# ii) func_quote_arg_unquoted_result +# has all characters that are still active within double +# quotes backslashified. Available only if 'unquoted' is specified. +# +# Available modes: +# ---------------- +# 'eval' (default) +# - escape shell special characters +# 'expand' +# - the same as 'eval'; but do not quote variable references +# 'pretty' +# - request aesthetic output, i.e. '"a b"' instead of 'a\ b'. This might +# be used later in func_quote to get output like: 'echo "a b"' instead +# of 'echo a\ b'. This is slower than default on some shells. +# 'unquoted' +# - produce also $func_quote_arg_unquoted_result which does not contain +# wrapping double-quotes. +# +# Examples for 'func_quote_arg pretty,unquoted string': +# +# string | *_result | *_unquoted_result +# ------------+-----------------------+------------------- +# " | \" | \" +# a b | "a b" | a b +# "a b" | "\"a b\"" | \"a b\" +# * | "*" | * +# z="${x-$y}" | "z=\"\${x-\$y}\"" | z=\"\${x-\$y}\" +# +# Examples for 'func_quote_arg pretty,unquoted,expand string': +# +# string | *_result | *_unquoted_result +# --------------+---------------------+-------------------- +# z="${x-$y}" | "z=\"${x-$y}\"" | z=\"${x-$y}\" +func_quote_arg () +{ + _G_quote_expand=false + case ,$1, in + *,expand,*) + _G_quote_expand=: + ;; + esac + + case ,$1, in + *,pretty,*|*,expand,*|*,unquoted,*) + func_quote_portable $_G_quote_expand "$2" + func_quote_arg_result=$func_quote_portable_result + func_quote_arg_unquoted_result=$func_quote_portable_unquoted_result + ;; + *) + # Faster quote-for-eval for some shells. + func_quotefast_eval "$2" + func_quote_arg_result=$func_quotefast_eval_result + ;; + esac +} + + +# func_quote MODEs ARGs... +# ------------------------ +# Quote all ARGs to be evaled later and join them into single command. See +# func_quote_arg's description for more info. +func_quote () +{ + $debug_cmd + _G_func_quote_mode=$1 ; shift + func_quote_result= + while test 0 -lt $#; do + func_quote_arg "$_G_func_quote_mode" "$1" + if test -n "$func_quote_result"; then + func_append func_quote_result " $func_quote_arg_result" + else + func_append func_quote_result "$func_quote_arg_result" + fi + shift + done +} + + +# func_stripname PREFIX SUFFIX NAME +# --------------------------------- +# strip PREFIX and SUFFIX from NAME, and store in func_stripname_result. +# PREFIX and SUFFIX must not contain globbing or regex special +# characters, hashes, percent signs, but SUFFIX may contain a leading +# dot (in which case that matches only a dot). +if test yes = "$_G_HAVE_XSI_OPS"; then + eval 'func_stripname () + { + $debug_cmd + + # pdksh 5.2.14 does not do ${X%$Y} correctly if both X and Y are + # positional parameters, so assign one to ordinary variable first. + func_stripname_result=$3 + func_stripname_result=${func_stripname_result#"$1"} + func_stripname_result=${func_stripname_result%"$2"} + }' +else + func_stripname () + { + $debug_cmd + + case $2 in + .*) func_stripname_result=`$ECHO "$3" | $SED -e "s%^$1%%" -e "s%\\\\$2\$%%"`;; + *) func_stripname_result=`$ECHO "$3" | $SED -e "s%^$1%%" -e "s%$2\$%%"`;; + esac + } +fi + + +# func_show_eval CMD [FAIL_EXP] +# ----------------------------- +# Unless opt_quiet is true, then output CMD. Then, if opt_dryrun is +# not true, evaluate CMD. If the evaluation of CMD fails, and FAIL_EXP +# is given, then evaluate it. +func_show_eval () +{ + $debug_cmd + + _G_cmd=$1 + _G_fail_exp=${2-':'} + + func_quote_arg pretty,expand "$_G_cmd" + eval "func_notquiet $func_quote_arg_result" + + $opt_dry_run || { + eval "$_G_cmd" + _G_status=$? + if test 0 -ne "$_G_status"; then + eval "(exit $_G_status); $_G_fail_exp" + fi + } +} + + +# func_show_eval_locale CMD [FAIL_EXP] +# ------------------------------------ +# Unless opt_quiet is true, then output CMD. Then, if opt_dryrun is +# not true, evaluate CMD. If the evaluation of CMD fails, and FAIL_EXP +# is given, then evaluate it. Use the saved locale for evaluation. +func_show_eval_locale () +{ + $debug_cmd + + _G_cmd=$1 + _G_fail_exp=${2-':'} + + $opt_quiet || { + func_quote_arg expand,pretty "$_G_cmd" + eval "func_echo $func_quote_arg_result" + } + + $opt_dry_run || { + eval "$_G_user_locale + $_G_cmd" + _G_status=$? + eval "$_G_safe_locale" + if test 0 -ne "$_G_status"; then + eval "(exit $_G_status); $_G_fail_exp" + fi + } +} + + +# func_tr_sh +# ---------- +# Turn $1 into a string suitable for a shell variable name. +# Result is stored in $func_tr_sh_result. All characters +# not in the set a-zA-Z0-9_ are replaced with '_'. Further, +# if $1 begins with a digit, a '_' is prepended as well. +func_tr_sh () +{ + $debug_cmd + + case $1 in + [0-9]* | *[!a-zA-Z0-9_]*) + func_tr_sh_result=`$ECHO "$1" | $SED -e 's/^\([0-9]\)/_\1/' -e 's/[^a-zA-Z0-9_]/_/g'` + ;; + * ) + func_tr_sh_result=$1 + ;; + esac +} + + +# func_verbose ARG... +# ------------------- +# Echo program name prefixed message in verbose mode only. +func_verbose () +{ + $debug_cmd + + $opt_verbose && func_echo "$*" + + : +} + + +# func_warn_and_continue ARG... +# ----------------------------- +# Echo program name prefixed warning message to standard error. +func_warn_and_continue () +{ + $debug_cmd + + $require_term_colors + + func_echo_infix_1 "${tc_red}warning$tc_reset" "$*" >&2 +} + + +# func_warning CATEGORY ARG... +# ---------------------------- +# Echo program name prefixed warning message to standard error. Warning +# messages can be filtered according to CATEGORY, where this function +# elides messages where CATEGORY is not listed in the global variable +# 'opt_warning_types'. +func_warning () +{ + $debug_cmd + + # CATEGORY must be in the warning_categories list! + case " $warning_categories " in + *" $1 "*) ;; + *) func_internal_error "invalid warning category '$1'" ;; + esac + + _G_category=$1 + shift + + case " $opt_warning_types " in + *" $_G_category "*) $warning_func ${1+"$@"} ;; + esac +} + + +# func_sort_ver VER1 VER2 +# ----------------------- +# 'sort -V' is not generally available. +# Note this deviates from the version comparison in automake +# in that it treats 1.5 < 1.5.0, and treats 1.4.4a < 1.4-p3a +# but this should suffice as we won't be specifying old +# version formats or redundant trailing .0 in bootstrap.conf. +# If we did want full compatibility then we should probably +# use m4_version_compare from autoconf. +func_sort_ver () +{ + $debug_cmd + + printf '%s\n%s\n' "$1" "$2" \ + | sort -t. -k 1,1n -k 2,2n -k 3,3n -k 4,4n -k 5,5n -k 6,6n -k 7,7n -k 8,8n -k 9,9n +} + +# func_lt_ver PREV CURR +# --------------------- +# Return true if PREV and CURR are in the correct order according to +# func_sort_ver, otherwise false. Use it like this: +# +# func_lt_ver "$prev_ver" "$proposed_ver" || func_fatal_error "..." +func_lt_ver () +{ + $debug_cmd + + test "x$1" = x`func_sort_ver "$1" "$2" | $SED 1q` +} + + +# Local variables: +# mode: shell-script +# sh-indentation: 2 +# eval: (add-hook 'before-save-hook 'time-stamp) +# time-stamp-pattern: "10/scriptversion=%:y-%02m-%02d.%02H; # UTC" +# time-stamp-time-zone: "UTC" +# End: +#! /bin/sh + +# A portable, pluggable option parser for Bourne shell. +# Written by Gary V. Vaughan, 2010 + +# This is free software. There is NO warranty; not even for +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. +# +# Copyright (C) 2010-2019, 2021 Bootstrap Authors +# +# This file is dual licensed under the terms of the MIT license +# , and GPL version 2 or later +# . You must apply one of +# these licenses when using or redistributing this software or any of +# the files within it. See the URLs above, or the file `LICENSE` +# included in the Bootstrap distribution for the full license texts. + +# Please report bugs or propose patches to: +# + +# Set a version string for this script. +scriptversion=2019-02-19.15; # UTC + + +## ------ ## +## Usage. ## +## ------ ## + +# This file is a library for parsing options in your shell scripts along +# with assorted other useful supporting features that you can make use +# of too. +# +# For the simplest scripts you might need only: +# +# #!/bin/sh +# . relative/path/to/funclib.sh +# . relative/path/to/options-parser +# scriptversion=1.0 +# func_options ${1+"$@"} +# eval set dummy "$func_options_result"; shift +# ...rest of your script... +# +# In order for the '--version' option to work, you will need to have a +# suitably formatted comment like the one at the top of this file +# starting with '# Written by ' and ending with '# Copyright'. +# +# For '-h' and '--help' to work, you will also need a one line +# description of your script's purpose in a comment directly above the +# '# Written by ' line, like the one at the top of this file. +# +# The default options also support '--debug', which will turn on shell +# execution tracing (see the comment above debug_cmd below for another +# use), and '--verbose' and the func_verbose function to allow your script +# to display verbose messages only when your user has specified +# '--verbose'. +# +# After sourcing this file, you can plug in processing for additional +# options by amending the variables from the 'Configuration' section +# below, and following the instructions in the 'Option parsing' +# section further down. + +## -------------- ## +## Configuration. ## +## -------------- ## + +# You should override these variables in your script after sourcing this +# file so that they reflect the customisations you have added to the +# option parser. + +# The usage line for option parsing errors and the start of '-h' and +# '--help' output messages. You can embed shell variables for delayed +# expansion at the time the message is displayed, but you will need to +# quote other shell meta-characters carefully to prevent them being +# expanded when the contents are evaled. +usage='$progpath [OPTION]...' + +# Short help message in response to '-h' and '--help'. Add to this or +# override it after sourcing this library to reflect the full set of +# options your script accepts. +usage_message="\ + --debug enable verbose shell tracing + -W, --warnings=CATEGORY + report the warnings falling in CATEGORY [all] + -v, --verbose verbosely report processing + --version print version information and exit + -h, --help print short or long help message and exit +" + +# Additional text appended to 'usage_message' in response to '--help'. +long_help_message=" +Warning categories include: + 'all' show all warnings + 'none' turn off all the warnings + 'error' warnings are treated as fatal errors" + +# Help message printed before fatal option parsing errors. +fatal_help="Try '\$progname --help' for more information." + + + +## ------------------------- ## +## Hook function management. ## +## ------------------------- ## + +# This section contains functions for adding, removing, and running hooks +# in the main code. A hook is just a list of function names that can be +# run in order later on. + +# func_hookable FUNC_NAME +# ----------------------- +# Declare that FUNC_NAME will run hooks added with +# 'func_add_hook FUNC_NAME ...'. +func_hookable () +{ + $debug_cmd + + func_append hookable_fns " $1" +} + + +# func_add_hook FUNC_NAME HOOK_FUNC +# --------------------------------- +# Request that FUNC_NAME call HOOK_FUNC before it returns. FUNC_NAME must +# first have been declared "hookable" by a call to 'func_hookable'. +func_add_hook () +{ + $debug_cmd + + case " $hookable_fns " in + *" $1 "*) ;; + *) func_fatal_error "'$1' does not accept hook functions." ;; + esac + + eval func_append ${1}_hooks '" $2"' +} + + +# func_remove_hook FUNC_NAME HOOK_FUNC +# ------------------------------------ +# Remove HOOK_FUNC from the list of hook functions to be called by +# FUNC_NAME. +func_remove_hook () +{ + $debug_cmd + + eval ${1}_hooks='`$ECHO "\$'$1'_hooks" |$SED "s| '$2'||"`' +} + + +# func_propagate_result FUNC_NAME_A FUNC_NAME_B +# --------------------------------------------- +# If the *_result variable of FUNC_NAME_A _is set_, assign its value to +# *_result variable of FUNC_NAME_B. +func_propagate_result () +{ + $debug_cmd + + func_propagate_result_result=: + if eval "test \"\${${1}_result+set}\" = set" + then + eval "${2}_result=\$${1}_result" + else + func_propagate_result_result=false + fi +} + + +# func_run_hooks FUNC_NAME [ARG]... +# --------------------------------- +# Run all hook functions registered to FUNC_NAME. +# It's assumed that the list of hook functions contains nothing more +# than a whitespace-delimited list of legal shell function names, and +# no effort is wasted trying to catch shell meta-characters or preserve +# whitespace. +func_run_hooks () +{ + $debug_cmd + + case " $hookable_fns " in + *" $1 "*) ;; + *) func_fatal_error "'$1' does not support hook functions." ;; + esac + + eval _G_hook_fns=\$$1_hooks; shift + + for _G_hook in $_G_hook_fns; do + func_unset "${_G_hook}_result" + eval $_G_hook '${1+"$@"}' + func_propagate_result $_G_hook func_run_hooks + if $func_propagate_result_result; then + eval set dummy "$func_run_hooks_result"; shift + fi + done +} + + + +## --------------- ## +## Option parsing. ## +## --------------- ## + +# In order to add your own option parsing hooks, you must accept the +# full positional parameter list from your hook function. You may remove +# or edit any options that you action, and then pass back the remaining +# unprocessed options in '_result', escaped +# suitably for 'eval'. +# +# The '_result' variable is automatically unset +# before your hook gets called; for best performance, only set the +# *_result variable when necessary (i.e. don't call the 'func_quote' +# function unnecessarily because it can be an expensive operation on some +# machines). +# +# Like this: +# +# my_options_prep () +# { +# $debug_cmd +# +# # Extend the existing usage message. +# usage_message=$usage_message' +# -s, --silent don'\''t print informational messages +# ' +# # No change in '$@' (ignored completely by this hook). Leave +# # my_options_prep_result variable intact. +# } +# func_add_hook func_options_prep my_options_prep +# +# +# my_silent_option () +# { +# $debug_cmd +# +# args_changed=false +# +# # Note that, for efficiency, we parse as many options as we can +# # recognise in a loop before passing the remainder back to the +# # caller on the first unrecognised argument we encounter. +# while test $# -gt 0; do +# opt=$1; shift +# case $opt in +# --silent|-s) opt_silent=: +# args_changed=: +# ;; +# # Separate non-argument short options: +# -s*) func_split_short_opt "$_G_opt" +# set dummy "$func_split_short_opt_name" \ +# "-$func_split_short_opt_arg" ${1+"$@"} +# shift +# args_changed=: +# ;; +# *) # Make sure the first unrecognised option "$_G_opt" +# # is added back to "$@" in case we need it later, +# # if $args_changed was set to 'true'. +# set dummy "$_G_opt" ${1+"$@"}; shift; break ;; +# esac +# done +# +# # Only call 'func_quote' here if we processed at least one argument. +# if $args_changed; then +# func_quote eval ${1+"$@"} +# my_silent_option_result=$func_quote_result +# fi +# } +# func_add_hook func_parse_options my_silent_option +# +# +# my_option_validation () +# { +# $debug_cmd +# +# $opt_silent && $opt_verbose && func_fatal_help "\ +# '--silent' and '--verbose' options are mutually exclusive." +# } +# func_add_hook func_validate_options my_option_validation +# +# You'll also need to manually amend $usage_message to reflect the extra +# options you parse. It's preferable to append if you can, so that +# multiple option parsing hooks can be added safely. + + +# func_options_finish [ARG]... +# ---------------------------- +# Finishing the option parse loop (call 'func_options' hooks ATM). +func_options_finish () +{ + $debug_cmd + + func_run_hooks func_options ${1+"$@"} + func_propagate_result func_run_hooks func_options_finish +} + + +# func_options [ARG]... +# --------------------- +# All the functions called inside func_options are hookable. See the +# individual implementations for details. +func_hookable func_options +func_options () +{ + $debug_cmd + + _G_options_quoted=false + + for my_func in options_prep parse_options validate_options options_finish + do + func_unset func_${my_func}_result + func_unset func_run_hooks_result + eval func_$my_func '${1+"$@"}' + func_propagate_result func_$my_func func_options + if $func_propagate_result_result; then + eval set dummy "$func_options_result"; shift + _G_options_quoted=: + fi + done + + $_G_options_quoted || { + # As we (func_options) are top-level options-parser function and + # nobody quoted "$@" for us yet, we need to do it explicitly for + # caller. + func_quote eval ${1+"$@"} + func_options_result=$func_quote_result + } +} + + +# func_options_prep [ARG]... +# -------------------------- +# All initialisations required before starting the option parse loop. +# Note that when calling hook functions, we pass through the list of +# positional parameters. If a hook function modifies that list, and +# needs to propagate that back to rest of this script, then the complete +# modified list must be put in 'func_run_hooks_result' before returning. +func_hookable func_options_prep +func_options_prep () +{ + $debug_cmd + + # Option defaults: + opt_verbose=false + opt_warning_types= + + func_run_hooks func_options_prep ${1+"$@"} + func_propagate_result func_run_hooks func_options_prep +} + + +# func_parse_options [ARG]... +# --------------------------- +# The main option parsing loop. +func_hookable func_parse_options +func_parse_options () +{ + $debug_cmd + + _G_parse_options_requote=false + # this just eases exit handling + while test $# -gt 0; do + # Defer to hook functions for initial option parsing, so they + # get priority in the event of reusing an option name. + func_run_hooks func_parse_options ${1+"$@"} + func_propagate_result func_run_hooks func_parse_options + if $func_propagate_result_result; then + eval set dummy "$func_parse_options_result"; shift + # Even though we may have changed "$@", we passed the "$@" array + # down into the hook and it quoted it for us (because we are in + # this if-branch). No need to quote it again. + _G_parse_options_requote=false + fi + + # Break out of the loop if we already parsed every option. + test $# -gt 0 || break + + # We expect that one of the options parsed in this function matches + # and thus we remove _G_opt from "$@" and need to re-quote. + _G_match_parse_options=: + _G_opt=$1 + shift + case $_G_opt in + --debug|-x) debug_cmd='set -x' + func_echo "enabling shell trace mode" >&2 + $debug_cmd + ;; + + --no-warnings|--no-warning|--no-warn) + set dummy --warnings none ${1+"$@"} + shift + ;; + + --warnings|--warning|-W) + if test $# = 0 && func_missing_arg $_G_opt; then + _G_parse_options_requote=: + break + fi + case " $warning_categories $1" in + *" $1 "*) + # trailing space prevents matching last $1 above + func_append_uniq opt_warning_types " $1" + ;; + *all) + opt_warning_types=$warning_categories + ;; + *none) + opt_warning_types=none + warning_func=: + ;; + *error) + opt_warning_types=$warning_categories + warning_func=func_fatal_error + ;; + *) + func_fatal_error \ + "unsupported warning category: '$1'" + ;; + esac + shift + ;; + + --verbose|-v) opt_verbose=: ;; + --version) func_version ;; + -\?|-h) func_usage ;; + --help) func_help ;; + + # Separate optargs to long options (plugins may need this): + --*=*) func_split_equals "$_G_opt" + set dummy "$func_split_equals_lhs" \ + "$func_split_equals_rhs" ${1+"$@"} + shift + ;; + + # Separate optargs to short options: + -W*) + func_split_short_opt "$_G_opt" + set dummy "$func_split_short_opt_name" \ + "$func_split_short_opt_arg" ${1+"$@"} + shift + ;; + + # Separate non-argument short options: + -\?*|-h*|-v*|-x*) + func_split_short_opt "$_G_opt" + set dummy "$func_split_short_opt_name" \ + "-$func_split_short_opt_arg" ${1+"$@"} + shift + ;; + + --) _G_parse_options_requote=: ; break ;; + -*) func_fatal_help "unrecognised option: '$_G_opt'" ;; + *) set dummy "$_G_opt" ${1+"$@"}; shift + _G_match_parse_options=false + break + ;; + esac + + if $_G_match_parse_options; then + _G_parse_options_requote=: + fi + done + + if $_G_parse_options_requote; then + # save modified positional parameters for caller + func_quote eval ${1+"$@"} + func_parse_options_result=$func_quote_result + fi +} + + +# func_validate_options [ARG]... +# ------------------------------ +# Perform any sanity checks on option settings and/or unconsumed +# arguments. +func_hookable func_validate_options +func_validate_options () +{ + $debug_cmd + + # Display all warnings if -W was not given. + test -n "$opt_warning_types" || opt_warning_types=" $warning_categories" + + func_run_hooks func_validate_options ${1+"$@"} + func_propagate_result func_run_hooks func_validate_options + + # Bail if the options were screwed! + $exit_cmd $EXIT_FAILURE +} + + + +## ----------------- ## +## Helper functions. ## +## ----------------- ## + +# This section contains the helper functions used by the rest of the +# hookable option parser framework in ascii-betical order. + + +# func_fatal_help ARG... +# ---------------------- +# Echo program name prefixed message to standard error, followed by +# a help hint, and exit. +func_fatal_help () +{ + $debug_cmd + + eval \$ECHO \""Usage: $usage"\" + eval \$ECHO \""$fatal_help"\" + func_error ${1+"$@"} + exit $EXIT_FAILURE +} + + +# func_help +# --------- +# Echo long help message to standard output and exit. +func_help () +{ + $debug_cmd + + func_usage_message + $ECHO "$long_help_message" + exit 0 +} + + +# func_missing_arg ARGNAME +# ------------------------ +# Echo program name prefixed message to standard error and set global +# exit_cmd. +func_missing_arg () +{ + $debug_cmd + + func_error "Missing argument for '$1'." + exit_cmd=exit +} + + +# func_split_equals STRING +# ------------------------ +# Set func_split_equals_lhs and func_split_equals_rhs shell variables +# after splitting STRING at the '=' sign. +test -z "$_G_HAVE_XSI_OPS" \ + && (eval 'x=a/b/c; + test 5aa/bb/cc = "${#x}${x%%/*}${x%/*}${x#*/}${x##*/}"') 2>/dev/null \ + && _G_HAVE_XSI_OPS=yes + +if test yes = "$_G_HAVE_XSI_OPS" +then + # This is an XSI compatible shell, allowing a faster implementation... + eval 'func_split_equals () + { + $debug_cmd + + func_split_equals_lhs=${1%%=*} + func_split_equals_rhs=${1#*=} + if test "x$func_split_equals_lhs" = "x$1"; then + func_split_equals_rhs= + fi + }' +else + # ...otherwise fall back to using expr, which is often a shell builtin. + func_split_equals () + { + $debug_cmd + + func_split_equals_lhs=`expr "x$1" : 'x\([^=]*\)'` + func_split_equals_rhs= + test "x$func_split_equals_lhs=" = "x$1" \ + || func_split_equals_rhs=`expr "x$1" : 'x[^=]*=\(.*\)$'` + } +fi #func_split_equals + + +# func_split_short_opt SHORTOPT +# ----------------------------- +# Set func_split_short_opt_name and func_split_short_opt_arg shell +# variables after splitting SHORTOPT after the 2nd character. +if test yes = "$_G_HAVE_XSI_OPS" +then + # This is an XSI compatible shell, allowing a faster implementation... + eval 'func_split_short_opt () + { + $debug_cmd + + func_split_short_opt_arg=${1#??} + func_split_short_opt_name=${1%"$func_split_short_opt_arg"} + }' +else + # ...otherwise fall back to using expr, which is often a shell builtin. + func_split_short_opt () + { + $debug_cmd + + func_split_short_opt_name=`expr "x$1" : 'x\(-.\)'` + func_split_short_opt_arg=`expr "x$1" : 'x-.\(.*\)$'` + } +fi #func_split_short_opt + + +# func_usage +# ---------- +# Echo short help message to standard output and exit. +func_usage () +{ + $debug_cmd + + func_usage_message + $ECHO "Run '$progname --help |${PAGER-more}' for full usage" + exit 0 +} + + +# func_usage_message +# ------------------ +# Echo short help message to standard output. +func_usage_message () +{ + $debug_cmd + + eval \$ECHO \""Usage: $usage"\" + echo + $SED -n 's|^# || + /^Written by/{ + x;p;x + } + h + /^Written by/q' < "$progpath" + echo + eval \$ECHO \""$usage_message"\" +} + + +# func_version +# ------------ +# Echo version message to standard output and exit. +# The version message is extracted from the calling file's header +# comments, with leading '# ' stripped: +# 1. First display the progname and version +# 2. Followed by the header comment line matching /^# Written by / +# 3. Then a blank line followed by the first following line matching +# /^# Copyright / +# 4. Immediately followed by any lines between the previous matches, +# except lines preceding the intervening completely blank line. +# For example, see the header comments of this file. +func_version () +{ + $debug_cmd + + printf '%s\n' "$progname $scriptversion" + $SED -n ' + /^# Written by /!b + s|^# ||; p; n + + :fwd2blnk + /./ { + n + b fwd2blnk + } + p; n + + :holdwrnt + s|^# || + s|^# *$|| + /^Copyright /!{ + /./H + n + b holdwrnt + } + + s|\((C)\)[ 0-9,-]*[ ,-]\([1-9][0-9]* \)|\1 \2| + G + s|\(\n\)\n*|\1|g + p; q' < "$progpath" + + exit $? +} + + +# Local variables: +# mode: shell-script +# sh-indentation: 2 +# eval: (add-hook 'before-save-hook 'time-stamp) +# time-stamp-pattern: "30/scriptversion=%:y-%02m-%02d.%02H; # UTC" +# time-stamp-time-zone: "UTC" +# End: + +# Set a version string. +scriptversion='(GNU libtool) 2.4.7' + + +# func_echo ARG... +# ---------------- +# Libtool also displays the current mode in messages, so override +# funclib.sh func_echo with this custom definition. +func_echo () +{ + $debug_cmd + + _G_message=$* + + func_echo_IFS=$IFS + IFS=$nl + for _G_line in $_G_message; do + IFS=$func_echo_IFS + $ECHO "$progname${opt_mode+: $opt_mode}: $_G_line" + done + IFS=$func_echo_IFS +} + + +# func_warning ARG... +# ------------------- +# Libtool warnings are not categorized, so override funclib.sh +# func_warning with this simpler definition. +func_warning () +{ + $debug_cmd + + $warning_func ${1+"$@"} +} + + +## ---------------- ## +## Options parsing. ## +## ---------------- ## + +# Hook in the functions to make sure our own options are parsed during +# the option parsing loop. + +usage='$progpath [OPTION]... [MODE-ARG]...' + +# Short help message in response to '-h'. +usage_message="Options: + --config show all configuration variables + --debug enable verbose shell tracing + -n, --dry-run display commands without modifying any files + --features display basic configuration information and exit + --mode=MODE use operation mode MODE + --no-warnings equivalent to '-Wnone' + --preserve-dup-deps don't remove duplicate dependency libraries + --quiet, --silent don't print informational messages + --tag=TAG use configuration variables from tag TAG + -v, --verbose print more informational messages than default + --version print version information + -W, --warnings=CATEGORY report the warnings falling in CATEGORY [all] + -h, --help, --help-all print short, long, or detailed help message +" + +# Additional text appended to 'usage_message' in response to '--help'. +func_help () +{ + $debug_cmd + + func_usage_message + $ECHO "$long_help_message + +MODE must be one of the following: + + clean remove files from the build directory + compile compile a source file into a libtool object + execute automatically set library path, then run a program + finish complete the installation of libtool libraries + install install libraries or executables + link create a library or an executable + uninstall remove libraries from an installed directory + +MODE-ARGS vary depending on the MODE. When passed as first option, +'--mode=MODE' may be abbreviated as 'MODE' or a unique abbreviation of that. +Try '$progname --help --mode=MODE' for a more detailed description of MODE. + +When reporting a bug, please describe a test case to reproduce it and +include the following information: + + host-triplet: $host + shell: $SHELL + compiler: $LTCC + compiler flags: $LTCFLAGS + linker: $LD (gnu? $with_gnu_ld) + version: $progname (GNU libtool) 2.4.7 + automake: `($AUTOMAKE --version) 2>/dev/null |$SED 1q` + autoconf: `($AUTOCONF --version) 2>/dev/null |$SED 1q` + +Report bugs to . +GNU libtool home page: . +General help using GNU software: ." + exit 0 +} + + +# func_lo2o OBJECT-NAME +# --------------------- +# Transform OBJECT-NAME from a '.lo' suffix to the platform specific +# object suffix. + +lo2o=s/\\.lo\$/.$objext/ +o2lo=s/\\.$objext\$/.lo/ + +if test yes = "$_G_HAVE_XSI_OPS"; then + eval 'func_lo2o () + { + case $1 in + *.lo) func_lo2o_result=${1%.lo}.$objext ;; + * ) func_lo2o_result=$1 ;; + esac + }' + + # func_xform LIBOBJ-OR-SOURCE + # --------------------------- + # Transform LIBOBJ-OR-SOURCE from a '.o' or '.c' (or otherwise) + # suffix to a '.lo' libtool-object suffix. + eval 'func_xform () + { + func_xform_result=${1%.*}.lo + }' +else + # ...otherwise fall back to using sed. + func_lo2o () + { + func_lo2o_result=`$ECHO "$1" | $SED "$lo2o"` + } + + func_xform () + { + func_xform_result=`$ECHO "$1" | $SED 's|\.[^.]*$|.lo|'` + } +fi + + +# func_fatal_configuration ARG... +# ------------------------------- +# Echo program name prefixed message to standard error, followed by +# a configuration failure hint, and exit. +func_fatal_configuration () +{ + func_fatal_error ${1+"$@"} \ + "See the $PACKAGE documentation for more information." \ + "Fatal configuration error." +} + + +# func_config +# ----------- +# Display the configuration for all the tags in this script. +func_config () +{ + re_begincf='^# ### BEGIN LIBTOOL' + re_endcf='^# ### END LIBTOOL' + + # Default configuration. + $SED "1,/$re_begincf CONFIG/d;/$re_endcf CONFIG/,\$d" < "$progpath" + + # Now print the configurations for the tags. + for tagname in $taglist; do + $SED -n "/$re_begincf TAG CONFIG: $tagname\$/,/$re_endcf TAG CONFIG: $tagname\$/p" < "$progpath" + done + + exit $? +} + + +# func_features +# ------------- +# Display the features supported by this script. +func_features () +{ + echo "host: $host" + if test yes = "$build_libtool_libs"; then + echo "enable shared libraries" + else + echo "disable shared libraries" + fi + if test yes = "$build_old_libs"; then + echo "enable static libraries" + else + echo "disable static libraries" + fi + + exit $? +} + + +# func_enable_tag TAGNAME +# ----------------------- +# Verify that TAGNAME is valid, and either flag an error and exit, or +# enable the TAGNAME tag. We also add TAGNAME to the global $taglist +# variable here. +func_enable_tag () +{ + # Global variable: + tagname=$1 + + re_begincf="^# ### BEGIN LIBTOOL TAG CONFIG: $tagname\$" + re_endcf="^# ### END LIBTOOL TAG CONFIG: $tagname\$" + sed_extractcf=/$re_begincf/,/$re_endcf/p + + # Validate tagname. + case $tagname in + *[!-_A-Za-z0-9,/]*) + func_fatal_error "invalid tag name: $tagname" + ;; + esac + + # Don't test for the "default" C tag, as we know it's + # there but not specially marked. + case $tagname in + CC) ;; + *) + if $GREP "$re_begincf" "$progpath" >/dev/null 2>&1; then + taglist="$taglist $tagname" + + # Evaluate the configuration. Be careful to quote the path + # and the sed script, to avoid splitting on whitespace, but + # also don't use non-portable quotes within backquotes within + # quotes we have to do it in 2 steps: + extractedcf=`$SED -n -e "$sed_extractcf" < "$progpath"` + eval "$extractedcf" + else + func_error "ignoring unknown tag $tagname" + fi + ;; + esac +} + + +# func_check_version_match +# ------------------------ +# Ensure that we are using m4 macros, and libtool script from the same +# release of libtool. +func_check_version_match () +{ + if test "$package_revision" != "$macro_revision"; then + if test "$VERSION" != "$macro_version"; then + if test -z "$macro_version"; then + cat >&2 <<_LT_EOF +$progname: Version mismatch error. This is $PACKAGE $VERSION, but the +$progname: definition of this LT_INIT comes from an older release. +$progname: You should recreate aclocal.m4 with macros from $PACKAGE $VERSION +$progname: and run autoconf again. +_LT_EOF + else + cat >&2 <<_LT_EOF +$progname: Version mismatch error. This is $PACKAGE $VERSION, but the +$progname: definition of this LT_INIT comes from $PACKAGE $macro_version. +$progname: You should recreate aclocal.m4 with macros from $PACKAGE $VERSION +$progname: and run autoconf again. +_LT_EOF + fi + else + cat >&2 <<_LT_EOF +$progname: Version mismatch error. This is $PACKAGE $VERSION, revision $package_revision, +$progname: but the definition of this LT_INIT comes from revision $macro_revision. +$progname: You should recreate aclocal.m4 with macros from revision $package_revision +$progname: of $PACKAGE $VERSION and run autoconf again. +_LT_EOF + fi + + exit $EXIT_MISMATCH + fi +} + + +# libtool_options_prep [ARG]... +# ----------------------------- +# Preparation for options parsed by libtool. +libtool_options_prep () +{ + $debug_mode + + # Option defaults: + opt_config=false + opt_dlopen= + opt_dry_run=false + opt_help=false + opt_mode= + opt_preserve_dup_deps=false + opt_quiet=false + + nonopt= + preserve_args= + + _G_rc_lt_options_prep=: + + # Shorthand for --mode=foo, only valid as the first argument + case $1 in + clean|clea|cle|cl) + shift; set dummy --mode clean ${1+"$@"}; shift + ;; + compile|compil|compi|comp|com|co|c) + shift; set dummy --mode compile ${1+"$@"}; shift + ;; + execute|execut|execu|exec|exe|ex|e) + shift; set dummy --mode execute ${1+"$@"}; shift + ;; + finish|finis|fini|fin|fi|f) + shift; set dummy --mode finish ${1+"$@"}; shift + ;; + install|instal|insta|inst|ins|in|i) + shift; set dummy --mode install ${1+"$@"}; shift + ;; + link|lin|li|l) + shift; set dummy --mode link ${1+"$@"}; shift + ;; + uninstall|uninstal|uninsta|uninst|unins|unin|uni|un|u) + shift; set dummy --mode uninstall ${1+"$@"}; shift + ;; + *) + _G_rc_lt_options_prep=false + ;; + esac + + if $_G_rc_lt_options_prep; then + # Pass back the list of options. + func_quote eval ${1+"$@"} + libtool_options_prep_result=$func_quote_result + fi +} +func_add_hook func_options_prep libtool_options_prep + + +# libtool_parse_options [ARG]... +# --------------------------------- +# Provide handling for libtool specific options. +libtool_parse_options () +{ + $debug_cmd + + _G_rc_lt_parse_options=false + + # Perform our own loop to consume as many options as possible in + # each iteration. + while test $# -gt 0; do + _G_match_lt_parse_options=: + _G_opt=$1 + shift + case $_G_opt in + --dry-run|--dryrun|-n) + opt_dry_run=: + ;; + + --config) func_config ;; + + --dlopen|-dlopen) + opt_dlopen="${opt_dlopen+$opt_dlopen +}$1" + shift + ;; + + --preserve-dup-deps) + opt_preserve_dup_deps=: ;; + + --features) func_features ;; + + --finish) set dummy --mode finish ${1+"$@"}; shift ;; + + --help) opt_help=: ;; + + --help-all) opt_help=': help-all' ;; + + --mode) test $# = 0 && func_missing_arg $_G_opt && break + opt_mode=$1 + case $1 in + # Valid mode arguments: + clean|compile|execute|finish|install|link|relink|uninstall) ;; + + # Catch anything else as an error + *) func_error "invalid argument for $_G_opt" + exit_cmd=exit + break + ;; + esac + shift + ;; + + --no-silent|--no-quiet) + opt_quiet=false + func_append preserve_args " $_G_opt" + ;; + + --no-warnings|--no-warning|--no-warn) + opt_warning=false + func_append preserve_args " $_G_opt" + ;; + + --no-verbose) + opt_verbose=false + func_append preserve_args " $_G_opt" + ;; + + --silent|--quiet) + opt_quiet=: + opt_verbose=false + func_append preserve_args " $_G_opt" + ;; + + --tag) test $# = 0 && func_missing_arg $_G_opt && break + opt_tag=$1 + func_append preserve_args " $_G_opt $1" + func_enable_tag "$1" + shift + ;; + + --verbose|-v) opt_quiet=false + opt_verbose=: + func_append preserve_args " $_G_opt" + ;; + + # An option not handled by this hook function: + *) set dummy "$_G_opt" ${1+"$@"} ; shift + _G_match_lt_parse_options=false + break + ;; + esac + $_G_match_lt_parse_options && _G_rc_lt_parse_options=: + done + + if $_G_rc_lt_parse_options; then + # save modified positional parameters for caller + func_quote eval ${1+"$@"} + libtool_parse_options_result=$func_quote_result + fi +} +func_add_hook func_parse_options libtool_parse_options + + + +# libtool_validate_options [ARG]... +# --------------------------------- +# Perform any sanity checks on option settings and/or unconsumed +# arguments. +libtool_validate_options () +{ + # save first non-option argument + if test 0 -lt $#; then + nonopt=$1 + shift + fi + + # preserve --debug + test : = "$debug_cmd" || func_append preserve_args " --debug" + + case $host in + # Solaris2 added to fix http://debbugs.gnu.org/cgi/bugreport.cgi?bug=16452 + # see also: http://gcc.gnu.org/bugzilla/show_bug.cgi?id=59788 + *cygwin* | *mingw* | *pw32* | *cegcc* | *solaris2* | *os2*) + # don't eliminate duplications in $postdeps and $predeps + opt_duplicate_compiler_generated_deps=: + ;; + *) + opt_duplicate_compiler_generated_deps=$opt_preserve_dup_deps + ;; + esac + + $opt_help || { + # Sanity checks first: + func_check_version_match + + test yes != "$build_libtool_libs" \ + && test yes != "$build_old_libs" \ + && func_fatal_configuration "not configured to build any kind of library" + + # Darwin sucks + eval std_shrext=\"$shrext_cmds\" + + # Only execute mode is allowed to have -dlopen flags. + if test -n "$opt_dlopen" && test execute != "$opt_mode"; then + func_error "unrecognized option '-dlopen'" + $ECHO "$help" 1>&2 + exit $EXIT_FAILURE + fi + + # Change the help message to a mode-specific one. + generic_help=$help + help="Try '$progname --help --mode=$opt_mode' for more information." + } + + # Pass back the unparsed argument list + func_quote eval ${1+"$@"} + libtool_validate_options_result=$func_quote_result +} +func_add_hook func_validate_options libtool_validate_options + + +# Process options as early as possible so that --help and --version +# can return quickly. +func_options ${1+"$@"} +eval set dummy "$func_options_result"; shift + + + +## ----------- ## +## Main. ## +## ----------- ## + +magic='%%%MAGIC variable%%%' +magic_exe='%%%MAGIC EXE variable%%%' + +# Global variables. +extracted_archives= +extracted_serial=0 + +# If this variable is set in any of the actions, the command in it +# will be execed at the end. This prevents here-documents from being +# left over by shells. +exec_cmd= + + +# A function that is used when there is no print builtin or printf. +func_fallback_echo () +{ + eval 'cat <<_LTECHO_EOF +$1 +_LTECHO_EOF' +} + +# func_generated_by_libtool +# True iff stdin has been generated by Libtool. This function is only +# a basic sanity check; it will hardly flush out determined imposters. +func_generated_by_libtool_p () +{ + $GREP "^# Generated by .*$PACKAGE" > /dev/null 2>&1 +} + +# func_lalib_p file +# True iff FILE is a libtool '.la' library or '.lo' object file. +# This function is only a basic sanity check; it will hardly flush out +# determined imposters. +func_lalib_p () +{ + test -f "$1" && + $SED -e 4q "$1" 2>/dev/null | func_generated_by_libtool_p +} + +# func_lalib_unsafe_p file +# True iff FILE is a libtool '.la' library or '.lo' object file. +# This function implements the same check as func_lalib_p without +# resorting to external programs. To this end, it redirects stdin and +# closes it afterwards, without saving the original file descriptor. +# As a safety measure, use it only where a negative result would be +# fatal anyway. Works if 'file' does not exist. +func_lalib_unsafe_p () +{ + lalib_p=no + if test -f "$1" && test -r "$1" && exec 5<&0 <"$1"; then + for lalib_p_l in 1 2 3 4 + do + read lalib_p_line + case $lalib_p_line in + \#\ Generated\ by\ *$PACKAGE* ) lalib_p=yes; break;; + esac + done + exec 0<&5 5<&- + fi + test yes = "$lalib_p" +} + +# func_ltwrapper_script_p file +# True iff FILE is a libtool wrapper script +# This function is only a basic sanity check; it will hardly flush out +# determined imposters. +func_ltwrapper_script_p () +{ + test -f "$1" && + $lt_truncate_bin < "$1" 2>/dev/null | func_generated_by_libtool_p +} + +# func_ltwrapper_executable_p file +# True iff FILE is a libtool wrapper executable +# This function is only a basic sanity check; it will hardly flush out +# determined imposters. +func_ltwrapper_executable_p () +{ + func_ltwrapper_exec_suffix= + case $1 in + *.exe) ;; + *) func_ltwrapper_exec_suffix=.exe ;; + esac + $GREP "$magic_exe" "$1$func_ltwrapper_exec_suffix" >/dev/null 2>&1 +} + +# func_ltwrapper_scriptname file +# Assumes file is an ltwrapper_executable +# uses $file to determine the appropriate filename for a +# temporary ltwrapper_script. +func_ltwrapper_scriptname () +{ + func_dirname_and_basename "$1" "" "." + func_stripname '' '.exe' "$func_basename_result" + func_ltwrapper_scriptname_result=$func_dirname_result/$objdir/${func_stripname_result}_ltshwrapper +} + +# func_ltwrapper_p file +# True iff FILE is a libtool wrapper script or wrapper executable +# This function is only a basic sanity check; it will hardly flush out +# determined imposters. +func_ltwrapper_p () +{ + func_ltwrapper_script_p "$1" || func_ltwrapper_executable_p "$1" +} + + +# func_execute_cmds commands fail_cmd +# Execute tilde-delimited COMMANDS. +# If FAIL_CMD is given, eval that upon failure. +# FAIL_CMD may read-access the current command in variable CMD! +func_execute_cmds () +{ + $debug_cmd + + save_ifs=$IFS; IFS='~' + for cmd in $1; do + IFS=$sp$nl + eval cmd=\"$cmd\" + IFS=$save_ifs + func_show_eval "$cmd" "${2-:}" + done + IFS=$save_ifs +} + + +# func_source file +# Source FILE, adding directory component if necessary. +# Note that it is not necessary on cygwin/mingw to append a dot to +# FILE even if both FILE and FILE.exe exist: automatic-append-.exe +# behavior happens only for exec(3), not for open(2)! Also, sourcing +# 'FILE.' does not work on cygwin managed mounts. +func_source () +{ + $debug_cmd + + case $1 in + */* | *\\*) . "$1" ;; + *) . "./$1" ;; + esac +} + + +# func_resolve_sysroot PATH +# Replace a leading = in PATH with a sysroot. Store the result into +# func_resolve_sysroot_result +func_resolve_sysroot () +{ + func_resolve_sysroot_result=$1 + case $func_resolve_sysroot_result in + =*) + func_stripname '=' '' "$func_resolve_sysroot_result" + func_resolve_sysroot_result=$lt_sysroot$func_stripname_result + ;; + esac +} + +# func_replace_sysroot PATH +# If PATH begins with the sysroot, replace it with = and +# store the result into func_replace_sysroot_result. +func_replace_sysroot () +{ + case $lt_sysroot:$1 in + ?*:"$lt_sysroot"*) + func_stripname "$lt_sysroot" '' "$1" + func_replace_sysroot_result='='$func_stripname_result + ;; + *) + # Including no sysroot. + func_replace_sysroot_result=$1 + ;; + esac +} + +# func_infer_tag arg +# Infer tagged configuration to use if any are available and +# if one wasn't chosen via the "--tag" command line option. +# Only attempt this if the compiler in the base compile +# command doesn't match the default compiler. +# arg is usually of the form 'gcc ...' +func_infer_tag () +{ + $debug_cmd + + if test -n "$available_tags" && test -z "$tagname"; then + CC_quoted= + for arg in $CC; do + func_append_quoted CC_quoted "$arg" + done + CC_expanded=`func_echo_all $CC` + CC_quoted_expanded=`func_echo_all $CC_quoted` + case $@ in + # Blanks in the command may have been stripped by the calling shell, + # but not from the CC environment variable when configure was run. + " $CC "* | "$CC "* | " $CC_expanded "* | "$CC_expanded "* | \ + " $CC_quoted"* | "$CC_quoted "* | " $CC_quoted_expanded "* | "$CC_quoted_expanded "*) ;; + # Blanks at the start of $base_compile will cause this to fail + # if we don't check for them as well. + *) + for z in $available_tags; do + if $GREP "^# ### BEGIN LIBTOOL TAG CONFIG: $z$" < "$progpath" > /dev/null; then + # Evaluate the configuration. + eval "`$SED -n -e '/^# ### BEGIN LIBTOOL TAG CONFIG: '$z'$/,/^# ### END LIBTOOL TAG CONFIG: '$z'$/p' < $progpath`" + CC_quoted= + for arg in $CC; do + # Double-quote args containing other shell metacharacters. + func_append_quoted CC_quoted "$arg" + done + CC_expanded=`func_echo_all $CC` + CC_quoted_expanded=`func_echo_all $CC_quoted` + case "$@ " in + " $CC "* | "$CC "* | " $CC_expanded "* | "$CC_expanded "* | \ + " $CC_quoted"* | "$CC_quoted "* | " $CC_quoted_expanded "* | "$CC_quoted_expanded "*) + # The compiler in the base compile command matches + # the one in the tagged configuration. + # Assume this is the tagged configuration we want. + tagname=$z + break + ;; + esac + fi + done + # If $tagname still isn't set, then no tagged configuration + # was found and let the user know that the "--tag" command + # line option must be used. + if test -z "$tagname"; then + func_echo "unable to infer tagged configuration" + func_fatal_error "specify a tag with '--tag'" +# else +# func_verbose "using $tagname tagged configuration" + fi + ;; + esac + fi +} + + + +# func_write_libtool_object output_name pic_name nonpic_name +# Create a libtool object file (analogous to a ".la" file), +# but don't create it if we're doing a dry run. +func_write_libtool_object () +{ + write_libobj=$1 + if test yes = "$build_libtool_libs"; then + write_lobj=\'$2\' + else + write_lobj=none + fi + + if test yes = "$build_old_libs"; then + write_oldobj=\'$3\' + else + write_oldobj=none + fi + + $opt_dry_run || { + cat >${write_libobj}T </dev/null` + if test "$?" -eq 0 && test -n "$func_convert_core_file_wine_to_w32_tmp"; then + func_convert_core_file_wine_to_w32_result=`$ECHO "$func_convert_core_file_wine_to_w32_tmp" | + $SED -e "$sed_naive_backslashify"` + else + func_convert_core_file_wine_to_w32_result= + fi + fi +} +# end: func_convert_core_file_wine_to_w32 + + +# func_convert_core_path_wine_to_w32 ARG +# Helper function used by path conversion functions when $build is *nix, and +# $host is mingw, cygwin, or some other w32 environment. Relies on a correctly +# configured wine environment available, with the winepath program in $build's +# $PATH. Assumes ARG has no leading or trailing path separator characters. +# +# ARG is path to be converted from $build format to win32. +# Result is available in $func_convert_core_path_wine_to_w32_result. +# Unconvertible file (directory) names in ARG are skipped; if no directory names +# are convertible, then the result may be empty. +func_convert_core_path_wine_to_w32 () +{ + $debug_cmd + + # unfortunately, winepath doesn't convert paths, only file names + func_convert_core_path_wine_to_w32_result= + if test -n "$1"; then + oldIFS=$IFS + IFS=: + for func_convert_core_path_wine_to_w32_f in $1; do + IFS=$oldIFS + func_convert_core_file_wine_to_w32 "$func_convert_core_path_wine_to_w32_f" + if test -n "$func_convert_core_file_wine_to_w32_result"; then + if test -z "$func_convert_core_path_wine_to_w32_result"; then + func_convert_core_path_wine_to_w32_result=$func_convert_core_file_wine_to_w32_result + else + func_append func_convert_core_path_wine_to_w32_result ";$func_convert_core_file_wine_to_w32_result" + fi + fi + done + IFS=$oldIFS + fi +} +# end: func_convert_core_path_wine_to_w32 + + +# func_cygpath ARGS... +# Wrapper around calling the cygpath program via LT_CYGPATH. This is used when +# when (1) $build is *nix and Cygwin is hosted via a wine environment; or (2) +# $build is MSYS and $host is Cygwin, or (3) $build is Cygwin. In case (1) or +# (2), returns the Cygwin file name or path in func_cygpath_result (input +# file name or path is assumed to be in w32 format, as previously converted +# from $build's *nix or MSYS format). In case (3), returns the w32 file name +# or path in func_cygpath_result (input file name or path is assumed to be in +# Cygwin format). Returns an empty string on error. +# +# ARGS are passed to cygpath, with the last one being the file name or path to +# be converted. +# +# Specify the absolute *nix (or w32) name to cygpath in the LT_CYGPATH +# environment variable; do not put it in $PATH. +func_cygpath () +{ + $debug_cmd + + if test -n "$LT_CYGPATH" && test -f "$LT_CYGPATH"; then + func_cygpath_result=`$LT_CYGPATH "$@" 2>/dev/null` + if test "$?" -ne 0; then + # on failure, ensure result is empty + func_cygpath_result= + fi + else + func_cygpath_result= + func_error "LT_CYGPATH is empty or specifies non-existent file: '$LT_CYGPATH'" + fi +} +#end: func_cygpath + + +# func_convert_core_msys_to_w32 ARG +# Convert file name or path ARG from MSYS format to w32 format. Return +# result in func_convert_core_msys_to_w32_result. +func_convert_core_msys_to_w32 () +{ + $debug_cmd + + # awkward: cmd appends spaces to result + func_convert_core_msys_to_w32_result=`( cmd //c echo "$1" ) 2>/dev/null | + $SED -e 's/[ ]*$//' -e "$sed_naive_backslashify"` +} +#end: func_convert_core_msys_to_w32 + + +# func_convert_file_check ARG1 ARG2 +# Verify that ARG1 (a file name in $build format) was converted to $host +# format in ARG2. Otherwise, emit an error message, but continue (resetting +# func_to_host_file_result to ARG1). +func_convert_file_check () +{ + $debug_cmd + + if test -z "$2" && test -n "$1"; then + func_error "Could not determine host file name corresponding to" + func_error " '$1'" + func_error "Continuing, but uninstalled executables may not work." + # Fallback: + func_to_host_file_result=$1 + fi +} +# end func_convert_file_check + + +# func_convert_path_check FROM_PATHSEP TO_PATHSEP FROM_PATH TO_PATH +# Verify that FROM_PATH (a path in $build format) was converted to $host +# format in TO_PATH. Otherwise, emit an error message, but continue, resetting +# func_to_host_file_result to a simplistic fallback value (see below). +func_convert_path_check () +{ + $debug_cmd + + if test -z "$4" && test -n "$3"; then + func_error "Could not determine the host path corresponding to" + func_error " '$3'" + func_error "Continuing, but uninstalled executables may not work." + # Fallback. This is a deliberately simplistic "conversion" and + # should not be "improved". See libtool.info. + if test "x$1" != "x$2"; then + lt_replace_pathsep_chars="s|$1|$2|g" + func_to_host_path_result=`echo "$3" | + $SED -e "$lt_replace_pathsep_chars"` + else + func_to_host_path_result=$3 + fi + fi +} +# end func_convert_path_check + + +# func_convert_path_front_back_pathsep FRONTPAT BACKPAT REPL ORIG +# Modifies func_to_host_path_result by prepending REPL if ORIG matches FRONTPAT +# and appending REPL if ORIG matches BACKPAT. +func_convert_path_front_back_pathsep () +{ + $debug_cmd + + case $4 in + $1 ) func_to_host_path_result=$3$func_to_host_path_result + ;; + esac + case $4 in + $2 ) func_append func_to_host_path_result "$3" + ;; + esac +} +# end func_convert_path_front_back_pathsep + + +################################################## +# $build to $host FILE NAME CONVERSION FUNCTIONS # +################################################## +# invoked via '$to_host_file_cmd ARG' +# +# In each case, ARG is the path to be converted from $build to $host format. +# Result will be available in $func_to_host_file_result. + + +# func_to_host_file ARG +# Converts the file name ARG from $build format to $host format. Return result +# in func_to_host_file_result. +func_to_host_file () +{ + $debug_cmd + + $to_host_file_cmd "$1" +} +# end func_to_host_file + + +# func_to_tool_file ARG LAZY +# converts the file name ARG from $build format to toolchain format. Return +# result in func_to_tool_file_result. If the conversion in use is listed +# in (the comma separated) LAZY, no conversion takes place. +func_to_tool_file () +{ + $debug_cmd + + case ,$2, in + *,"$to_tool_file_cmd",*) + func_to_tool_file_result=$1 + ;; + *) + $to_tool_file_cmd "$1" + func_to_tool_file_result=$func_to_host_file_result + ;; + esac +} +# end func_to_tool_file + + +# func_convert_file_noop ARG +# Copy ARG to func_to_host_file_result. +func_convert_file_noop () +{ + func_to_host_file_result=$1 +} +# end func_convert_file_noop + + +# func_convert_file_msys_to_w32 ARG +# Convert file name ARG from (mingw) MSYS to (mingw) w32 format; automatic +# conversion to w32 is not available inside the cwrapper. Returns result in +# func_to_host_file_result. +func_convert_file_msys_to_w32 () +{ + $debug_cmd + + func_to_host_file_result=$1 + if test -n "$1"; then + func_convert_core_msys_to_w32 "$1" + func_to_host_file_result=$func_convert_core_msys_to_w32_result + fi + func_convert_file_check "$1" "$func_to_host_file_result" +} +# end func_convert_file_msys_to_w32 + + +# func_convert_file_cygwin_to_w32 ARG +# Convert file name ARG from Cygwin to w32 format. Returns result in +# func_to_host_file_result. +func_convert_file_cygwin_to_w32 () +{ + $debug_cmd + + func_to_host_file_result=$1 + if test -n "$1"; then + # because $build is cygwin, we call "the" cygpath in $PATH; no need to use + # LT_CYGPATH in this case. + func_to_host_file_result=`cygpath -m "$1"` + fi + func_convert_file_check "$1" "$func_to_host_file_result" +} +# end func_convert_file_cygwin_to_w32 + + +# func_convert_file_nix_to_w32 ARG +# Convert file name ARG from *nix to w32 format. Requires a wine environment +# and a working winepath. Returns result in func_to_host_file_result. +func_convert_file_nix_to_w32 () +{ + $debug_cmd + + func_to_host_file_result=$1 + if test -n "$1"; then + func_convert_core_file_wine_to_w32 "$1" + func_to_host_file_result=$func_convert_core_file_wine_to_w32_result + fi + func_convert_file_check "$1" "$func_to_host_file_result" +} +# end func_convert_file_nix_to_w32 + + +# func_convert_file_msys_to_cygwin ARG +# Convert file name ARG from MSYS to Cygwin format. Requires LT_CYGPATH set. +# Returns result in func_to_host_file_result. +func_convert_file_msys_to_cygwin () +{ + $debug_cmd + + func_to_host_file_result=$1 + if test -n "$1"; then + func_convert_core_msys_to_w32 "$1" + func_cygpath -u "$func_convert_core_msys_to_w32_result" + func_to_host_file_result=$func_cygpath_result + fi + func_convert_file_check "$1" "$func_to_host_file_result" +} +# end func_convert_file_msys_to_cygwin + + +# func_convert_file_nix_to_cygwin ARG +# Convert file name ARG from *nix to Cygwin format. Requires Cygwin installed +# in a wine environment, working winepath, and LT_CYGPATH set. Returns result +# in func_to_host_file_result. +func_convert_file_nix_to_cygwin () +{ + $debug_cmd + + func_to_host_file_result=$1 + if test -n "$1"; then + # convert from *nix to w32, then use cygpath to convert from w32 to cygwin. + func_convert_core_file_wine_to_w32 "$1" + func_cygpath -u "$func_convert_core_file_wine_to_w32_result" + func_to_host_file_result=$func_cygpath_result + fi + func_convert_file_check "$1" "$func_to_host_file_result" +} +# end func_convert_file_nix_to_cygwin + + +############################################# +# $build to $host PATH CONVERSION FUNCTIONS # +############################################# +# invoked via '$to_host_path_cmd ARG' +# +# In each case, ARG is the path to be converted from $build to $host format. +# The result will be available in $func_to_host_path_result. +# +# Path separators are also converted from $build format to $host format. If +# ARG begins or ends with a path separator character, it is preserved (but +# converted to $host format) on output. +# +# All path conversion functions are named using the following convention: +# file name conversion function : func_convert_file_X_to_Y () +# path conversion function : func_convert_path_X_to_Y () +# where, for any given $build/$host combination the 'X_to_Y' value is the +# same. If conversion functions are added for new $build/$host combinations, +# the two new functions must follow this pattern, or func_init_to_host_path_cmd +# will break. + + +# func_init_to_host_path_cmd +# Ensures that function "pointer" variable $to_host_path_cmd is set to the +# appropriate value, based on the value of $to_host_file_cmd. +to_host_path_cmd= +func_init_to_host_path_cmd () +{ + $debug_cmd + + if test -z "$to_host_path_cmd"; then + func_stripname 'func_convert_file_' '' "$to_host_file_cmd" + to_host_path_cmd=func_convert_path_$func_stripname_result + fi +} + + +# func_to_host_path ARG +# Converts the path ARG from $build format to $host format. Return result +# in func_to_host_path_result. +func_to_host_path () +{ + $debug_cmd + + func_init_to_host_path_cmd + $to_host_path_cmd "$1" +} +# end func_to_host_path + + +# func_convert_path_noop ARG +# Copy ARG to func_to_host_path_result. +func_convert_path_noop () +{ + func_to_host_path_result=$1 +} +# end func_convert_path_noop + + +# func_convert_path_msys_to_w32 ARG +# Convert path ARG from (mingw) MSYS to (mingw) w32 format; automatic +# conversion to w32 is not available inside the cwrapper. Returns result in +# func_to_host_path_result. +func_convert_path_msys_to_w32 () +{ + $debug_cmd + + func_to_host_path_result=$1 + if test -n "$1"; then + # Remove leading and trailing path separator characters from ARG. MSYS + # behavior is inconsistent here; cygpath turns them into '.;' and ';.'; + # and winepath ignores them completely. + func_stripname : : "$1" + func_to_host_path_tmp1=$func_stripname_result + func_convert_core_msys_to_w32 "$func_to_host_path_tmp1" + func_to_host_path_result=$func_convert_core_msys_to_w32_result + func_convert_path_check : ";" \ + "$func_to_host_path_tmp1" "$func_to_host_path_result" + func_convert_path_front_back_pathsep ":*" "*:" ";" "$1" + fi +} +# end func_convert_path_msys_to_w32 + + +# func_convert_path_cygwin_to_w32 ARG +# Convert path ARG from Cygwin to w32 format. Returns result in +# func_to_host_file_result. +func_convert_path_cygwin_to_w32 () +{ + $debug_cmd + + func_to_host_path_result=$1 + if test -n "$1"; then + # See func_convert_path_msys_to_w32: + func_stripname : : "$1" + func_to_host_path_tmp1=$func_stripname_result + func_to_host_path_result=`cygpath -m -p "$func_to_host_path_tmp1"` + func_convert_path_check : ";" \ + "$func_to_host_path_tmp1" "$func_to_host_path_result" + func_convert_path_front_back_pathsep ":*" "*:" ";" "$1" + fi +} +# end func_convert_path_cygwin_to_w32 + + +# func_convert_path_nix_to_w32 ARG +# Convert path ARG from *nix to w32 format. Requires a wine environment and +# a working winepath. Returns result in func_to_host_file_result. +func_convert_path_nix_to_w32 () +{ + $debug_cmd + + func_to_host_path_result=$1 + if test -n "$1"; then + # See func_convert_path_msys_to_w32: + func_stripname : : "$1" + func_to_host_path_tmp1=$func_stripname_result + func_convert_core_path_wine_to_w32 "$func_to_host_path_tmp1" + func_to_host_path_result=$func_convert_core_path_wine_to_w32_result + func_convert_path_check : ";" \ + "$func_to_host_path_tmp1" "$func_to_host_path_result" + func_convert_path_front_back_pathsep ":*" "*:" ";" "$1" + fi +} +# end func_convert_path_nix_to_w32 + + +# func_convert_path_msys_to_cygwin ARG +# Convert path ARG from MSYS to Cygwin format. Requires LT_CYGPATH set. +# Returns result in func_to_host_file_result. +func_convert_path_msys_to_cygwin () +{ + $debug_cmd + + func_to_host_path_result=$1 + if test -n "$1"; then + # See func_convert_path_msys_to_w32: + func_stripname : : "$1" + func_to_host_path_tmp1=$func_stripname_result + func_convert_core_msys_to_w32 "$func_to_host_path_tmp1" + func_cygpath -u -p "$func_convert_core_msys_to_w32_result" + func_to_host_path_result=$func_cygpath_result + func_convert_path_check : : \ + "$func_to_host_path_tmp1" "$func_to_host_path_result" + func_convert_path_front_back_pathsep ":*" "*:" : "$1" + fi +} +# end func_convert_path_msys_to_cygwin + + +# func_convert_path_nix_to_cygwin ARG +# Convert path ARG from *nix to Cygwin format. Requires Cygwin installed in a +# a wine environment, working winepath, and LT_CYGPATH set. Returns result in +# func_to_host_file_result. +func_convert_path_nix_to_cygwin () +{ + $debug_cmd + + func_to_host_path_result=$1 + if test -n "$1"; then + # Remove leading and trailing path separator characters from + # ARG. msys behavior is inconsistent here, cygpath turns them + # into '.;' and ';.', and winepath ignores them completely. + func_stripname : : "$1" + func_to_host_path_tmp1=$func_stripname_result + func_convert_core_path_wine_to_w32 "$func_to_host_path_tmp1" + func_cygpath -u -p "$func_convert_core_path_wine_to_w32_result" + func_to_host_path_result=$func_cygpath_result + func_convert_path_check : : \ + "$func_to_host_path_tmp1" "$func_to_host_path_result" + func_convert_path_front_back_pathsep ":*" "*:" : "$1" + fi +} +# end func_convert_path_nix_to_cygwin + + +# func_dll_def_p FILE +# True iff FILE is a Windows DLL '.def' file. +# Keep in sync with _LT_DLL_DEF_P in libtool.m4 +func_dll_def_p () +{ + $debug_cmd + + func_dll_def_p_tmp=`$SED -n \ + -e 's/^[ ]*//' \ + -e '/^\(;.*\)*$/d' \ + -e 's/^\(EXPORTS\|LIBRARY\)\([ ].*\)*$/DEF/p' \ + -e q \ + "$1"` + test DEF = "$func_dll_def_p_tmp" +} + + +# func_mode_compile arg... +func_mode_compile () +{ + $debug_cmd + + # Get the compilation command and the source file. + base_compile= + srcfile=$nonopt # always keep a non-empty value in "srcfile" + suppress_opt=yes + suppress_output= + arg_mode=normal + libobj= + later= + pie_flag= + + for arg + do + case $arg_mode in + arg ) + # do not "continue". Instead, add this to base_compile + lastarg=$arg + arg_mode=normal + ;; + + target ) + libobj=$arg + arg_mode=normal + continue + ;; + + normal ) + # Accept any command-line options. + case $arg in + -o) + test -n "$libobj" && \ + func_fatal_error "you cannot specify '-o' more than once" + arg_mode=target + continue + ;; + + -pie | -fpie | -fPIE) + func_append pie_flag " $arg" + continue + ;; + + -shared | -static | -prefer-pic | -prefer-non-pic) + func_append later " $arg" + continue + ;; + + -no-suppress) + suppress_opt=no + continue + ;; + + -Xcompiler) + arg_mode=arg # the next one goes into the "base_compile" arg list + continue # The current "srcfile" will either be retained or + ;; # replaced later. I would guess that would be a bug. + + -Wc,*) + func_stripname '-Wc,' '' "$arg" + args=$func_stripname_result + lastarg= + save_ifs=$IFS; IFS=, + for arg in $args; do + IFS=$save_ifs + func_append_quoted lastarg "$arg" + done + IFS=$save_ifs + func_stripname ' ' '' "$lastarg" + lastarg=$func_stripname_result + + # Add the arguments to base_compile. + func_append base_compile " $lastarg" + continue + ;; + + *) + # Accept the current argument as the source file. + # The previous "srcfile" becomes the current argument. + # + lastarg=$srcfile + srcfile=$arg + ;; + esac # case $arg + ;; + esac # case $arg_mode + + # Aesthetically quote the previous argument. + func_append_quoted base_compile "$lastarg" + done # for arg + + case $arg_mode in + arg) + func_fatal_error "you must specify an argument for -Xcompile" + ;; + target) + func_fatal_error "you must specify a target with '-o'" + ;; + *) + # Get the name of the library object. + test -z "$libobj" && { + func_basename "$srcfile" + libobj=$func_basename_result + } + ;; + esac + + # Recognize several different file suffixes. + # If the user specifies -o file.o, it is replaced with file.lo + case $libobj in + *.[cCFSifmso] | \ + *.ada | *.adb | *.ads | *.asm | \ + *.c++ | *.cc | *.ii | *.class | *.cpp | *.cxx | \ + *.[fF][09]? | *.for | *.java | *.go | *.obj | *.sx | *.cu | *.cup) + func_xform "$libobj" + libobj=$func_xform_result + ;; + esac + + case $libobj in + *.lo) func_lo2o "$libobj"; obj=$func_lo2o_result ;; + *) + func_fatal_error "cannot determine name of library object from '$libobj'" + ;; + esac + + func_infer_tag $base_compile + + for arg in $later; do + case $arg in + -shared) + test yes = "$build_libtool_libs" \ + || func_fatal_configuration "cannot build a shared library" + build_old_libs=no + continue + ;; + + -static) + build_libtool_libs=no + build_old_libs=yes + continue + ;; + + -prefer-pic) + pic_mode=yes + continue + ;; + + -prefer-non-pic) + pic_mode=no + continue + ;; + esac + done + + func_quote_arg pretty "$libobj" + test "X$libobj" != "X$func_quote_arg_result" \ + && $ECHO "X$libobj" | $GREP '[]~#^*{};<>?"'"'"' &()|`$[]' \ + && func_warning "libobj name '$libobj' may not contain shell special characters." + func_dirname_and_basename "$obj" "/" "" + objname=$func_basename_result + xdir=$func_dirname_result + lobj=$xdir$objdir/$objname + + test -z "$base_compile" && \ + func_fatal_help "you must specify a compilation command" + + # Delete any leftover library objects. + if test yes = "$build_old_libs"; then + removelist="$obj $lobj $libobj ${libobj}T" + else + removelist="$lobj $libobj ${libobj}T" + fi + + # On Cygwin there's no "real" PIC flag so we must build both object types + case $host_os in + cygwin* | mingw* | pw32* | os2* | cegcc*) + pic_mode=default + ;; + esac + if test no = "$pic_mode" && test pass_all != "$deplibs_check_method"; then + # non-PIC code in shared libraries is not supported + pic_mode=default + fi + + # Calculate the filename of the output object if compiler does + # not support -o with -c + if test no = "$compiler_c_o"; then + output_obj=`$ECHO "$srcfile" | $SED 's%^.*/%%; s%\.[^.]*$%%'`.$objext + lockfile=$output_obj.lock + else + output_obj= + need_locks=no + lockfile= + fi + + # Lock this critical section if it is needed + # We use this script file to make the link, it avoids creating a new file + if test yes = "$need_locks"; then + until $opt_dry_run || ln "$progpath" "$lockfile" 2>/dev/null; do + func_echo "Waiting for $lockfile to be removed" + sleep 2 + done + elif test warn = "$need_locks"; then + if test -f "$lockfile"; then + $ECHO "\ +*** ERROR, $lockfile exists and contains: +`cat $lockfile 2>/dev/null` + +This indicates that another process is trying to use the same +temporary object file, and libtool could not work around it because +your compiler does not support '-c' and '-o' together. If you +repeat this compilation, it may succeed, by chance, but you had better +avoid parallel builds (make -j) in this platform, or get a better +compiler." + + $opt_dry_run || $RM $removelist + exit $EXIT_FAILURE + fi + func_append removelist " $output_obj" + $ECHO "$srcfile" > "$lockfile" + fi + + $opt_dry_run || $RM $removelist + func_append removelist " $lockfile" + trap '$opt_dry_run || $RM $removelist; exit $EXIT_FAILURE' 1 2 15 + + func_to_tool_file "$srcfile" func_convert_file_msys_to_w32 + srcfile=$func_to_tool_file_result + func_quote_arg pretty "$srcfile" + qsrcfile=$func_quote_arg_result + + # Only build a PIC object if we are building libtool libraries. + if test yes = "$build_libtool_libs"; then + # Without this assignment, base_compile gets emptied. + fbsd_hideous_sh_bug=$base_compile + + if test no != "$pic_mode"; then + command="$base_compile $qsrcfile $pic_flag" + else + # Don't build PIC code + command="$base_compile $qsrcfile" + fi + + func_mkdir_p "$xdir$objdir" + + if test -z "$output_obj"; then + # Place PIC objects in $objdir + func_append command " -o $lobj" + fi + + func_show_eval_locale "$command" \ + 'test -n "$output_obj" && $RM $removelist; exit $EXIT_FAILURE' + + if test warn = "$need_locks" && + test "X`cat $lockfile 2>/dev/null`" != "X$srcfile"; then + $ECHO "\ +*** ERROR, $lockfile contains: +`cat $lockfile 2>/dev/null` + +but it should contain: +$srcfile + +This indicates that another process is trying to use the same +temporary object file, and libtool could not work around it because +your compiler does not support '-c' and '-o' together. If you +repeat this compilation, it may succeed, by chance, but you had better +avoid parallel builds (make -j) in this platform, or get a better +compiler." + + $opt_dry_run || $RM $removelist + exit $EXIT_FAILURE + fi + + # Just move the object if needed, then go on to compile the next one + if test -n "$output_obj" && test "X$output_obj" != "X$lobj"; then + func_show_eval '$MV "$output_obj" "$lobj"' \ + 'error=$?; $opt_dry_run || $RM $removelist; exit $error' + fi + + # Allow error messages only from the first compilation. + if test yes = "$suppress_opt"; then + suppress_output=' >/dev/null 2>&1' + fi + fi + + # Only build a position-dependent object if we build old libraries. + if test yes = "$build_old_libs"; then + if test yes != "$pic_mode"; then + # Don't build PIC code + command="$base_compile $qsrcfile$pie_flag" + else + command="$base_compile $qsrcfile $pic_flag" + fi + if test yes = "$compiler_c_o"; then + func_append command " -o $obj" + fi + + # Suppress compiler output if we already did a PIC compilation. + func_append command "$suppress_output" + func_show_eval_locale "$command" \ + '$opt_dry_run || $RM $removelist; exit $EXIT_FAILURE' + + if test warn = "$need_locks" && + test "X`cat $lockfile 2>/dev/null`" != "X$srcfile"; then + $ECHO "\ +*** ERROR, $lockfile contains: +`cat $lockfile 2>/dev/null` + +but it should contain: +$srcfile + +This indicates that another process is trying to use the same +temporary object file, and libtool could not work around it because +your compiler does not support '-c' and '-o' together. If you +repeat this compilation, it may succeed, by chance, but you had better +avoid parallel builds (make -j) in this platform, or get a better +compiler." + + $opt_dry_run || $RM $removelist + exit $EXIT_FAILURE + fi + + # Just move the object if needed + if test -n "$output_obj" && test "X$output_obj" != "X$obj"; then + func_show_eval '$MV "$output_obj" "$obj"' \ + 'error=$?; $opt_dry_run || $RM $removelist; exit $error' + fi + fi + + $opt_dry_run || { + func_write_libtool_object "$libobj" "$objdir/$objname" "$objname" + + # Unlock the critical section if it was locked + if test no != "$need_locks"; then + removelist=$lockfile + $RM "$lockfile" + fi + } + + exit $EXIT_SUCCESS +} + +$opt_help || { + test compile = "$opt_mode" && func_mode_compile ${1+"$@"} +} + +func_mode_help () +{ + # We need to display help for each of the modes. + case $opt_mode in + "") + # Generic help is extracted from the usage comments + # at the start of this file. + func_help + ;; + + clean) + $ECHO \ +"Usage: $progname [OPTION]... --mode=clean RM [RM-OPTION]... FILE... + +Remove files from the build directory. + +RM is the name of the program to use to delete files associated with each FILE +(typically '/bin/rm'). RM-OPTIONS are options (such as '-f') to be passed +to RM. + +If FILE is a libtool library, object or program, all the files associated +with it are deleted. Otherwise, only FILE itself is deleted using RM." + ;; + + compile) + $ECHO \ +"Usage: $progname [OPTION]... --mode=compile COMPILE-COMMAND... SOURCEFILE + +Compile a source file into a libtool library object. + +This mode accepts the following additional options: + + -o OUTPUT-FILE set the output file name to OUTPUT-FILE + -no-suppress do not suppress compiler output for multiple passes + -prefer-pic try to build PIC objects only + -prefer-non-pic try to build non-PIC objects only + -shared do not build a '.o' file suitable for static linking + -static only build a '.o' file suitable for static linking + -Wc,FLAG + -Xcompiler FLAG pass FLAG directly to the compiler + +COMPILE-COMMAND is a command to be used in creating a 'standard' object file +from the given SOURCEFILE. + +The output file name is determined by removing the directory component from +SOURCEFILE, then substituting the C source code suffix '.c' with the +library object suffix, '.lo'." + ;; + + execute) + $ECHO \ +"Usage: $progname [OPTION]... --mode=execute COMMAND [ARGS]... + +Automatically set library path, then run a program. + +This mode accepts the following additional options: + + -dlopen FILE add the directory containing FILE to the library path + +This mode sets the library path environment variable according to '-dlopen' +flags. + +If any of the ARGS are libtool executable wrappers, then they are translated +into their corresponding uninstalled binary, and any of their required library +directories are added to the library path. + +Then, COMMAND is executed, with ARGS as arguments." + ;; + + finish) + $ECHO \ +"Usage: $progname [OPTION]... --mode=finish [LIBDIR]... + +Complete the installation of libtool libraries. + +Each LIBDIR is a directory that contains libtool libraries. + +The commands that this mode executes may require superuser privileges. Use +the '--dry-run' option if you just want to see what would be executed." + ;; + + install) + $ECHO \ +"Usage: $progname [OPTION]... --mode=install INSTALL-COMMAND... + +Install executables or libraries. + +INSTALL-COMMAND is the installation command. The first component should be +either the 'install' or 'cp' program. + +The following components of INSTALL-COMMAND are treated specially: + + -inst-prefix-dir PREFIX-DIR Use PREFIX-DIR as a staging area for installation + +The rest of the components are interpreted as arguments to that command (only +BSD-compatible install options are recognized)." + ;; + + link) + $ECHO \ +"Usage: $progname [OPTION]... --mode=link LINK-COMMAND... + +Link object files or libraries together to form another library, or to +create an executable program. + +LINK-COMMAND is a command using the C compiler that you would use to create +a program from several object files. + +The following components of LINK-COMMAND are treated specially: + + -all-static do not do any dynamic linking at all + -avoid-version do not add a version suffix if possible + -bindir BINDIR specify path to binaries directory (for systems where + libraries must be found in the PATH setting at runtime) + -dlopen FILE '-dlpreopen' FILE if it cannot be dlopened at runtime + -dlpreopen FILE link in FILE and add its symbols to lt_preloaded_symbols + -export-dynamic allow symbols from OUTPUT-FILE to be resolved with dlsym(3) + -export-symbols SYMFILE + try to export only the symbols listed in SYMFILE + -export-symbols-regex REGEX + try to export only the symbols matching REGEX + -LLIBDIR search LIBDIR for required installed libraries + -lNAME OUTPUT-FILE requires the installed library libNAME + -module build a library that can dlopened + -no-fast-install disable the fast-install mode + -no-install link a not-installable executable + -no-undefined declare that a library does not refer to external symbols + -o OUTPUT-FILE create OUTPUT-FILE from the specified objects + -objectlist FILE use a list of object files found in FILE to specify objects + -os2dllname NAME force a short DLL name on OS/2 (no effect on other OSes) + -precious-files-regex REGEX + don't remove output files matching REGEX + -release RELEASE specify package release information + -rpath LIBDIR the created library will eventually be installed in LIBDIR + -R[ ]LIBDIR add LIBDIR to the runtime path of programs and libraries + -shared only do dynamic linking of libtool libraries + -shrext SUFFIX override the standard shared library file extension + -static do not do any dynamic linking of uninstalled libtool libraries + -static-libtool-libs + do not do any dynamic linking of libtool libraries + -version-info CURRENT[:REVISION[:AGE]] + specify library version info [each variable defaults to 0] + -weak LIBNAME declare that the target provides the LIBNAME interface + -Wc,FLAG + -Xcompiler FLAG pass linker-specific FLAG directly to the compiler + -Wa,FLAG + -Xassembler FLAG pass linker-specific FLAG directly to the assembler + -Wl,FLAG + -Xlinker FLAG pass linker-specific FLAG directly to the linker + -XCClinker FLAG pass link-specific FLAG to the compiler driver (CC) + +All other options (arguments beginning with '-') are ignored. + +Every other argument is treated as a filename. Files ending in '.la' are +treated as uninstalled libtool libraries, other files are standard or library +object files. + +If the OUTPUT-FILE ends in '.la', then a libtool library is created, +only library objects ('.lo' files) may be specified, and '-rpath' is +required, except when creating a convenience library. + +If OUTPUT-FILE ends in '.a' or '.lib', then a standard library is created +using 'ar' and 'ranlib', or on Windows using 'lib'. + +If OUTPUT-FILE ends in '.lo' or '.$objext', then a reloadable object file +is created, otherwise an executable program is created." + ;; + + uninstall) + $ECHO \ +"Usage: $progname [OPTION]... --mode=uninstall RM [RM-OPTION]... FILE... + +Remove libraries from an installation directory. + +RM is the name of the program to use to delete files associated with each FILE +(typically '/bin/rm'). RM-OPTIONS are options (such as '-f') to be passed +to RM. + +If FILE is a libtool library, all the files associated with it are deleted. +Otherwise, only FILE itself is deleted using RM." + ;; + + *) + func_fatal_help "invalid operation mode '$opt_mode'" + ;; + esac + + echo + $ECHO "Try '$progname --help' for more information about other modes." +} + +# Now that we've collected a possible --mode arg, show help if necessary +if $opt_help; then + if test : = "$opt_help"; then + func_mode_help + else + { + func_help noexit + for opt_mode in compile link execute install finish uninstall clean; do + func_mode_help + done + } | $SED -n '1p; 2,$s/^Usage:/ or: /p' + { + func_help noexit + for opt_mode in compile link execute install finish uninstall clean; do + echo + func_mode_help + done + } | + $SED '1d + /^When reporting/,/^Report/{ + H + d + } + $x + /information about other modes/d + /more detailed .*MODE/d + s/^Usage:.*--mode=\([^ ]*\) .*/Description of \1 mode:/' + fi + exit $? +fi + + +# func_mode_execute arg... +func_mode_execute () +{ + $debug_cmd + + # The first argument is the command name. + cmd=$nonopt + test -z "$cmd" && \ + func_fatal_help "you must specify a COMMAND" + + # Handle -dlopen flags immediately. + for file in $opt_dlopen; do + test -f "$file" \ + || func_fatal_help "'$file' is not a file" + + dir= + case $file in + *.la) + func_resolve_sysroot "$file" + file=$func_resolve_sysroot_result + + # Check to see that this really is a libtool archive. + func_lalib_unsafe_p "$file" \ + || func_fatal_help "'$lib' is not a valid libtool archive" + + # Read the libtool library. + dlname= + library_names= + func_source "$file" + + # Skip this library if it cannot be dlopened. + if test -z "$dlname"; then + # Warn if it was a shared library. + test -n "$library_names" && \ + func_warning "'$file' was not linked with '-export-dynamic'" + continue + fi + + func_dirname "$file" "" "." + dir=$func_dirname_result + + if test -f "$dir/$objdir/$dlname"; then + func_append dir "/$objdir" + else + if test ! -f "$dir/$dlname"; then + func_fatal_error "cannot find '$dlname' in '$dir' or '$dir/$objdir'" + fi + fi + ;; + + *.lo) + # Just add the directory containing the .lo file. + func_dirname "$file" "" "." + dir=$func_dirname_result + ;; + + *) + func_warning "'-dlopen' is ignored for non-libtool libraries and objects" + continue + ;; + esac + + # Get the absolute pathname. + absdir=`cd "$dir" && pwd` + test -n "$absdir" && dir=$absdir + + # Now add the directory to shlibpath_var. + if eval "test -z \"\$$shlibpath_var\""; then + eval "$shlibpath_var=\"\$dir\"" + else + eval "$shlibpath_var=\"\$dir:\$$shlibpath_var\"" + fi + done + + # This variable tells wrapper scripts just to set shlibpath_var + # rather than running their programs. + libtool_execute_magic=$magic + + # Check if any of the arguments is a wrapper script. + args= + for file + do + case $file in + -* | *.la | *.lo ) ;; + *) + # Do a test to see if this is really a libtool program. + if func_ltwrapper_script_p "$file"; then + func_source "$file" + # Transform arg to wrapped name. + file=$progdir/$program + elif func_ltwrapper_executable_p "$file"; then + func_ltwrapper_scriptname "$file" + func_source "$func_ltwrapper_scriptname_result" + # Transform arg to wrapped name. + file=$progdir/$program + fi + ;; + esac + # Quote arguments (to preserve shell metacharacters). + func_append_quoted args "$file" + done + + if $opt_dry_run; then + # Display what would be done. + if test -n "$shlibpath_var"; then + eval "\$ECHO \"\$shlibpath_var=\$$shlibpath_var\"" + echo "export $shlibpath_var" + fi + $ECHO "$cmd$args" + exit $EXIT_SUCCESS + else + if test -n "$shlibpath_var"; then + # Export the shlibpath_var. + eval "export $shlibpath_var" + fi + + # Restore saved environment variables + for lt_var in LANG LANGUAGE LC_ALL LC_CTYPE LC_COLLATE LC_MESSAGES + do + eval "if test \"\${save_$lt_var+set}\" = set; then + $lt_var=\$save_$lt_var; export $lt_var + else + $lt_unset $lt_var + fi" + done + + # Now prepare to actually exec the command. + exec_cmd=\$cmd$args + fi +} + +test execute = "$opt_mode" && func_mode_execute ${1+"$@"} + + +# func_mode_finish arg... +func_mode_finish () +{ + $debug_cmd + + libs= + libdirs= + admincmds= + + for opt in "$nonopt" ${1+"$@"} + do + if test -d "$opt"; then + func_append libdirs " $opt" + + elif test -f "$opt"; then + if func_lalib_unsafe_p "$opt"; then + func_append libs " $opt" + else + func_warning "'$opt' is not a valid libtool archive" + fi + + else + func_fatal_error "invalid argument '$opt'" + fi + done + + if test -n "$libs"; then + if test -n "$lt_sysroot"; then + sysroot_regex=`$ECHO "$lt_sysroot" | $SED "$sed_make_literal_regex"` + sysroot_cmd="s/\([ ']\)$sysroot_regex/\1/g;" + else + sysroot_cmd= + fi + + # Remove sysroot references + if $opt_dry_run; then + for lib in $libs; do + echo "removing references to $lt_sysroot and '=' prefixes from $lib" + done + else + tmpdir=`func_mktempdir` + for lib in $libs; do + $SED -e "$sysroot_cmd s/\([ ']-[LR]\)=/\1/g; s/\([ ']\)=/\1/g" $lib \ + > $tmpdir/tmp-la + mv -f $tmpdir/tmp-la $lib + done + ${RM}r "$tmpdir" + fi + fi + + if test -n "$finish_cmds$finish_eval" && test -n "$libdirs"; then + for libdir in $libdirs; do + if test -n "$finish_cmds"; then + # Do each command in the finish commands. + func_execute_cmds "$finish_cmds" 'admincmds="$admincmds +'"$cmd"'"' + fi + if test -n "$finish_eval"; then + # Do the single finish_eval. + eval cmds=\"$finish_eval\" + $opt_dry_run || eval "$cmds" || func_append admincmds " + $cmds" + fi + done + fi + + # Exit here if they wanted silent mode. + $opt_quiet && exit $EXIT_SUCCESS + + if test -n "$finish_cmds$finish_eval" && test -n "$libdirs"; then + echo "----------------------------------------------------------------------" + echo "Libraries have been installed in:" + for libdir in $libdirs; do + $ECHO " $libdir" + done + echo + echo "If you ever happen to want to link against installed libraries" + echo "in a given directory, LIBDIR, you must either use libtool, and" + echo "specify the full pathname of the library, or use the '-LLIBDIR'" + echo "flag during linking and do at least one of the following:" + if test -n "$shlibpath_var"; then + echo " - add LIBDIR to the '$shlibpath_var' environment variable" + echo " during execution" + fi + if test -n "$runpath_var"; then + echo " - add LIBDIR to the '$runpath_var' environment variable" + echo " during linking" + fi + if test -n "$hardcode_libdir_flag_spec"; then + libdir=LIBDIR + eval flag=\"$hardcode_libdir_flag_spec\" + + $ECHO " - use the '$flag' linker flag" + fi + if test -n "$admincmds"; then + $ECHO " - have your system administrator run these commands:$admincmds" + fi + if test -f /etc/ld.so.conf; then + echo " - have your system administrator add LIBDIR to '/etc/ld.so.conf'" + fi + echo + + echo "See any operating system documentation about shared libraries for" + case $host in + solaris2.[6789]|solaris2.1[0-9]) + echo "more information, such as the ld(1), crle(1) and ld.so(8) manual" + echo "pages." + ;; + *) + echo "more information, such as the ld(1) and ld.so(8) manual pages." + ;; + esac + echo "----------------------------------------------------------------------" + fi + exit $EXIT_SUCCESS +} + +test finish = "$opt_mode" && func_mode_finish ${1+"$@"} + + +# func_mode_install arg... +func_mode_install () +{ + $debug_cmd + + # There may be an optional sh(1) argument at the beginning of + # install_prog (especially on Windows NT). + if test "$SHELL" = "$nonopt" || test /bin/sh = "$nonopt" || + # Allow the use of GNU shtool's install command. + case $nonopt in *shtool*) :;; *) false;; esac + then + # Aesthetically quote it. + func_quote_arg pretty "$nonopt" + install_prog="$func_quote_arg_result " + arg=$1 + shift + else + install_prog= + arg=$nonopt + fi + + # The real first argument should be the name of the installation program. + # Aesthetically quote it. + func_quote_arg pretty "$arg" + func_append install_prog "$func_quote_arg_result" + install_shared_prog=$install_prog + case " $install_prog " in + *[\\\ /]cp\ *) install_cp=: ;; + *) install_cp=false ;; + esac + + # We need to accept at least all the BSD install flags. + dest= + files= + opts= + prev= + install_type= + isdir=false + stripme= + no_mode=: + for arg + do + arg2= + if test -n "$dest"; then + func_append files " $dest" + dest=$arg + continue + fi + + case $arg in + -d) isdir=: ;; + -f) + if $install_cp; then :; else + prev=$arg + fi + ;; + -g | -m | -o) + prev=$arg + ;; + -s) + stripme=" -s" + continue + ;; + -*) + ;; + *) + # If the previous option needed an argument, then skip it. + if test -n "$prev"; then + if test X-m = "X$prev" && test -n "$install_override_mode"; then + arg2=$install_override_mode + no_mode=false + fi + prev= + else + dest=$arg + continue + fi + ;; + esac + + # Aesthetically quote the argument. + func_quote_arg pretty "$arg" + func_append install_prog " $func_quote_arg_result" + if test -n "$arg2"; then + func_quote_arg pretty "$arg2" + fi + func_append install_shared_prog " $func_quote_arg_result" + done + + test -z "$install_prog" && \ + func_fatal_help "you must specify an install program" + + test -n "$prev" && \ + func_fatal_help "the '$prev' option requires an argument" + + if test -n "$install_override_mode" && $no_mode; then + if $install_cp; then :; else + func_quote_arg pretty "$install_override_mode" + func_append install_shared_prog " -m $func_quote_arg_result" + fi + fi + + if test -z "$files"; then + if test -z "$dest"; then + func_fatal_help "no file or destination specified" + else + func_fatal_help "you must specify a destination" + fi + fi + + # Strip any trailing slash from the destination. + func_stripname '' '/' "$dest" + dest=$func_stripname_result + + # Check to see that the destination is a directory. + test -d "$dest" && isdir=: + if $isdir; then + destdir=$dest + destname= + else + func_dirname_and_basename "$dest" "" "." + destdir=$func_dirname_result + destname=$func_basename_result + + # Not a directory, so check to see that there is only one file specified. + set dummy $files; shift + test "$#" -gt 1 && \ + func_fatal_help "'$dest' is not a directory" + fi + case $destdir in + [\\/]* | [A-Za-z]:[\\/]*) ;; + *) + for file in $files; do + case $file in + *.lo) ;; + *) + func_fatal_help "'$destdir' must be an absolute directory name" + ;; + esac + done + ;; + esac + + # This variable tells wrapper scripts just to set variables rather + # than running their programs. + libtool_install_magic=$magic + + staticlibs= + future_libdirs= + current_libdirs= + for file in $files; do + + # Do each installation. + case $file in + *.$libext) + # Do the static libraries later. + func_append staticlibs " $file" + ;; + + *.la) + func_resolve_sysroot "$file" + file=$func_resolve_sysroot_result + + # Check to see that this really is a libtool archive. + func_lalib_unsafe_p "$file" \ + || func_fatal_help "'$file' is not a valid libtool archive" + + library_names= + old_library= + relink_command= + func_source "$file" + + # Add the libdir to current_libdirs if it is the destination. + if test "X$destdir" = "X$libdir"; then + case "$current_libdirs " in + *" $libdir "*) ;; + *) func_append current_libdirs " $libdir" ;; + esac + else + # Note the libdir as a future libdir. + case "$future_libdirs " in + *" $libdir "*) ;; + *) func_append future_libdirs " $libdir" ;; + esac + fi + + func_dirname "$file" "/" "" + dir=$func_dirname_result + func_append dir "$objdir" + + if test -n "$relink_command"; then + # Determine the prefix the user has applied to our future dir. + inst_prefix_dir=`$ECHO "$destdir" | $SED -e "s%$libdir\$%%"` + + # Don't allow the user to place us outside of our expected + # location b/c this prevents finding dependent libraries that + # are installed to the same prefix. + # At present, this check doesn't affect windows .dll's that + # are installed into $libdir/../bin (currently, that works fine) + # but it's something to keep an eye on. + test "$inst_prefix_dir" = "$destdir" && \ + func_fatal_error "error: cannot install '$file' to a directory not ending in $libdir" + + if test -n "$inst_prefix_dir"; then + # Stick the inst_prefix_dir data into the link command. + relink_command=`$ECHO "$relink_command" | $SED "s%@inst_prefix_dir@%-inst-prefix-dir $inst_prefix_dir%"` + else + relink_command=`$ECHO "$relink_command" | $SED "s%@inst_prefix_dir@%%"` + fi + + func_warning "relinking '$file'" + func_show_eval "$relink_command" \ + 'func_fatal_error "error: relink '\''$file'\'' with the above command before installing it"' + fi + + # See the names of the shared library. + set dummy $library_names; shift + if test -n "$1"; then + realname=$1 + shift + + srcname=$realname + test -n "$relink_command" && srcname=${realname}T + + # Install the shared library and build the symlinks. + func_show_eval "$install_shared_prog $dir/$srcname $destdir/$realname" \ + 'exit $?' + tstripme=$stripme + case $host_os in + cygwin* | mingw* | pw32* | cegcc*) + case $realname in + *.dll.a) + tstripme= + ;; + esac + ;; + os2*) + case $realname in + *_dll.a) + tstripme= + ;; + esac + ;; + esac + if test -n "$tstripme" && test -n "$striplib"; then + func_show_eval "$striplib $destdir/$realname" 'exit $?' + fi + + if test "$#" -gt 0; then + # Delete the old symlinks, and create new ones. + # Try 'ln -sf' first, because the 'ln' binary might depend on + # the symlink we replace! Solaris /bin/ln does not understand -f, + # so we also need to try rm && ln -s. + for linkname + do + test "$linkname" != "$realname" \ + && func_show_eval "(cd $destdir && { $LN_S -f $realname $linkname || { $RM $linkname && $LN_S $realname $linkname; }; })" + done + fi + + # Do each command in the postinstall commands. + lib=$destdir/$realname + func_execute_cmds "$postinstall_cmds" 'exit $?' + fi + + # Install the pseudo-library for information purposes. + func_basename "$file" + name=$func_basename_result + instname=$dir/${name}i + func_show_eval "$install_prog $instname $destdir/$name" 'exit $?' + + # Maybe install the static library, too. + test -n "$old_library" && func_append staticlibs " $dir/$old_library" + ;; + + *.lo) + # Install (i.e. copy) a libtool object. + + # Figure out destination file name, if it wasn't already specified. + if test -n "$destname"; then + destfile=$destdir/$destname + else + func_basename "$file" + destfile=$func_basename_result + destfile=$destdir/$destfile + fi + + # Deduce the name of the destination old-style object file. + case $destfile in + *.lo) + func_lo2o "$destfile" + staticdest=$func_lo2o_result + ;; + *.$objext) + staticdest=$destfile + destfile= + ;; + *) + func_fatal_help "cannot copy a libtool object to '$destfile'" + ;; + esac + + # Install the libtool object if requested. + test -n "$destfile" && \ + func_show_eval "$install_prog $file $destfile" 'exit $?' + + # Install the old object if enabled. + if test yes = "$build_old_libs"; then + # Deduce the name of the old-style object file. + func_lo2o "$file" + staticobj=$func_lo2o_result + func_show_eval "$install_prog \$staticobj \$staticdest" 'exit $?' + fi + exit $EXIT_SUCCESS + ;; + + *) + # Figure out destination file name, if it wasn't already specified. + if test -n "$destname"; then + destfile=$destdir/$destname + else + func_basename "$file" + destfile=$func_basename_result + destfile=$destdir/$destfile + fi + + # If the file is missing, and there is a .exe on the end, strip it + # because it is most likely a libtool script we actually want to + # install + stripped_ext= + case $file in + *.exe) + if test ! -f "$file"; then + func_stripname '' '.exe' "$file" + file=$func_stripname_result + stripped_ext=.exe + fi + ;; + esac + + # Do a test to see if this is really a libtool program. + case $host in + *cygwin* | *mingw*) + if func_ltwrapper_executable_p "$file"; then + func_ltwrapper_scriptname "$file" + wrapper=$func_ltwrapper_scriptname_result + else + func_stripname '' '.exe' "$file" + wrapper=$func_stripname_result + fi + ;; + *) + wrapper=$file + ;; + esac + if func_ltwrapper_script_p "$wrapper"; then + notinst_deplibs= + relink_command= + + func_source "$wrapper" + + # Check the variables that should have been set. + test -z "$generated_by_libtool_version" && \ + func_fatal_error "invalid libtool wrapper script '$wrapper'" + + finalize=: + for lib in $notinst_deplibs; do + # Check to see that each library is installed. + libdir= + if test -f "$lib"; then + func_source "$lib" + fi + libfile=$libdir/`$ECHO "$lib" | $SED 's%^.*/%%g'` + if test -n "$libdir" && test ! -f "$libfile"; then + func_warning "'$lib' has not been installed in '$libdir'" + finalize=false + fi + done + + relink_command= + func_source "$wrapper" + + outputname= + if test no = "$fast_install" && test -n "$relink_command"; then + $opt_dry_run || { + if $finalize; then + tmpdir=`func_mktempdir` + func_basename "$file$stripped_ext" + file=$func_basename_result + outputname=$tmpdir/$file + # Replace the output file specification. + relink_command=`$ECHO "$relink_command" | $SED 's%@OUTPUT@%'"$outputname"'%g'` + + $opt_quiet || { + func_quote_arg expand,pretty "$relink_command" + eval "func_echo $func_quote_arg_result" + } + if eval "$relink_command"; then : + else + func_error "error: relink '$file' with the above command before installing it" + $opt_dry_run || ${RM}r "$tmpdir" + continue + fi + file=$outputname + else + func_warning "cannot relink '$file'" + fi + } + else + # Install the binary that we compiled earlier. + file=`$ECHO "$file$stripped_ext" | $SED "s%\([^/]*\)$%$objdir/\1%"` + fi + fi + + # remove .exe since cygwin /usr/bin/install will append another + # one anyway + case $install_prog,$host in + */usr/bin/install*,*cygwin*) + case $file:$destfile in + *.exe:*.exe) + # this is ok + ;; + *.exe:*) + destfile=$destfile.exe + ;; + *:*.exe) + func_stripname '' '.exe' "$destfile" + destfile=$func_stripname_result + ;; + esac + ;; + esac + func_show_eval "$install_prog\$stripme \$file \$destfile" 'exit $?' + $opt_dry_run || if test -n "$outputname"; then + ${RM}r "$tmpdir" + fi + ;; + esac + done + + for file in $staticlibs; do + func_basename "$file" + name=$func_basename_result + + # Set up the ranlib parameters. + oldlib=$destdir/$name + func_to_tool_file "$oldlib" func_convert_file_msys_to_w32 + tool_oldlib=$func_to_tool_file_result + + func_show_eval "$install_prog \$file \$oldlib" 'exit $?' + + if test -n "$stripme" && test -n "$old_striplib"; then + func_show_eval "$old_striplib $tool_oldlib" 'exit $?' + fi + + # Do each command in the postinstall commands. + func_execute_cmds "$old_postinstall_cmds" 'exit $?' + done + + test -n "$future_libdirs" && \ + func_warning "remember to run '$progname --finish$future_libdirs'" + + if test -n "$current_libdirs"; then + # Maybe just do a dry run. + $opt_dry_run && current_libdirs=" -n$current_libdirs" + exec_cmd='$SHELL "$progpath" $preserve_args --finish$current_libdirs' + else + exit $EXIT_SUCCESS + fi +} + +test install = "$opt_mode" && func_mode_install ${1+"$@"} + + +# func_generate_dlsyms outputname originator pic_p +# Extract symbols from dlprefiles and create ${outputname}S.o with +# a dlpreopen symbol table. +func_generate_dlsyms () +{ + $debug_cmd + + my_outputname=$1 + my_originator=$2 + my_pic_p=${3-false} + my_prefix=`$ECHO "$my_originator" | $SED 's%[^a-zA-Z0-9]%_%g'` + my_dlsyms= + + if test -n "$dlfiles$dlprefiles" || test no != "$dlself"; then + if test -n "$NM" && test -n "$global_symbol_pipe"; then + my_dlsyms=${my_outputname}S.c + else + func_error "not configured to extract global symbols from dlpreopened files" + fi + fi + + if test -n "$my_dlsyms"; then + case $my_dlsyms in + "") ;; + *.c) + # Discover the nlist of each of the dlfiles. + nlist=$output_objdir/$my_outputname.nm + + func_show_eval "$RM $nlist ${nlist}S ${nlist}T" + + # Parse the name list into a source file. + func_verbose "creating $output_objdir/$my_dlsyms" + + $opt_dry_run || $ECHO > "$output_objdir/$my_dlsyms" "\ +/* $my_dlsyms - symbol resolution table for '$my_outputname' dlsym emulation. */ +/* Generated by $PROGRAM (GNU $PACKAGE) $VERSION */ + +#ifdef __cplusplus +extern \"C\" { +#endif + +#if defined __GNUC__ && (((__GNUC__ == 4) && (__GNUC_MINOR__ >= 4)) || (__GNUC__ > 4)) +#pragma GCC diagnostic ignored \"-Wstrict-prototypes\" +#endif + +/* Keep this code in sync between libtool.m4, ltmain, lt_system.h, and tests. */ +#if defined _WIN32 || defined __CYGWIN__ || defined _WIN32_WCE +/* DATA imports from DLLs on WIN32 can't be const, because runtime + relocations are performed -- see ld's documentation on pseudo-relocs. */ +# define LT_DLSYM_CONST +#elif defined __osf__ +/* This system does not cope well with relocations in const data. */ +# define LT_DLSYM_CONST +#else +# define LT_DLSYM_CONST const +#endif + +#define STREQ(s1, s2) (strcmp ((s1), (s2)) == 0) + +/* External symbol declarations for the compiler. */\ +" + + if test yes = "$dlself"; then + func_verbose "generating symbol list for '$output'" + + $opt_dry_run || echo ': @PROGRAM@ ' > "$nlist" + + # Add our own program objects to the symbol list. + progfiles=`$ECHO "$objs$old_deplibs" | $SP2NL | $SED "$lo2o" | $NL2SP` + for progfile in $progfiles; do + func_to_tool_file "$progfile" func_convert_file_msys_to_w32 + func_verbose "extracting global C symbols from '$func_to_tool_file_result'" + $opt_dry_run || eval "$NM $func_to_tool_file_result | $global_symbol_pipe >> '$nlist'" + done + + if test -n "$exclude_expsyms"; then + $opt_dry_run || { + eval '$EGREP -v " ($exclude_expsyms)$" "$nlist" > "$nlist"T' + eval '$MV "$nlist"T "$nlist"' + } + fi + + if test -n "$export_symbols_regex"; then + $opt_dry_run || { + eval '$EGREP -e "$export_symbols_regex" "$nlist" > "$nlist"T' + eval '$MV "$nlist"T "$nlist"' + } + fi + + # Prepare the list of exported symbols + if test -z "$export_symbols"; then + export_symbols=$output_objdir/$outputname.exp + $opt_dry_run || { + $RM $export_symbols + eval "$SED -n -e '/^: @PROGRAM@ $/d' -e 's/^.* \(.*\)$/\1/p' "'< "$nlist" > "$export_symbols"' + case $host in + *cygwin* | *mingw* | *cegcc* ) + eval "echo EXPORTS "'> "$output_objdir/$outputname.def"' + eval 'cat "$export_symbols" >> "$output_objdir/$outputname.def"' + ;; + esac + } + else + $opt_dry_run || { + eval "$SED -e 's/\([].[*^$]\)/\\\\\1/g' -e 's/^/ /' -e 's/$/$/'"' < "$export_symbols" > "$output_objdir/$outputname.exp"' + eval '$GREP -f "$output_objdir/$outputname.exp" < "$nlist" > "$nlist"T' + eval '$MV "$nlist"T "$nlist"' + case $host in + *cygwin* | *mingw* | *cegcc* ) + eval "echo EXPORTS "'> "$output_objdir/$outputname.def"' + eval 'cat "$nlist" >> "$output_objdir/$outputname.def"' + ;; + esac + } + fi + fi + + for dlprefile in $dlprefiles; do + func_verbose "extracting global C symbols from '$dlprefile'" + func_basename "$dlprefile" + name=$func_basename_result + case $host in + *cygwin* | *mingw* | *cegcc* ) + # if an import library, we need to obtain dlname + if func_win32_import_lib_p "$dlprefile"; then + func_tr_sh "$dlprefile" + eval "curr_lafile=\$libfile_$func_tr_sh_result" + dlprefile_dlbasename= + if test -n "$curr_lafile" && func_lalib_p "$curr_lafile"; then + # Use subshell, to avoid clobbering current variable values + dlprefile_dlname=`source "$curr_lafile" && echo "$dlname"` + if test -n "$dlprefile_dlname"; then + func_basename "$dlprefile_dlname" + dlprefile_dlbasename=$func_basename_result + else + # no lafile. user explicitly requested -dlpreopen . + $sharedlib_from_linklib_cmd "$dlprefile" + dlprefile_dlbasename=$sharedlib_from_linklib_result + fi + fi + $opt_dry_run || { + if test -n "$dlprefile_dlbasename"; then + eval '$ECHO ": $dlprefile_dlbasename" >> "$nlist"' + else + func_warning "Could not compute DLL name from $name" + eval '$ECHO ": $name " >> "$nlist"' + fi + func_to_tool_file "$dlprefile" func_convert_file_msys_to_w32 + eval "$NM \"$func_to_tool_file_result\" 2>/dev/null | $global_symbol_pipe | + $SED -e '/I __imp/d' -e 's/I __nm_/D /;s/_nm__//' >> '$nlist'" + } + else # not an import lib + $opt_dry_run || { + eval '$ECHO ": $name " >> "$nlist"' + func_to_tool_file "$dlprefile" func_convert_file_msys_to_w32 + eval "$NM \"$func_to_tool_file_result\" 2>/dev/null | $global_symbol_pipe >> '$nlist'" + } + fi + ;; + *) + $opt_dry_run || { + eval '$ECHO ": $name " >> "$nlist"' + func_to_tool_file "$dlprefile" func_convert_file_msys_to_w32 + eval "$NM \"$func_to_tool_file_result\" 2>/dev/null | $global_symbol_pipe >> '$nlist'" + } + ;; + esac + done + + $opt_dry_run || { + # Make sure we have at least an empty file. + test -f "$nlist" || : > "$nlist" + + if test -n "$exclude_expsyms"; then + $EGREP -v " ($exclude_expsyms)$" "$nlist" > "$nlist"T + $MV "$nlist"T "$nlist" + fi + + # Try sorting and uniquifying the output. + if $GREP -v "^: " < "$nlist" | + if sort -k 3 /dev/null 2>&1; then + sort -k 3 + else + sort +2 + fi | + uniq > "$nlist"S; then + : + else + $GREP -v "^: " < "$nlist" > "$nlist"S + fi + + if test -f "$nlist"S; then + eval "$global_symbol_to_cdecl"' < "$nlist"S >> "$output_objdir/$my_dlsyms"' + else + echo '/* NONE */' >> "$output_objdir/$my_dlsyms" + fi + + func_show_eval '$RM "${nlist}I"' + if test -n "$global_symbol_to_import"; then + eval "$global_symbol_to_import"' < "$nlist"S > "$nlist"I' + fi + + echo >> "$output_objdir/$my_dlsyms" "\ + +/* The mapping between symbol names and symbols. */ +typedef struct { + const char *name; + void *address; +} lt_dlsymlist; +extern LT_DLSYM_CONST lt_dlsymlist +lt_${my_prefix}_LTX_preloaded_symbols[];\ +" + + if test -s "$nlist"I; then + echo >> "$output_objdir/$my_dlsyms" "\ +static void lt_syminit(void) +{ + LT_DLSYM_CONST lt_dlsymlist *symbol = lt_${my_prefix}_LTX_preloaded_symbols; + for (; symbol->name; ++symbol) + {" + $SED 's/.*/ if (STREQ (symbol->name, \"&\")) symbol->address = (void *) \&&;/' < "$nlist"I >> "$output_objdir/$my_dlsyms" + echo >> "$output_objdir/$my_dlsyms" "\ + } +}" + fi + echo >> "$output_objdir/$my_dlsyms" "\ +LT_DLSYM_CONST lt_dlsymlist +lt_${my_prefix}_LTX_preloaded_symbols[] = +{ {\"$my_originator\", (void *) 0}," + + if test -s "$nlist"I; then + echo >> "$output_objdir/$my_dlsyms" "\ + {\"@INIT@\", (void *) <_syminit}," + fi + + case $need_lib_prefix in + no) + eval "$global_symbol_to_c_name_address" < "$nlist" >> "$output_objdir/$my_dlsyms" + ;; + *) + eval "$global_symbol_to_c_name_address_lib_prefix" < "$nlist" >> "$output_objdir/$my_dlsyms" + ;; + esac + echo >> "$output_objdir/$my_dlsyms" "\ + {0, (void *) 0} +}; + +/* This works around a problem in FreeBSD linker */ +#ifdef FREEBSD_WORKAROUND +static const void *lt_preloaded_setup() { + return lt_${my_prefix}_LTX_preloaded_symbols; +} +#endif + +#ifdef __cplusplus +} +#endif\ +" + } # !$opt_dry_run + + pic_flag_for_symtable= + case "$compile_command " in + *" -static "*) ;; + *) + case $host in + # compiling the symbol table file with pic_flag works around + # a FreeBSD bug that causes programs to crash when -lm is + # linked before any other PIC object. But we must not use + # pic_flag when linking with -static. The problem exists in + # FreeBSD 2.2.6 and is fixed in FreeBSD 3.1. + *-*-freebsd2.*|*-*-freebsd3.0*|*-*-freebsdelf3.0*) + pic_flag_for_symtable=" $pic_flag -DFREEBSD_WORKAROUND" ;; + *-*-hpux*) + pic_flag_for_symtable=" $pic_flag" ;; + *) + $my_pic_p && pic_flag_for_symtable=" $pic_flag" + ;; + esac + ;; + esac + symtab_cflags= + for arg in $LTCFLAGS; do + case $arg in + -pie | -fpie | -fPIE) ;; + *) func_append symtab_cflags " $arg" ;; + esac + done + + # Now compile the dynamic symbol file. + func_show_eval '(cd $output_objdir && $LTCC$symtab_cflags -c$no_builtin_flag$pic_flag_for_symtable "$my_dlsyms")' 'exit $?' + + # Clean up the generated files. + func_show_eval '$RM "$output_objdir/$my_dlsyms" "$nlist" "${nlist}S" "${nlist}T" "${nlist}I"' + + # Transform the symbol file into the correct name. + symfileobj=$output_objdir/${my_outputname}S.$objext + case $host in + *cygwin* | *mingw* | *cegcc* ) + if test -f "$output_objdir/$my_outputname.def"; then + compile_command=`$ECHO "$compile_command" | $SED "s%@SYMFILE@%$output_objdir/$my_outputname.def $symfileobj%"` + finalize_command=`$ECHO "$finalize_command" | $SED "s%@SYMFILE@%$output_objdir/$my_outputname.def $symfileobj%"` + else + compile_command=`$ECHO "$compile_command" | $SED "s%@SYMFILE@%$symfileobj%"` + finalize_command=`$ECHO "$finalize_command" | $SED "s%@SYMFILE@%$symfileobj%"` + fi + ;; + *) + compile_command=`$ECHO "$compile_command" | $SED "s%@SYMFILE@%$symfileobj%"` + finalize_command=`$ECHO "$finalize_command" | $SED "s%@SYMFILE@%$symfileobj%"` + ;; + esac + ;; + *) + func_fatal_error "unknown suffix for '$my_dlsyms'" + ;; + esac + else + # We keep going just in case the user didn't refer to + # lt_preloaded_symbols. The linker will fail if global_symbol_pipe + # really was required. + + # Nullify the symbol file. + compile_command=`$ECHO "$compile_command" | $SED "s% @SYMFILE@%%"` + finalize_command=`$ECHO "$finalize_command" | $SED "s% @SYMFILE@%%"` + fi +} + +# func_cygming_gnu_implib_p ARG +# This predicate returns with zero status (TRUE) if +# ARG is a GNU/binutils-style import library. Returns +# with nonzero status (FALSE) otherwise. +func_cygming_gnu_implib_p () +{ + $debug_cmd + + func_to_tool_file "$1" func_convert_file_msys_to_w32 + func_cygming_gnu_implib_tmp=`$NM "$func_to_tool_file_result" | eval "$global_symbol_pipe" | $EGREP ' (_head_[A-Za-z0-9_]+_[ad]l*|[A-Za-z0-9_]+_[ad]l*_iname)$'` + test -n "$func_cygming_gnu_implib_tmp" +} + +# func_cygming_ms_implib_p ARG +# This predicate returns with zero status (TRUE) if +# ARG is an MS-style import library. Returns +# with nonzero status (FALSE) otherwise. +func_cygming_ms_implib_p () +{ + $debug_cmd + + func_to_tool_file "$1" func_convert_file_msys_to_w32 + func_cygming_ms_implib_tmp=`$NM "$func_to_tool_file_result" | eval "$global_symbol_pipe" | $GREP '_NULL_IMPORT_DESCRIPTOR'` + test -n "$func_cygming_ms_implib_tmp" +} + +# func_win32_libid arg +# return the library type of file 'arg' +# +# Need a lot of goo to handle *both* DLLs and import libs +# Has to be a shell function in order to 'eat' the argument +# that is supplied when $file_magic_command is called. +# Despite the name, also deal with 64 bit binaries. +func_win32_libid () +{ + $debug_cmd + + win32_libid_type=unknown + win32_fileres=`file -L $1 2>/dev/null` + case $win32_fileres in + *ar\ archive\ import\ library*) # definitely import + win32_libid_type="x86 archive import" + ;; + *ar\ archive*) # could be an import, or static + # Keep the egrep pattern in sync with the one in _LT_CHECK_MAGIC_METHOD. + if eval $OBJDUMP -f $1 | $SED -e '10q' 2>/dev/null | + $EGREP 'file format (pei*-i386(.*architecture: i386)?|pe-arm-wince|pe-x86-64)' >/dev/null; then + case $nm_interface in + "MS dumpbin") + if func_cygming_ms_implib_p "$1" || + func_cygming_gnu_implib_p "$1" + then + win32_nmres=import + else + win32_nmres= + fi + ;; + *) + func_to_tool_file "$1" func_convert_file_msys_to_w32 + win32_nmres=`eval $NM -f posix -A \"$func_to_tool_file_result\" | + $SED -n -e ' + 1,100{ + / I /{ + s|.*|import| + p + q + } + }'` + ;; + esac + case $win32_nmres in + import*) win32_libid_type="x86 archive import";; + *) win32_libid_type="x86 archive static";; + esac + fi + ;; + *DLL*) + win32_libid_type="x86 DLL" + ;; + *executable*) # but shell scripts are "executable" too... + case $win32_fileres in + *MS\ Windows\ PE\ Intel*) + win32_libid_type="x86 DLL" + ;; + esac + ;; + esac + $ECHO "$win32_libid_type" +} + +# func_cygming_dll_for_implib ARG +# +# Platform-specific function to extract the +# name of the DLL associated with the specified +# import library ARG. +# Invoked by eval'ing the libtool variable +# $sharedlib_from_linklib_cmd +# Result is available in the variable +# $sharedlib_from_linklib_result +func_cygming_dll_for_implib () +{ + $debug_cmd + + sharedlib_from_linklib_result=`$DLLTOOL --identify-strict --identify "$1"` +} + +# func_cygming_dll_for_implib_fallback_core SECTION_NAME LIBNAMEs +# +# The is the core of a fallback implementation of a +# platform-specific function to extract the name of the +# DLL associated with the specified import library LIBNAME. +# +# SECTION_NAME is either .idata$6 or .idata$7, depending +# on the platform and compiler that created the implib. +# +# Echos the name of the DLL associated with the +# specified import library. +func_cygming_dll_for_implib_fallback_core () +{ + $debug_cmd + + match_literal=`$ECHO "$1" | $SED "$sed_make_literal_regex"` + $OBJDUMP -s --section "$1" "$2" 2>/dev/null | + $SED '/^Contents of section '"$match_literal"':/{ + # Place marker at beginning of archive member dllname section + s/.*/====MARK====/ + p + d + } + # These lines can sometimes be longer than 43 characters, but + # are always uninteresting + /:[ ]*file format pe[i]\{,1\}-/d + /^In archive [^:]*:/d + # Ensure marker is printed + /^====MARK====/p + # Remove all lines with less than 43 characters + /^.\{43\}/!d + # From remaining lines, remove first 43 characters + s/^.\{43\}//' | + $SED -n ' + # Join marker and all lines until next marker into a single line + /^====MARK====/ b para + H + $ b para + b + :para + x + s/\n//g + # Remove the marker + s/^====MARK====// + # Remove trailing dots and whitespace + s/[\. \t]*$// + # Print + /./p' | + # we now have a list, one entry per line, of the stringified + # contents of the appropriate section of all members of the + # archive that possess that section. Heuristic: eliminate + # all those that have a first or second character that is + # a '.' (that is, objdump's representation of an unprintable + # character.) This should work for all archives with less than + # 0x302f exports -- but will fail for DLLs whose name actually + # begins with a literal '.' or a single character followed by + # a '.'. + # + # Of those that remain, print the first one. + $SED -e '/^\./d;/^.\./d;q' +} + +# func_cygming_dll_for_implib_fallback ARG +# Platform-specific function to extract the +# name of the DLL associated with the specified +# import library ARG. +# +# This fallback implementation is for use when $DLLTOOL +# does not support the --identify-strict option. +# Invoked by eval'ing the libtool variable +# $sharedlib_from_linklib_cmd +# Result is available in the variable +# $sharedlib_from_linklib_result +func_cygming_dll_for_implib_fallback () +{ + $debug_cmd + + if func_cygming_gnu_implib_p "$1"; then + # binutils import library + sharedlib_from_linklib_result=`func_cygming_dll_for_implib_fallback_core '.idata$7' "$1"` + elif func_cygming_ms_implib_p "$1"; then + # ms-generated import library + sharedlib_from_linklib_result=`func_cygming_dll_for_implib_fallback_core '.idata$6' "$1"` + else + # unknown + sharedlib_from_linklib_result= + fi +} + + +# func_extract_an_archive dir oldlib +func_extract_an_archive () +{ + $debug_cmd + + f_ex_an_ar_dir=$1; shift + f_ex_an_ar_oldlib=$1 + if test yes = "$lock_old_archive_extraction"; then + lockfile=$f_ex_an_ar_oldlib.lock + until $opt_dry_run || ln "$progpath" "$lockfile" 2>/dev/null; do + func_echo "Waiting for $lockfile to be removed" + sleep 2 + done + fi + func_show_eval "(cd \$f_ex_an_ar_dir && $AR x \"\$f_ex_an_ar_oldlib\")" \ + 'stat=$?; rm -f "$lockfile"; exit $stat' + if test yes = "$lock_old_archive_extraction"; then + $opt_dry_run || rm -f "$lockfile" + fi + if ($AR t "$f_ex_an_ar_oldlib" | sort | sort -uc >/dev/null 2>&1); then + : + else + func_fatal_error "object name conflicts in archive: $f_ex_an_ar_dir/$f_ex_an_ar_oldlib" + fi +} + + +# func_extract_archives gentop oldlib ... +func_extract_archives () +{ + $debug_cmd + + my_gentop=$1; shift + my_oldlibs=${1+"$@"} + my_oldobjs= + my_xlib= + my_xabs= + my_xdir= + + for my_xlib in $my_oldlibs; do + # Extract the objects. + case $my_xlib in + [\\/]* | [A-Za-z]:[\\/]*) my_xabs=$my_xlib ;; + *) my_xabs=`pwd`"/$my_xlib" ;; + esac + func_basename "$my_xlib" + my_xlib=$func_basename_result + my_xlib_u=$my_xlib + while :; do + case " $extracted_archives " in + *" $my_xlib_u "*) + func_arith $extracted_serial + 1 + extracted_serial=$func_arith_result + my_xlib_u=lt$extracted_serial-$my_xlib ;; + *) break ;; + esac + done + extracted_archives="$extracted_archives $my_xlib_u" + my_xdir=$my_gentop/$my_xlib_u + + func_mkdir_p "$my_xdir" + + case $host in + *-darwin*) + func_verbose "Extracting $my_xabs" + # Do not bother doing anything if just a dry run + $opt_dry_run || { + darwin_orig_dir=`pwd` + cd $my_xdir || exit $? + darwin_archive=$my_xabs + darwin_curdir=`pwd` + func_basename "$darwin_archive" + darwin_base_archive=$func_basename_result + darwin_arches=`$LIPO -info "$darwin_archive" 2>/dev/null | $GREP Architectures 2>/dev/null || true` + if test -n "$darwin_arches"; then + darwin_arches=`$ECHO "$darwin_arches" | $SED -e 's/.*are://'` + darwin_arch= + func_verbose "$darwin_base_archive has multiple architectures $darwin_arches" + for darwin_arch in $darwin_arches; do + func_mkdir_p "unfat-$$/$darwin_base_archive-$darwin_arch" + $LIPO -thin $darwin_arch -output "unfat-$$/$darwin_base_archive-$darwin_arch/$darwin_base_archive" "$darwin_archive" + cd "unfat-$$/$darwin_base_archive-$darwin_arch" + func_extract_an_archive "`pwd`" "$darwin_base_archive" + cd "$darwin_curdir" + $RM "unfat-$$/$darwin_base_archive-$darwin_arch/$darwin_base_archive" + done # $darwin_arches + ## Okay now we've a bunch of thin objects, gotta fatten them up :) + darwin_filelist=`find unfat-$$ -type f -name \*.o -print -o -name \*.lo -print | $SED -e "$sed_basename" | sort -u` + darwin_file= + darwin_files= + for darwin_file in $darwin_filelist; do + darwin_files=`find unfat-$$ -name $darwin_file -print | sort | $NL2SP` + $LIPO -create -output "$darwin_file" $darwin_files + done # $darwin_filelist + $RM -rf unfat-$$ + cd "$darwin_orig_dir" + else + cd $darwin_orig_dir + func_extract_an_archive "$my_xdir" "$my_xabs" + fi # $darwin_arches + } # !$opt_dry_run + ;; + *) + func_extract_an_archive "$my_xdir" "$my_xabs" + ;; + esac + my_oldobjs="$my_oldobjs "`find $my_xdir -name \*.$objext -print -o -name \*.lo -print | sort | $NL2SP` + done + + func_extract_archives_result=$my_oldobjs +} + + +# func_emit_wrapper [arg=no] +# +# Emit a libtool wrapper script on stdout. +# Don't directly open a file because we may want to +# incorporate the script contents within a cygwin/mingw +# wrapper executable. Must ONLY be called from within +# func_mode_link because it depends on a number of variables +# set therein. +# +# ARG is the value that the WRAPPER_SCRIPT_BELONGS_IN_OBJDIR +# variable will take. If 'yes', then the emitted script +# will assume that the directory where it is stored is +# the $objdir directory. This is a cygwin/mingw-specific +# behavior. +func_emit_wrapper () +{ + func_emit_wrapper_arg1=${1-no} + + $ECHO "\ +#! $SHELL + +# $output - temporary wrapper script for $objdir/$outputname +# Generated by $PROGRAM (GNU $PACKAGE) $VERSION +# +# The $output program cannot be directly executed until all the libtool +# libraries that it depends on are installed. +# +# This wrapper script should never be moved out of the build directory. +# If it is, it will not operate correctly. + +# Sed substitution that helps us do robust quoting. It backslashifies +# metacharacters that are still active within double-quoted strings. +sed_quote_subst='$sed_quote_subst' + +# Be Bourne compatible +if test -n \"\${ZSH_VERSION+set}\" && (emulate sh) >/dev/null 2>&1; then + emulate sh + NULLCMD=: + # Zsh 3.x and 4.x performs word splitting on \${1+\"\$@\"}, which + # is contrary to our usage. Disable this feature. + alias -g '\${1+\"\$@\"}'='\"\$@\"' + setopt NO_GLOB_SUBST +else + case \`(set -o) 2>/dev/null\` in *posix*) set -o posix;; esac +fi +BIN_SH=xpg4; export BIN_SH # for Tru64 +DUALCASE=1; export DUALCASE # for MKS sh + +# The HP-UX ksh and POSIX shell print the target directory to stdout +# if CDPATH is set. +(unset CDPATH) >/dev/null 2>&1 && unset CDPATH + +relink_command=\"$relink_command\" + +# This environment variable determines our operation mode. +if test \"\$libtool_install_magic\" = \"$magic\"; then + # install mode needs the following variables: + generated_by_libtool_version='$macro_version' + notinst_deplibs='$notinst_deplibs' +else + # When we are sourced in execute mode, \$file and \$ECHO are already set. + if test \"\$libtool_execute_magic\" != \"$magic\"; then + file=\"\$0\"" + + func_quote_arg pretty "$ECHO" + qECHO=$func_quote_arg_result + $ECHO "\ + +# A function that is used when there is no print builtin or printf. +func_fallback_echo () +{ + eval 'cat <<_LTECHO_EOF +\$1 +_LTECHO_EOF' +} + ECHO=$qECHO + fi + +# Very basic option parsing. These options are (a) specific to +# the libtool wrapper, (b) are identical between the wrapper +# /script/ and the wrapper /executable/ that is used only on +# windows platforms, and (c) all begin with the string "--lt-" +# (application programs are unlikely to have options that match +# this pattern). +# +# There are only two supported options: --lt-debug and +# --lt-dump-script. There is, deliberately, no --lt-help. +# +# The first argument to this parsing function should be the +# script's $0 value, followed by "$@". +lt_option_debug= +func_parse_lt_options () +{ + lt_script_arg0=\$0 + shift + for lt_opt + do + case \"\$lt_opt\" in + --lt-debug) lt_option_debug=1 ;; + --lt-dump-script) + lt_dump_D=\`\$ECHO \"X\$lt_script_arg0\" | $SED -e 's/^X//' -e 's%/[^/]*$%%'\` + test \"X\$lt_dump_D\" = \"X\$lt_script_arg0\" && lt_dump_D=. + lt_dump_F=\`\$ECHO \"X\$lt_script_arg0\" | $SED -e 's/^X//' -e 's%^.*/%%'\` + cat \"\$lt_dump_D/\$lt_dump_F\" + exit 0 + ;; + --lt-*) + \$ECHO \"Unrecognized --lt- option: '\$lt_opt'\" 1>&2 + exit 1 + ;; + esac + done + + # Print the debug banner immediately: + if test -n \"\$lt_option_debug\"; then + echo \"$outputname:$output:\$LINENO: libtool wrapper (GNU $PACKAGE) $VERSION\" 1>&2 + fi +} + +# Used when --lt-debug. Prints its arguments to stdout +# (redirection is the responsibility of the caller) +func_lt_dump_args () +{ + lt_dump_args_N=1; + for lt_arg + do + \$ECHO \"$outputname:$output:\$LINENO: newargv[\$lt_dump_args_N]: \$lt_arg\" + lt_dump_args_N=\`expr \$lt_dump_args_N + 1\` + done +} + +# Core function for launching the target application +func_exec_program_core () +{ +" + case $host in + # Backslashes separate directories on plain windows + *-*-mingw | *-*-os2* | *-cegcc*) + $ECHO "\ + if test -n \"\$lt_option_debug\"; then + \$ECHO \"$outputname:$output:\$LINENO: newargv[0]: \$progdir\\\\\$program\" 1>&2 + func_lt_dump_args \${1+\"\$@\"} 1>&2 + fi + exec \"\$progdir\\\\\$program\" \${1+\"\$@\"} +" + ;; + + *) + $ECHO "\ + if test -n \"\$lt_option_debug\"; then + \$ECHO \"$outputname:$output:\$LINENO: newargv[0]: \$progdir/\$program\" 1>&2 + func_lt_dump_args \${1+\"\$@\"} 1>&2 + fi + exec \"\$progdir/\$program\" \${1+\"\$@\"} +" + ;; + esac + $ECHO "\ + \$ECHO \"\$0: cannot exec \$program \$*\" 1>&2 + exit 1 +} + +# A function to encapsulate launching the target application +# Strips options in the --lt-* namespace from \$@ and +# launches target application with the remaining arguments. +func_exec_program () +{ + case \" \$* \" in + *\\ --lt-*) + for lt_wr_arg + do + case \$lt_wr_arg in + --lt-*) ;; + *) set x \"\$@\" \"\$lt_wr_arg\"; shift;; + esac + shift + done ;; + esac + func_exec_program_core \${1+\"\$@\"} +} + + # Parse options + func_parse_lt_options \"\$0\" \${1+\"\$@\"} + + # Find the directory that this script lives in. + thisdir=\`\$ECHO \"\$file\" | $SED 's%/[^/]*$%%'\` + test \"x\$thisdir\" = \"x\$file\" && thisdir=. + + # Follow symbolic links until we get to the real thisdir. + file=\`ls -ld \"\$file\" | $SED -n 's/.*-> //p'\` + while test -n \"\$file\"; do + destdir=\`\$ECHO \"\$file\" | $SED 's%/[^/]*\$%%'\` + + # If there was a directory component, then change thisdir. + if test \"x\$destdir\" != \"x\$file\"; then + case \"\$destdir\" in + [\\\\/]* | [A-Za-z]:[\\\\/]*) thisdir=\"\$destdir\" ;; + *) thisdir=\"\$thisdir/\$destdir\" ;; + esac + fi + + file=\`\$ECHO \"\$file\" | $SED 's%^.*/%%'\` + file=\`ls -ld \"\$thisdir/\$file\" | $SED -n 's/.*-> //p'\` + done + + # Usually 'no', except on cygwin/mingw when embedded into + # the cwrapper. + WRAPPER_SCRIPT_BELONGS_IN_OBJDIR=$func_emit_wrapper_arg1 + if test \"\$WRAPPER_SCRIPT_BELONGS_IN_OBJDIR\" = \"yes\"; then + # special case for '.' + if test \"\$thisdir\" = \".\"; then + thisdir=\`pwd\` + fi + # remove .libs from thisdir + case \"\$thisdir\" in + *[\\\\/]$objdir ) thisdir=\`\$ECHO \"\$thisdir\" | $SED 's%[\\\\/][^\\\\/]*$%%'\` ;; + $objdir ) thisdir=. ;; + esac + fi + + # Try to get the absolute directory name. + absdir=\`cd \"\$thisdir\" && pwd\` + test -n \"\$absdir\" && thisdir=\"\$absdir\" +" + + if test yes = "$fast_install"; then + $ECHO "\ + program=lt-'$outputname'$exeext + progdir=\"\$thisdir/$objdir\" + + if test ! -f \"\$progdir/\$program\" || + { file=\`ls -1dt \"\$progdir/\$program\" \"\$progdir/../\$program\" 2>/dev/null | $SED 1q\`; \\ + test \"X\$file\" != \"X\$progdir/\$program\"; }; then + + file=\"\$\$-\$program\" + + if test ! -d \"\$progdir\"; then + $MKDIR \"\$progdir\" + else + $RM \"\$progdir/\$file\" + fi" + + $ECHO "\ + + # relink executable if necessary + if test -n \"\$relink_command\"; then + if relink_command_output=\`eval \$relink_command 2>&1\`; then : + else + \$ECHO \"\$relink_command_output\" >&2 + $RM \"\$progdir/\$file\" + exit 1 + fi + fi + + $MV \"\$progdir/\$file\" \"\$progdir/\$program\" 2>/dev/null || + { $RM \"\$progdir/\$program\"; + $MV \"\$progdir/\$file\" \"\$progdir/\$program\"; } + $RM \"\$progdir/\$file\" + fi" + else + $ECHO "\ + program='$outputname' + progdir=\"\$thisdir/$objdir\" +" + fi + + $ECHO "\ + + if test -f \"\$progdir/\$program\"; then" + + # fixup the dll searchpath if we need to. + # + # Fix the DLL searchpath if we need to. Do this before prepending + # to shlibpath, because on Windows, both are PATH and uninstalled + # libraries must come first. + if test -n "$dllsearchpath"; then + $ECHO "\ + # Add the dll search path components to the executable PATH + PATH=$dllsearchpath:\$PATH +" + fi + + # Export our shlibpath_var if we have one. + if test yes = "$shlibpath_overrides_runpath" && test -n "$shlibpath_var" && test -n "$temp_rpath"; then + $ECHO "\ + # Add our own library path to $shlibpath_var + $shlibpath_var=\"$temp_rpath\$$shlibpath_var\" + + # Some systems cannot cope with colon-terminated $shlibpath_var + # The second colon is a workaround for a bug in BeOS R4 sed + $shlibpath_var=\`\$ECHO \"\$$shlibpath_var\" | $SED 's/::*\$//'\` + + export $shlibpath_var +" + fi + + $ECHO "\ + if test \"\$libtool_execute_magic\" != \"$magic\"; then + # Run the actual program with our arguments. + func_exec_program \${1+\"\$@\"} + fi + else + # The program doesn't exist. + \$ECHO \"\$0: error: '\$progdir/\$program' does not exist\" 1>&2 + \$ECHO \"This script is just a wrapper for \$program.\" 1>&2 + \$ECHO \"See the $PACKAGE documentation for more information.\" 1>&2 + exit 1 + fi +fi\ +" +} + + +# func_emit_cwrapperexe_src +# emit the source code for a wrapper executable on stdout +# Must ONLY be called from within func_mode_link because +# it depends on a number of variable set therein. +func_emit_cwrapperexe_src () +{ + cat < +#include +#ifdef _MSC_VER +# include +# include +# include +#else +# include +# include +# ifdef __CYGWIN__ +# include +# endif +#endif +#include +#include +#include +#include +#include +#include +#include +#include + +#define STREQ(s1, s2) (strcmp ((s1), (s2)) == 0) + +/* declarations of non-ANSI functions */ +#if defined __MINGW32__ +# ifdef __STRICT_ANSI__ +int _putenv (const char *); +# endif +#elif defined __CYGWIN__ +# ifdef __STRICT_ANSI__ +char *realpath (const char *, char *); +int putenv (char *); +int setenv (const char *, const char *, int); +# endif +/* #elif defined other_platform || defined ... */ +#endif + +/* portability defines, excluding path handling macros */ +#if defined _MSC_VER +# define setmode _setmode +# define stat _stat +# define chmod _chmod +# define getcwd _getcwd +# define putenv _putenv +# define S_IXUSR _S_IEXEC +#elif defined __MINGW32__ +# define setmode _setmode +# define stat _stat +# define chmod _chmod +# define getcwd _getcwd +# define putenv _putenv +#elif defined __CYGWIN__ +# define HAVE_SETENV +# define FOPEN_WB "wb" +/* #elif defined other platforms ... */ +#endif + +#if defined PATH_MAX +# define LT_PATHMAX PATH_MAX +#elif defined MAXPATHLEN +# define LT_PATHMAX MAXPATHLEN +#else +# define LT_PATHMAX 1024 +#endif + +#ifndef S_IXOTH +# define S_IXOTH 0 +#endif +#ifndef S_IXGRP +# define S_IXGRP 0 +#endif + +/* path handling portability macros */ +#ifndef DIR_SEPARATOR +# define DIR_SEPARATOR '/' +# define PATH_SEPARATOR ':' +#endif + +#if defined _WIN32 || defined __MSDOS__ || defined __DJGPP__ || \ + defined __OS2__ +# define HAVE_DOS_BASED_FILE_SYSTEM +# define FOPEN_WB "wb" +# ifndef DIR_SEPARATOR_2 +# define DIR_SEPARATOR_2 '\\' +# endif +# ifndef PATH_SEPARATOR_2 +# define PATH_SEPARATOR_2 ';' +# endif +#endif + +#ifndef DIR_SEPARATOR_2 +# define IS_DIR_SEPARATOR(ch) ((ch) == DIR_SEPARATOR) +#else /* DIR_SEPARATOR_2 */ +# define IS_DIR_SEPARATOR(ch) \ + (((ch) == DIR_SEPARATOR) || ((ch) == DIR_SEPARATOR_2)) +#endif /* DIR_SEPARATOR_2 */ + +#ifndef PATH_SEPARATOR_2 +# define IS_PATH_SEPARATOR(ch) ((ch) == PATH_SEPARATOR) +#else /* PATH_SEPARATOR_2 */ +# define IS_PATH_SEPARATOR(ch) ((ch) == PATH_SEPARATOR_2) +#endif /* PATH_SEPARATOR_2 */ + +#ifndef FOPEN_WB +# define FOPEN_WB "w" +#endif +#ifndef _O_BINARY +# define _O_BINARY 0 +#endif + +#define XMALLOC(type, num) ((type *) xmalloc ((num) * sizeof(type))) +#define XFREE(stale) do { \ + if (stale) { free (stale); stale = 0; } \ +} while (0) + +#if defined LT_DEBUGWRAPPER +static int lt_debug = 1; +#else +static int lt_debug = 0; +#endif + +const char *program_name = "libtool-wrapper"; /* in case xstrdup fails */ + +void *xmalloc (size_t num); +char *xstrdup (const char *string); +const char *base_name (const char *name); +char *find_executable (const char *wrapper); +char *chase_symlinks (const char *pathspec); +int make_executable (const char *path); +int check_executable (const char *path); +char *strendzap (char *str, const char *pat); +void lt_debugprintf (const char *file, int line, const char *fmt, ...); +void lt_fatal (const char *file, int line, const char *message, ...); +static const char *nonnull (const char *s); +static const char *nonempty (const char *s); +void lt_setenv (const char *name, const char *value); +char *lt_extend_str (const char *orig_value, const char *add, int to_end); +void lt_update_exe_path (const char *name, const char *value); +void lt_update_lib_path (const char *name, const char *value); +char **prepare_spawn (char **argv); +void lt_dump_script (FILE *f); +EOF + + cat <= 0) + && (st.st_mode & (S_IXUSR | S_IXGRP | S_IXOTH))) + return 1; + else + return 0; +} + +int +make_executable (const char *path) +{ + int rval = 0; + struct stat st; + + lt_debugprintf (__FILE__, __LINE__, "(make_executable): %s\n", + nonempty (path)); + if ((!path) || (!*path)) + return 0; + + if (stat (path, &st) >= 0) + { + rval = chmod (path, st.st_mode | S_IXOTH | S_IXGRP | S_IXUSR); + } + return rval; +} + +/* Searches for the full path of the wrapper. Returns + newly allocated full path name if found, NULL otherwise + Does not chase symlinks, even on platforms that support them. +*/ +char * +find_executable (const char *wrapper) +{ + int has_slash = 0; + const char *p; + const char *p_next; + /* static buffer for getcwd */ + char tmp[LT_PATHMAX + 1]; + size_t tmp_len; + char *concat_name; + + lt_debugprintf (__FILE__, __LINE__, "(find_executable): %s\n", + nonempty (wrapper)); + + if ((wrapper == NULL) || (*wrapper == '\0')) + return NULL; + + /* Absolute path? */ +#if defined HAVE_DOS_BASED_FILE_SYSTEM + if (isalpha ((unsigned char) wrapper[0]) && wrapper[1] == ':') + { + concat_name = xstrdup (wrapper); + if (check_executable (concat_name)) + return concat_name; + XFREE (concat_name); + } + else + { +#endif + if (IS_DIR_SEPARATOR (wrapper[0])) + { + concat_name = xstrdup (wrapper); + if (check_executable (concat_name)) + return concat_name; + XFREE (concat_name); + } +#if defined HAVE_DOS_BASED_FILE_SYSTEM + } +#endif + + for (p = wrapper; *p; p++) + if (*p == '/') + { + has_slash = 1; + break; + } + if (!has_slash) + { + /* no slashes; search PATH */ + const char *path = getenv ("PATH"); + if (path != NULL) + { + for (p = path; *p; p = p_next) + { + const char *q; + size_t p_len; + for (q = p; *q; q++) + if (IS_PATH_SEPARATOR (*q)) + break; + p_len = (size_t) (q - p); + p_next = (*q == '\0' ? q : q + 1); + if (p_len == 0) + { + /* empty path: current directory */ + if (getcwd (tmp, LT_PATHMAX) == NULL) + lt_fatal (__FILE__, __LINE__, "getcwd failed: %s", + nonnull (strerror (errno))); + tmp_len = strlen (tmp); + concat_name = + XMALLOC (char, tmp_len + 1 + strlen (wrapper) + 1); + memcpy (concat_name, tmp, tmp_len); + concat_name[tmp_len] = '/'; + strcpy (concat_name + tmp_len + 1, wrapper); + } + else + { + concat_name = + XMALLOC (char, p_len + 1 + strlen (wrapper) + 1); + memcpy (concat_name, p, p_len); + concat_name[p_len] = '/'; + strcpy (concat_name + p_len + 1, wrapper); + } + if (check_executable (concat_name)) + return concat_name; + XFREE (concat_name); + } + } + /* not found in PATH; assume curdir */ + } + /* Relative path | not found in path: prepend cwd */ + if (getcwd (tmp, LT_PATHMAX) == NULL) + lt_fatal (__FILE__, __LINE__, "getcwd failed: %s", + nonnull (strerror (errno))); + tmp_len = strlen (tmp); + concat_name = XMALLOC (char, tmp_len + 1 + strlen (wrapper) + 1); + memcpy (concat_name, tmp, tmp_len); + concat_name[tmp_len] = '/'; + strcpy (concat_name + tmp_len + 1, wrapper); + + if (check_executable (concat_name)) + return concat_name; + XFREE (concat_name); + return NULL; +} + +char * +chase_symlinks (const char *pathspec) +{ +#ifndef S_ISLNK + return xstrdup (pathspec); +#else + char buf[LT_PATHMAX]; + struct stat s; + char *tmp_pathspec = xstrdup (pathspec); + char *p; + int has_symlinks = 0; + while (strlen (tmp_pathspec) && !has_symlinks) + { + lt_debugprintf (__FILE__, __LINE__, + "checking path component for symlinks: %s\n", + tmp_pathspec); + if (lstat (tmp_pathspec, &s) == 0) + { + if (S_ISLNK (s.st_mode) != 0) + { + has_symlinks = 1; + break; + } + + /* search backwards for last DIR_SEPARATOR */ + p = tmp_pathspec + strlen (tmp_pathspec) - 1; + while ((p > tmp_pathspec) && (!IS_DIR_SEPARATOR (*p))) + p--; + if ((p == tmp_pathspec) && (!IS_DIR_SEPARATOR (*p))) + { + /* no more DIR_SEPARATORS left */ + break; + } + *p = '\0'; + } + else + { + lt_fatal (__FILE__, __LINE__, + "error accessing file \"%s\": %s", + tmp_pathspec, nonnull (strerror (errno))); + } + } + XFREE (tmp_pathspec); + + if (!has_symlinks) + { + return xstrdup (pathspec); + } + + tmp_pathspec = realpath (pathspec, buf); + if (tmp_pathspec == 0) + { + lt_fatal (__FILE__, __LINE__, + "could not follow symlinks for %s", pathspec); + } + return xstrdup (tmp_pathspec); +#endif +} + +char * +strendzap (char *str, const char *pat) +{ + size_t len, patlen; + + assert (str != NULL); + assert (pat != NULL); + + len = strlen (str); + patlen = strlen (pat); + + if (patlen <= len) + { + str += len - patlen; + if (STREQ (str, pat)) + *str = '\0'; + } + return str; +} + +void +lt_debugprintf (const char *file, int line, const char *fmt, ...) +{ + va_list args; + if (lt_debug) + { + (void) fprintf (stderr, "%s:%s:%d: ", program_name, file, line); + va_start (args, fmt); + (void) vfprintf (stderr, fmt, args); + va_end (args); + } +} + +static void +lt_error_core (int exit_status, const char *file, + int line, const char *mode, + const char *message, va_list ap) +{ + fprintf (stderr, "%s:%s:%d: %s: ", program_name, file, line, mode); + vfprintf (stderr, message, ap); + fprintf (stderr, ".\n"); + + if (exit_status >= 0) + exit (exit_status); +} + +void +lt_fatal (const char *file, int line, const char *message, ...) +{ + va_list ap; + va_start (ap, message); + lt_error_core (EXIT_FAILURE, file, line, "FATAL", message, ap); + va_end (ap); +} + +static const char * +nonnull (const char *s) +{ + return s ? s : "(null)"; +} + +static const char * +nonempty (const char *s) +{ + return (s && !*s) ? "(empty)" : nonnull (s); +} + +void +lt_setenv (const char *name, const char *value) +{ + lt_debugprintf (__FILE__, __LINE__, + "(lt_setenv) setting '%s' to '%s'\n", + nonnull (name), nonnull (value)); + { +#ifdef HAVE_SETENV + /* always make a copy, for consistency with !HAVE_SETENV */ + char *str = xstrdup (value); + setenv (name, str, 1); +#else + size_t len = strlen (name) + 1 + strlen (value) + 1; + char *str = XMALLOC (char, len); + sprintf (str, "%s=%s", name, value); + if (putenv (str) != EXIT_SUCCESS) + { + XFREE (str); + } +#endif + } +} + +char * +lt_extend_str (const char *orig_value, const char *add, int to_end) +{ + char *new_value; + if (orig_value && *orig_value) + { + size_t orig_value_len = strlen (orig_value); + size_t add_len = strlen (add); + new_value = XMALLOC (char, add_len + orig_value_len + 1); + if (to_end) + { + strcpy (new_value, orig_value); + strcpy (new_value + orig_value_len, add); + } + else + { + strcpy (new_value, add); + strcpy (new_value + add_len, orig_value); + } + } + else + { + new_value = xstrdup (add); + } + return new_value; +} + +void +lt_update_exe_path (const char *name, const char *value) +{ + lt_debugprintf (__FILE__, __LINE__, + "(lt_update_exe_path) modifying '%s' by prepending '%s'\n", + nonnull (name), nonnull (value)); + + if (name && *name && value && *value) + { + char *new_value = lt_extend_str (getenv (name), value, 0); + /* some systems can't cope with a ':'-terminated path #' */ + size_t len = strlen (new_value); + while ((len > 0) && IS_PATH_SEPARATOR (new_value[len-1])) + { + new_value[--len] = '\0'; + } + lt_setenv (name, new_value); + XFREE (new_value); + } +} + +void +lt_update_lib_path (const char *name, const char *value) +{ + lt_debugprintf (__FILE__, __LINE__, + "(lt_update_lib_path) modifying '%s' by prepending '%s'\n", + nonnull (name), nonnull (value)); + + if (name && *name && value && *value) + { + char *new_value = lt_extend_str (getenv (name), value, 0); + lt_setenv (name, new_value); + XFREE (new_value); + } +} + +EOF + case $host_os in + mingw*) + cat <<"EOF" + +/* Prepares an argument vector before calling spawn(). + Note that spawn() does not by itself call the command interpreter + (getenv ("COMSPEC") != NULL ? getenv ("COMSPEC") : + ({ OSVERSIONINFO v; v.dwOSVersionInfoSize = sizeof(OSVERSIONINFO); + GetVersionEx(&v); + v.dwPlatformId == VER_PLATFORM_WIN32_NT; + }) ? "cmd.exe" : "command.com"). + Instead it simply concatenates the arguments, separated by ' ', and calls + CreateProcess(). We must quote the arguments since Win32 CreateProcess() + interprets characters like ' ', '\t', '\\', '"' (but not '<' and '>') in a + special way: + - Space and tab are interpreted as delimiters. They are not treated as + delimiters if they are surrounded by double quotes: "...". + - Unescaped double quotes are removed from the input. Their only effect is + that within double quotes, space and tab are treated like normal + characters. + - Backslashes not followed by double quotes are not special. + - But 2*n+1 backslashes followed by a double quote become + n backslashes followed by a double quote (n >= 0): + \" -> " + \\\" -> \" + \\\\\" -> \\" + */ +#define SHELL_SPECIAL_CHARS "\"\\ \001\002\003\004\005\006\007\010\011\012\013\014\015\016\017\020\021\022\023\024\025\026\027\030\031\032\033\034\035\036\037" +#define SHELL_SPACE_CHARS " \001\002\003\004\005\006\007\010\011\012\013\014\015\016\017\020\021\022\023\024\025\026\027\030\031\032\033\034\035\036\037" +char ** +prepare_spawn (char **argv) +{ + size_t argc; + char **new_argv; + size_t i; + + /* Count number of arguments. */ + for (argc = 0; argv[argc] != NULL; argc++) + ; + + /* Allocate new argument vector. */ + new_argv = XMALLOC (char *, argc + 1); + + /* Put quoted arguments into the new argument vector. */ + for (i = 0; i < argc; i++) + { + const char *string = argv[i]; + + if (string[0] == '\0') + new_argv[i] = xstrdup ("\"\""); + else if (strpbrk (string, SHELL_SPECIAL_CHARS) != NULL) + { + int quote_around = (strpbrk (string, SHELL_SPACE_CHARS) != NULL); + size_t length; + unsigned int backslashes; + const char *s; + char *quoted_string; + char *p; + + length = 0; + backslashes = 0; + if (quote_around) + length++; + for (s = string; *s != '\0'; s++) + { + char c = *s; + if (c == '"') + length += backslashes + 1; + length++; + if (c == '\\') + backslashes++; + else + backslashes = 0; + } + if (quote_around) + length += backslashes + 1; + + quoted_string = XMALLOC (char, length + 1); + + p = quoted_string; + backslashes = 0; + if (quote_around) + *p++ = '"'; + for (s = string; *s != '\0'; s++) + { + char c = *s; + if (c == '"') + { + unsigned int j; + for (j = backslashes + 1; j > 0; j--) + *p++ = '\\'; + } + *p++ = c; + if (c == '\\') + backslashes++; + else + backslashes = 0; + } + if (quote_around) + { + unsigned int j; + for (j = backslashes; j > 0; j--) + *p++ = '\\'; + *p++ = '"'; + } + *p = '\0'; + + new_argv[i] = quoted_string; + } + else + new_argv[i] = (char *) string; + } + new_argv[argc] = NULL; + + return new_argv; +} +EOF + ;; + esac + + cat <<"EOF" +void lt_dump_script (FILE* f) +{ +EOF + func_emit_wrapper yes | + $SED -n -e ' +s/^\(.\{79\}\)\(..*\)/\1\ +\2/ +h +s/\([\\"]\)/\\\1/g +s/$/\\n/ +s/\([^\n]*\).*/ fputs ("\1", f);/p +g +D' + cat <<"EOF" +} +EOF +} +# end: func_emit_cwrapperexe_src + +# func_win32_import_lib_p ARG +# True if ARG is an import lib, as indicated by $file_magic_cmd +func_win32_import_lib_p () +{ + $debug_cmd + + case `eval $file_magic_cmd \"\$1\" 2>/dev/null | $SED -e 10q` in + *import*) : ;; + *) false ;; + esac +} + +# func_suncc_cstd_abi +# !!ONLY CALL THIS FOR SUN CC AFTER $compile_command IS FULLY EXPANDED!! +# Several compiler flags select an ABI that is incompatible with the +# Cstd library. Avoid specifying it if any are in CXXFLAGS. +func_suncc_cstd_abi () +{ + $debug_cmd + + case " $compile_command " in + *" -compat=g "*|*\ -std=c++[0-9][0-9]\ *|*" -library=stdcxx4 "*|*" -library=stlport4 "*) + suncc_use_cstd_abi=no + ;; + *) + suncc_use_cstd_abi=yes + ;; + esac +} + +# func_mode_link arg... +func_mode_link () +{ + $debug_cmd + + case $host in + *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-cegcc*) + # It is impossible to link a dll without this setting, and + # we shouldn't force the makefile maintainer to figure out + # what system we are compiling for in order to pass an extra + # flag for every libtool invocation. + # allow_undefined=no + + # FIXME: Unfortunately, there are problems with the above when trying + # to make a dll that has undefined symbols, in which case not + # even a static library is built. For now, we need to specify + # -no-undefined on the libtool link line when we can be certain + # that all symbols are satisfied, otherwise we get a static library. + allow_undefined=yes + ;; + *) + allow_undefined=yes + ;; + esac + libtool_args=$nonopt + base_compile="$nonopt $@" + compile_command=$nonopt + finalize_command=$nonopt + + compile_rpath= + finalize_rpath= + compile_shlibpath= + finalize_shlibpath= + convenience= + old_convenience= + deplibs= + old_deplibs= + compiler_flags= + linker_flags= + dllsearchpath= + lib_search_path=`pwd` + inst_prefix_dir= + new_inherited_linker_flags= + + avoid_version=no + bindir= + dlfiles= + dlprefiles= + dlself=no + export_dynamic=no + export_symbols= + export_symbols_regex= + generated= + libobjs= + ltlibs= + module=no + no_install=no + objs= + os2dllname= + non_pic_objects= + precious_files_regex= + prefer_static_libs=no + preload=false + prev= + prevarg= + release= + rpath= + xrpath= + perm_rpath= + temp_rpath= + thread_safe=no + vinfo= + vinfo_number=no + weak_libs= + single_module=$wl-single_module + func_infer_tag $base_compile + + # We need to know -static, to get the right output filenames. + for arg + do + case $arg in + -shared) + test yes != "$build_libtool_libs" \ + && func_fatal_configuration "cannot build a shared library" + build_old_libs=no + break + ;; + -all-static | -static | -static-libtool-libs) + case $arg in + -all-static) + if test yes = "$build_libtool_libs" && test -z "$link_static_flag"; then + func_warning "complete static linking is impossible in this configuration" + fi + if test -n "$link_static_flag"; then + dlopen_self=$dlopen_self_static + fi + prefer_static_libs=yes + ;; + -static) + if test -z "$pic_flag" && test -n "$link_static_flag"; then + dlopen_self=$dlopen_self_static + fi + prefer_static_libs=built + ;; + -static-libtool-libs) + if test -z "$pic_flag" && test -n "$link_static_flag"; then + dlopen_self=$dlopen_self_static + fi + prefer_static_libs=yes + ;; + esac + build_libtool_libs=no + build_old_libs=yes + break + ;; + esac + done + + # See if our shared archives depend on static archives. + test -n "$old_archive_from_new_cmds" && build_old_libs=yes + + # Go through the arguments, transforming them on the way. + while test "$#" -gt 0; do + arg=$1 + shift + func_quote_arg pretty,unquoted "$arg" + qarg=$func_quote_arg_unquoted_result + func_append libtool_args " $func_quote_arg_result" + + # If the previous option needs an argument, assign it. + if test -n "$prev"; then + case $prev in + output) + func_append compile_command " @OUTPUT@" + func_append finalize_command " @OUTPUT@" + ;; + esac + + case $prev in + bindir) + bindir=$arg + prev= + continue + ;; + dlfiles|dlprefiles) + $preload || { + # Add the symbol object into the linking commands. + func_append compile_command " @SYMFILE@" + func_append finalize_command " @SYMFILE@" + preload=: + } + case $arg in + *.la | *.lo) ;; # We handle these cases below. + force) + if test no = "$dlself"; then + dlself=needless + export_dynamic=yes + fi + prev= + continue + ;; + self) + if test dlprefiles = "$prev"; then + dlself=yes + elif test dlfiles = "$prev" && test yes != "$dlopen_self"; then + dlself=yes + else + dlself=needless + export_dynamic=yes + fi + prev= + continue + ;; + *) + if test dlfiles = "$prev"; then + func_append dlfiles " $arg" + else + func_append dlprefiles " $arg" + fi + prev= + continue + ;; + esac + ;; + expsyms) + export_symbols=$arg + test -f "$arg" \ + || func_fatal_error "symbol file '$arg' does not exist" + prev= + continue + ;; + expsyms_regex) + export_symbols_regex=$arg + prev= + continue + ;; + framework) + case $host in + *-*-darwin*) + case "$deplibs " in + *" $qarg.ltframework "*) ;; + *) func_append deplibs " $qarg.ltframework" # this is fixed later + ;; + esac + ;; + esac + prev= + continue + ;; + inst_prefix) + inst_prefix_dir=$arg + prev= + continue + ;; + mllvm) + # Clang does not use LLVM to link, so we can simply discard any + # '-mllvm $arg' options when doing the link step. + prev= + continue + ;; + objectlist) + if test -f "$arg"; then + save_arg=$arg + moreargs= + for fil in `cat "$save_arg"` + do +# func_append moreargs " $fil" + arg=$fil + # A libtool-controlled object. + + # Check to see that this really is a libtool object. + if func_lalib_unsafe_p "$arg"; then + pic_object= + non_pic_object= + + # Read the .lo file + func_source "$arg" + + if test -z "$pic_object" || + test -z "$non_pic_object" || + test none = "$pic_object" && + test none = "$non_pic_object"; then + func_fatal_error "cannot find name of object for '$arg'" + fi + + # Extract subdirectory from the argument. + func_dirname "$arg" "/" "" + xdir=$func_dirname_result + + if test none != "$pic_object"; then + # Prepend the subdirectory the object is found in. + pic_object=$xdir$pic_object + + if test dlfiles = "$prev"; then + if test yes = "$build_libtool_libs" && test yes = "$dlopen_support"; then + func_append dlfiles " $pic_object" + prev= + continue + else + # If libtool objects are unsupported, then we need to preload. + prev=dlprefiles + fi + fi + + # CHECK ME: I think I busted this. -Ossama + if test dlprefiles = "$prev"; then + # Preload the old-style object. + func_append dlprefiles " $pic_object" + prev= + fi + + # A PIC object. + func_append libobjs " $pic_object" + arg=$pic_object + fi + + # Non-PIC object. + if test none != "$non_pic_object"; then + # Prepend the subdirectory the object is found in. + non_pic_object=$xdir$non_pic_object + + # A standard non-PIC object + func_append non_pic_objects " $non_pic_object" + if test -z "$pic_object" || test none = "$pic_object"; then + arg=$non_pic_object + fi + else + # If the PIC object exists, use it instead. + # $xdir was prepended to $pic_object above. + non_pic_object=$pic_object + func_append non_pic_objects " $non_pic_object" + fi + else + # Only an error if not doing a dry-run. + if $opt_dry_run; then + # Extract subdirectory from the argument. + func_dirname "$arg" "/" "" + xdir=$func_dirname_result + + func_lo2o "$arg" + pic_object=$xdir$objdir/$func_lo2o_result + non_pic_object=$xdir$func_lo2o_result + func_append libobjs " $pic_object" + func_append non_pic_objects " $non_pic_object" + else + func_fatal_error "'$arg' is not a valid libtool object" + fi + fi + done + else + func_fatal_error "link input file '$arg' does not exist" + fi + arg=$save_arg + prev= + continue + ;; + os2dllname) + os2dllname=$arg + prev= + continue + ;; + precious_regex) + precious_files_regex=$arg + prev= + continue + ;; + release) + release=-$arg + prev= + continue + ;; + rpath | xrpath) + # We need an absolute path. + case $arg in + [\\/]* | [A-Za-z]:[\\/]*) ;; + *) + func_fatal_error "only absolute run-paths are allowed" + ;; + esac + if test rpath = "$prev"; then + case "$rpath " in + *" $arg "*) ;; + *) func_append rpath " $arg" ;; + esac + else + case "$xrpath " in + *" $arg "*) ;; + *) func_append xrpath " $arg" ;; + esac + fi + prev= + continue + ;; + shrext) + shrext_cmds=$arg + prev= + continue + ;; + weak) + func_append weak_libs " $arg" + prev= + continue + ;; + xassembler) + func_append compiler_flags " -Xassembler $qarg" + prev= + func_append compile_command " -Xassembler $qarg" + func_append finalize_command " -Xassembler $qarg" + continue + ;; + xcclinker) + func_append linker_flags " $qarg" + func_append compiler_flags " $qarg" + prev= + func_append compile_command " $qarg" + func_append finalize_command " $qarg" + continue + ;; + xcompiler) + func_append compiler_flags " $qarg" + prev= + func_append compile_command " $qarg" + func_append finalize_command " $qarg" + continue + ;; + xlinker) + func_append linker_flags " $qarg" + func_append compiler_flags " $wl$qarg" + prev= + func_append compile_command " $wl$qarg" + func_append finalize_command " $wl$qarg" + continue + ;; + *) + eval "$prev=\"\$arg\"" + prev= + continue + ;; + esac + fi # test -n "$prev" + + prevarg=$arg + + case $arg in + -all-static) + if test -n "$link_static_flag"; then + # See comment for -static flag below, for more details. + func_append compile_command " $link_static_flag" + func_append finalize_command " $link_static_flag" + fi + continue + ;; + + -allow-undefined) + # FIXME: remove this flag sometime in the future. + func_fatal_error "'-allow-undefined' must not be used because it is the default" + ;; + + -avoid-version) + avoid_version=yes + continue + ;; + + -bindir) + prev=bindir + continue + ;; + + -dlopen) + prev=dlfiles + continue + ;; + + -dlpreopen) + prev=dlprefiles + continue + ;; + + -export-dynamic) + export_dynamic=yes + continue + ;; + + -export-symbols | -export-symbols-regex) + if test -n "$export_symbols" || test -n "$export_symbols_regex"; then + func_fatal_error "more than one -exported-symbols argument is not allowed" + fi + if test X-export-symbols = "X$arg"; then + prev=expsyms + else + prev=expsyms_regex + fi + continue + ;; + + -framework) + prev=framework + continue + ;; + + -inst-prefix-dir) + prev=inst_prefix + continue + ;; + + # The native IRIX linker understands -LANG:*, -LIST:* and -LNO:* + # so, if we see these flags be careful not to treat them like -L + -L[A-Z][A-Z]*:*) + case $with_gcc/$host in + no/*-*-irix* | /*-*-irix*) + func_append compile_command " $arg" + func_append finalize_command " $arg" + ;; + esac + continue + ;; + + -L*) + func_stripname "-L" '' "$arg" + if test -z "$func_stripname_result"; then + if test "$#" -gt 0; then + func_fatal_error "require no space between '-L' and '$1'" + else + func_fatal_error "need path for '-L' option" + fi + fi + func_resolve_sysroot "$func_stripname_result" + dir=$func_resolve_sysroot_result + # We need an absolute path. + case $dir in + [\\/]* | [A-Za-z]:[\\/]*) ;; + *) + absdir=`cd "$dir" && pwd` + test -z "$absdir" && \ + func_fatal_error "cannot determine absolute directory name of '$dir'" + dir=$absdir + ;; + esac + case "$deplibs " in + *" -L$dir "* | *" $arg "*) + # Will only happen for absolute or sysroot arguments + ;; + *) + # Preserve sysroot, but never include relative directories + case $dir in + [\\/]* | [A-Za-z]:[\\/]* | =*) func_append deplibs " $arg" ;; + *) func_append deplibs " -L$dir" ;; + esac + func_append lib_search_path " $dir" + ;; + esac + case $host in + *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-cegcc*) + testbindir=`$ECHO "$dir" | $SED 's*/lib$*/bin*'` + case :$dllsearchpath: in + *":$dir:"*) ;; + ::) dllsearchpath=$dir;; + *) func_append dllsearchpath ":$dir";; + esac + case :$dllsearchpath: in + *":$testbindir:"*) ;; + ::) dllsearchpath=$testbindir;; + *) func_append dllsearchpath ":$testbindir";; + esac + ;; + esac + continue + ;; + + -l*) + if test X-lc = "X$arg" || test X-lm = "X$arg"; then + case $host in + *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-beos* | *-cegcc* | *-*-haiku*) + # These systems don't actually have a C or math library (as such) + continue + ;; + *-*-os2*) + # These systems don't actually have a C library (as such) + test X-lc = "X$arg" && continue + ;; + *-*-openbsd* | *-*-freebsd* | *-*-dragonfly* | *-*-bitrig* | *-*-midnightbsd*) + # Do not include libc due to us having libc/libc_r. + test X-lc = "X$arg" && continue + ;; + *-*-rhapsody* | *-*-darwin1.[012]) + # Rhapsody C and math libraries are in the System framework + func_append deplibs " System.ltframework" + continue + ;; + *-*-sco3.2v5* | *-*-sco5v6*) + # Causes problems with __ctype + test X-lc = "X$arg" && continue + ;; + *-*-sysv4.2uw2* | *-*-sysv5* | *-*-unixware* | *-*-OpenUNIX*) + # Compiler inserts libc in the correct place for threads to work + test X-lc = "X$arg" && continue + ;; + esac + elif test X-lc_r = "X$arg"; then + case $host in + *-*-openbsd* | *-*-freebsd* | *-*-dragonfly* | *-*-bitrig* | *-*-midnightbsd*) + # Do not include libc_r directly, use -pthread flag. + continue + ;; + esac + fi + func_append deplibs " $arg" + continue + ;; + + -mllvm) + prev=mllvm + continue + ;; + + -module) + module=yes + continue + ;; + + # Tru64 UNIX uses -model [arg] to determine the layout of C++ + # classes, name mangling, and exception handling. + # Darwin uses the -arch flag to determine output architecture. + -model|-arch|-isysroot|--sysroot) + func_append compiler_flags " $arg" + func_append compile_command " $arg" + func_append finalize_command " $arg" + prev=xcompiler + continue + ;; + # Solaris ld rejects as of 11.4. Refer to Oracle bug 22985199. + -pthread) + case $host in + *solaris2*) ;; + *) + case "$new_inherited_linker_flags " in + *" $arg "*) ;; + * ) func_append new_inherited_linker_flags " $arg" ;; + esac + ;; + esac + continue + ;; + -mt|-mthreads|-kthread|-Kthread|-pthreads|--thread-safe \ + |-threads|-fopenmp|-openmp|-mp|-xopenmp|-omp|-qsmp=*) + func_append compiler_flags " $arg" + func_append compile_command " $arg" + func_append finalize_command " $arg" + case "$new_inherited_linker_flags " in + *" $arg "*) ;; + * ) func_append new_inherited_linker_flags " $arg" ;; + esac + continue + ;; + + -multi_module) + single_module=$wl-multi_module + continue + ;; + + -no-fast-install) + fast_install=no + continue + ;; + + -no-install) + case $host in + *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-*-darwin* | *-cegcc*) + # The PATH hackery in wrapper scripts is required on Windows + # and Darwin in order for the loader to find any dlls it needs. + func_warning "'-no-install' is ignored for $host" + func_warning "assuming '-no-fast-install' instead" + fast_install=no + ;; + *) no_install=yes ;; + esac + continue + ;; + + -no-undefined) + allow_undefined=no + continue + ;; + + -objectlist) + prev=objectlist + continue + ;; + + -os2dllname) + prev=os2dllname + continue + ;; + + -o) prev=output ;; + + -precious-files-regex) + prev=precious_regex + continue + ;; + + -release) + prev=release + continue + ;; + + -rpath) + prev=rpath + continue + ;; + + -R) + prev=xrpath + continue + ;; + + -R*) + func_stripname '-R' '' "$arg" + dir=$func_stripname_result + # We need an absolute path. + case $dir in + [\\/]* | [A-Za-z]:[\\/]*) ;; + =*) + func_stripname '=' '' "$dir" + dir=$lt_sysroot$func_stripname_result + ;; + *) + func_fatal_error "only absolute run-paths are allowed" + ;; + esac + case "$xrpath " in + *" $dir "*) ;; + *) func_append xrpath " $dir" ;; + esac + continue + ;; + + -shared) + # The effects of -shared are defined in a previous loop. + continue + ;; + + -shrext) + prev=shrext + continue + ;; + + -static | -static-libtool-libs) + # The effects of -static are defined in a previous loop. + # We used to do the same as -all-static on platforms that + # didn't have a PIC flag, but the assumption that the effects + # would be equivalent was wrong. It would break on at least + # Digital Unix and AIX. + continue + ;; + + -thread-safe) + thread_safe=yes + continue + ;; + + -version-info) + prev=vinfo + continue + ;; + + -version-number) + prev=vinfo + vinfo_number=yes + continue + ;; + + -weak) + prev=weak + continue + ;; + + -Wc,*) + func_stripname '-Wc,' '' "$arg" + args=$func_stripname_result + arg= + save_ifs=$IFS; IFS=, + for flag in $args; do + IFS=$save_ifs + func_quote_arg pretty "$flag" + func_append arg " $func_quote_arg_result" + func_append compiler_flags " $func_quote_arg_result" + done + IFS=$save_ifs + func_stripname ' ' '' "$arg" + arg=$func_stripname_result + ;; + + -Wl,*) + func_stripname '-Wl,' '' "$arg" + args=$func_stripname_result + arg= + save_ifs=$IFS; IFS=, + for flag in $args; do + IFS=$save_ifs + func_quote_arg pretty "$flag" + func_append arg " $wl$func_quote_arg_result" + func_append compiler_flags " $wl$func_quote_arg_result" + func_append linker_flags " $func_quote_arg_result" + done + IFS=$save_ifs + func_stripname ' ' '' "$arg" + arg=$func_stripname_result + ;; + + -Xassembler) + prev=xassembler + continue + ;; + + -Xcompiler) + prev=xcompiler + continue + ;; + + -Xlinker) + prev=xlinker + continue + ;; + + -XCClinker) + prev=xcclinker + continue + ;; + + # -msg_* for osf cc + -msg_*) + func_quote_arg pretty "$arg" + arg=$func_quote_arg_result + ;; + + # Flags to be passed through unchanged, with rationale: + # -64, -mips[0-9] enable 64-bit mode for the SGI compiler + # -r[0-9][0-9]* specify processor for the SGI compiler + # -xarch=*, -xtarget=* enable 64-bit mode for the Sun compiler + # +DA*, +DD* enable 64-bit mode for the HP compiler + # -q* compiler args for the IBM compiler + # -m*, -t[45]*, -txscale* architecture-specific flags for GCC + # -F/path path to uninstalled frameworks, gcc on darwin + # -p, -pg, --coverage, -fprofile-* profiling flags for GCC + # -fstack-protector* stack protector flags for GCC + # @file GCC response files + # -tp=* Portland pgcc target processor selection + # --sysroot=* for sysroot support + # -O*, -g*, -flto*, -fwhopr*, -fuse-linker-plugin GCC link-time optimization + # -specs=* GCC specs files + # -stdlib=* select c++ std lib with clang + # -fsanitize=* Clang/GCC memory and address sanitizer + # -fuse-ld=* Linker select flags for GCC + # -Wa,* Pass flags directly to the assembler + -64|-mips[0-9]|-r[0-9][0-9]*|-xarch=*|-xtarget=*|+DA*|+DD*|-q*|-m*| \ + -t[45]*|-txscale*|-p|-pg|--coverage|-fprofile-*|-F*|@*|-tp=*|--sysroot=*| \ + -O*|-g*|-flto*|-fwhopr*|-fuse-linker-plugin|-fstack-protector*|-stdlib=*| \ + -specs=*|-fsanitize=*|-fuse-ld=*|-Wa,*) + func_quote_arg pretty "$arg" + arg=$func_quote_arg_result + func_append compile_command " $arg" + func_append finalize_command " $arg" + func_append compiler_flags " $arg" + continue + ;; + + -Z*) + if test os2 = "`expr $host : '.*\(os2\)'`"; then + # OS/2 uses -Zxxx to specify OS/2-specific options + compiler_flags="$compiler_flags $arg" + func_append compile_command " $arg" + func_append finalize_command " $arg" + case $arg in + -Zlinker | -Zstack) + prev=xcompiler + ;; + esac + continue + else + # Otherwise treat like 'Some other compiler flag' below + func_quote_arg pretty "$arg" + arg=$func_quote_arg_result + fi + ;; + + # Some other compiler flag. + -* | +*) + func_quote_arg pretty "$arg" + arg=$func_quote_arg_result + ;; + + *.$objext) + # A standard object. + func_append objs " $arg" + ;; + + *.lo) + # A libtool-controlled object. + + # Check to see that this really is a libtool object. + if func_lalib_unsafe_p "$arg"; then + pic_object= + non_pic_object= + + # Read the .lo file + func_source "$arg" + + if test -z "$pic_object" || + test -z "$non_pic_object" || + test none = "$pic_object" && + test none = "$non_pic_object"; then + func_fatal_error "cannot find name of object for '$arg'" + fi + + # Extract subdirectory from the argument. + func_dirname "$arg" "/" "" + xdir=$func_dirname_result + + test none = "$pic_object" || { + # Prepend the subdirectory the object is found in. + pic_object=$xdir$pic_object + + if test dlfiles = "$prev"; then + if test yes = "$build_libtool_libs" && test yes = "$dlopen_support"; then + func_append dlfiles " $pic_object" + prev= + continue + else + # If libtool objects are unsupported, then we need to preload. + prev=dlprefiles + fi + fi + + # CHECK ME: I think I busted this. -Ossama + if test dlprefiles = "$prev"; then + # Preload the old-style object. + func_append dlprefiles " $pic_object" + prev= + fi + + # A PIC object. + func_append libobjs " $pic_object" + arg=$pic_object + } + + # Non-PIC object. + if test none != "$non_pic_object"; then + # Prepend the subdirectory the object is found in. + non_pic_object=$xdir$non_pic_object + + # A standard non-PIC object + func_append non_pic_objects " $non_pic_object" + if test -z "$pic_object" || test none = "$pic_object"; then + arg=$non_pic_object + fi + else + # If the PIC object exists, use it instead. + # $xdir was prepended to $pic_object above. + non_pic_object=$pic_object + func_append non_pic_objects " $non_pic_object" + fi + else + # Only an error if not doing a dry-run. + if $opt_dry_run; then + # Extract subdirectory from the argument. + func_dirname "$arg" "/" "" + xdir=$func_dirname_result + + func_lo2o "$arg" + pic_object=$xdir$objdir/$func_lo2o_result + non_pic_object=$xdir$func_lo2o_result + func_append libobjs " $pic_object" + func_append non_pic_objects " $non_pic_object" + else + func_fatal_error "'$arg' is not a valid libtool object" + fi + fi + ;; + + *.$libext) + # An archive. + func_append deplibs " $arg" + func_append old_deplibs " $arg" + continue + ;; + + *.la) + # A libtool-controlled library. + + func_resolve_sysroot "$arg" + if test dlfiles = "$prev"; then + # This library was specified with -dlopen. + func_append dlfiles " $func_resolve_sysroot_result" + prev= + elif test dlprefiles = "$prev"; then + # The library was specified with -dlpreopen. + func_append dlprefiles " $func_resolve_sysroot_result" + prev= + else + func_append deplibs " $func_resolve_sysroot_result" + fi + continue + ;; + + # Some other compiler argument. + *) + # Unknown arguments in both finalize_command and compile_command need + # to be aesthetically quoted because they are evaled later. + func_quote_arg pretty "$arg" + arg=$func_quote_arg_result + ;; + esac # arg + + # Now actually substitute the argument into the commands. + if test -n "$arg"; then + func_append compile_command " $arg" + func_append finalize_command " $arg" + fi + done # argument parsing loop + + test -n "$prev" && \ + func_fatal_help "the '$prevarg' option requires an argument" + + if test yes = "$export_dynamic" && test -n "$export_dynamic_flag_spec"; then + eval arg=\"$export_dynamic_flag_spec\" + func_append compile_command " $arg" + func_append finalize_command " $arg" + fi + + oldlibs= + # calculate the name of the file, without its directory + func_basename "$output" + outputname=$func_basename_result + libobjs_save=$libobjs + + if test -n "$shlibpath_var"; then + # get the directories listed in $shlibpath_var + eval shlib_search_path=\`\$ECHO \"\$$shlibpath_var\" \| \$SED \'s/:/ /g\'\` + else + shlib_search_path= + fi + eval sys_lib_search_path=\"$sys_lib_search_path_spec\" + eval sys_lib_dlsearch_path=\"$sys_lib_dlsearch_path_spec\" + + # Definition is injected by LT_CONFIG during libtool generation. + func_munge_path_list sys_lib_dlsearch_path "$LT_SYS_LIBRARY_PATH" + + func_dirname "$output" "/" "" + output_objdir=$func_dirname_result$objdir + func_to_tool_file "$output_objdir/" + tool_output_objdir=$func_to_tool_file_result + # Create the object directory. + func_mkdir_p "$output_objdir" + + # Determine the type of output + case $output in + "") + func_fatal_help "you must specify an output file" + ;; + *.$libext) linkmode=oldlib ;; + *.lo | *.$objext) linkmode=obj ;; + *.la) linkmode=lib ;; + *) linkmode=prog ;; # Anything else should be a program. + esac + + specialdeplibs= + + libs= + # Find all interdependent deplibs by searching for libraries + # that are linked more than once (e.g. -la -lb -la) + for deplib in $deplibs; do + if $opt_preserve_dup_deps; then + case "$libs " in + *" $deplib "*) func_append specialdeplibs " $deplib" ;; + esac + fi + func_append libs " $deplib" + done + + if test lib = "$linkmode"; then + libs="$predeps $libs $compiler_lib_search_path $postdeps" + + # Compute libraries that are listed more than once in $predeps + # $postdeps and mark them as special (i.e., whose duplicates are + # not to be eliminated). + pre_post_deps= + if $opt_duplicate_compiler_generated_deps; then + for pre_post_dep in $predeps $postdeps; do + case "$pre_post_deps " in + *" $pre_post_dep "*) func_append specialdeplibs " $pre_post_deps" ;; + esac + func_append pre_post_deps " $pre_post_dep" + done + fi + pre_post_deps= + fi + + deplibs= + newdependency_libs= + newlib_search_path= + need_relink=no # whether we're linking any uninstalled libtool libraries + notinst_deplibs= # not-installed libtool libraries + notinst_path= # paths that contain not-installed libtool libraries + + case $linkmode in + lib) + passes="conv dlpreopen link" + for file in $dlfiles $dlprefiles; do + case $file in + *.la) ;; + *) + func_fatal_help "libraries can '-dlopen' only libtool libraries: $file" + ;; + esac + done + ;; + prog) + compile_deplibs= + finalize_deplibs= + alldeplibs=false + newdlfiles= + newdlprefiles= + passes="conv scan dlopen dlpreopen link" + ;; + *) passes="conv" + ;; + esac + + for pass in $passes; do + # The preopen pass in lib mode reverses $deplibs; put it back here + # so that -L comes before libs that need it for instance... + if test lib,link = "$linkmode,$pass"; then + ## FIXME: Find the place where the list is rebuilt in the wrong + ## order, and fix it there properly + tmp_deplibs= + for deplib in $deplibs; do + tmp_deplibs="$deplib $tmp_deplibs" + done + deplibs=$tmp_deplibs + fi + + if test lib,link = "$linkmode,$pass" || + test prog,scan = "$linkmode,$pass"; then + libs=$deplibs + deplibs= + fi + if test prog = "$linkmode"; then + case $pass in + dlopen) libs=$dlfiles ;; + dlpreopen) libs=$dlprefiles ;; + link) libs="$deplibs %DEPLIBS% $dependency_libs" ;; + esac + fi + if test lib,dlpreopen = "$linkmode,$pass"; then + # Collect and forward deplibs of preopened libtool libs + for lib in $dlprefiles; do + # Ignore non-libtool-libs + dependency_libs= + func_resolve_sysroot "$lib" + case $lib in + *.la) func_source "$func_resolve_sysroot_result" ;; + esac + + # Collect preopened libtool deplibs, except any this library + # has declared as weak libs + for deplib in $dependency_libs; do + func_basename "$deplib" + deplib_base=$func_basename_result + case " $weak_libs " in + *" $deplib_base "*) ;; + *) func_append deplibs " $deplib" ;; + esac + done + done + libs=$dlprefiles + fi + if test dlopen = "$pass"; then + # Collect dlpreopened libraries + save_deplibs=$deplibs + deplibs= + fi + + for deplib in $libs; do + lib= + found=false + case $deplib in + -mt|-mthreads|-kthread|-Kthread|-pthread|-pthreads|--thread-safe \ + |-threads|-fopenmp|-openmp|-mp|-xopenmp|-omp|-qsmp=*) + if test prog,link = "$linkmode,$pass"; then + compile_deplibs="$deplib $compile_deplibs" + finalize_deplibs="$deplib $finalize_deplibs" + else + func_append compiler_flags " $deplib" + if test lib = "$linkmode"; then + case "$new_inherited_linker_flags " in + *" $deplib "*) ;; + * ) func_append new_inherited_linker_flags " $deplib" ;; + esac + fi + fi + continue + ;; + -l*) + if test lib != "$linkmode" && test prog != "$linkmode"; then + func_warning "'-l' is ignored for archives/objects" + continue + fi + func_stripname '-l' '' "$deplib" + name=$func_stripname_result + if test lib = "$linkmode"; then + searchdirs="$newlib_search_path $lib_search_path $compiler_lib_search_dirs $sys_lib_search_path $shlib_search_path" + else + searchdirs="$newlib_search_path $lib_search_path $sys_lib_search_path $shlib_search_path" + fi + for searchdir in $searchdirs; do + for search_ext in .la $std_shrext .so .a; do + # Search the libtool library + lib=$searchdir/lib$name$search_ext + if test -f "$lib"; then + if test .la = "$search_ext"; then + found=: + else + found=false + fi + break 2 + fi + done + done + if $found; then + # deplib is a libtool library + # If $allow_libtool_libs_with_static_runtimes && $deplib is a stdlib, + # We need to do some special things here, and not later. + if test yes = "$allow_libtool_libs_with_static_runtimes"; then + case " $predeps $postdeps " in + *" $deplib "*) + if func_lalib_p "$lib"; then + library_names= + old_library= + func_source "$lib" + for l in $old_library $library_names; do + ll=$l + done + if test "X$ll" = "X$old_library"; then # only static version available + found=false + func_dirname "$lib" "" "." + ladir=$func_dirname_result + lib=$ladir/$old_library + if test prog,link = "$linkmode,$pass"; then + compile_deplibs="$deplib $compile_deplibs" + finalize_deplibs="$deplib $finalize_deplibs" + else + deplibs="$deplib $deplibs" + test lib = "$linkmode" && newdependency_libs="$deplib $newdependency_libs" + fi + continue + fi + fi + ;; + *) ;; + esac + fi + else + # deplib doesn't seem to be a libtool library + if test prog,link = "$linkmode,$pass"; then + compile_deplibs="$deplib $compile_deplibs" + finalize_deplibs="$deplib $finalize_deplibs" + else + deplibs="$deplib $deplibs" + test lib = "$linkmode" && newdependency_libs="$deplib $newdependency_libs" + fi + continue + fi + ;; # -l + *.ltframework) + if test prog,link = "$linkmode,$pass"; then + compile_deplibs="$deplib $compile_deplibs" + finalize_deplibs="$deplib $finalize_deplibs" + else + deplibs="$deplib $deplibs" + if test lib = "$linkmode"; then + case "$new_inherited_linker_flags " in + *" $deplib "*) ;; + * ) func_append new_inherited_linker_flags " $deplib" ;; + esac + fi + fi + continue + ;; + -L*) + case $linkmode in + lib) + deplibs="$deplib $deplibs" + test conv = "$pass" && continue + newdependency_libs="$deplib $newdependency_libs" + func_stripname '-L' '' "$deplib" + func_resolve_sysroot "$func_stripname_result" + func_append newlib_search_path " $func_resolve_sysroot_result" + ;; + prog) + if test conv = "$pass"; then + deplibs="$deplib $deplibs" + continue + fi + if test scan = "$pass"; then + deplibs="$deplib $deplibs" + else + compile_deplibs="$deplib $compile_deplibs" + finalize_deplibs="$deplib $finalize_deplibs" + fi + func_stripname '-L' '' "$deplib" + func_resolve_sysroot "$func_stripname_result" + func_append newlib_search_path " $func_resolve_sysroot_result" + ;; + *) + func_warning "'-L' is ignored for archives/objects" + ;; + esac # linkmode + continue + ;; # -L + -R*) + if test link = "$pass"; then + func_stripname '-R' '' "$deplib" + func_resolve_sysroot "$func_stripname_result" + dir=$func_resolve_sysroot_result + # Make sure the xrpath contains only unique directories. + case "$xrpath " in + *" $dir "*) ;; + *) func_append xrpath " $dir" ;; + esac + fi + deplibs="$deplib $deplibs" + continue + ;; + *.la) + func_resolve_sysroot "$deplib" + lib=$func_resolve_sysroot_result + ;; + *.$libext) + if test conv = "$pass"; then + deplibs="$deplib $deplibs" + continue + fi + case $linkmode in + lib) + # Linking convenience modules into shared libraries is allowed, + # but linking other static libraries is non-portable. + case " $dlpreconveniencelibs " in + *" $deplib "*) ;; + *) + valid_a_lib=false + case $deplibs_check_method in + match_pattern*) + set dummy $deplibs_check_method; shift + match_pattern_regex=`expr "$deplibs_check_method" : "$1 \(.*\)"` + if eval "\$ECHO \"$deplib\"" 2>/dev/null | $SED 10q \ + | $EGREP "$match_pattern_regex" > /dev/null; then + valid_a_lib=: + fi + ;; + pass_all) + valid_a_lib=: + ;; + esac + if $valid_a_lib; then + echo + $ECHO "*** Warning: Linking the shared library $output against the" + $ECHO "*** static library $deplib is not portable!" + deplibs="$deplib $deplibs" + else + echo + $ECHO "*** Warning: Trying to link with static lib archive $deplib." + echo "*** I have the capability to make that library automatically link in when" + echo "*** you link to this library. But I can only do this if you have a" + echo "*** shared version of the library, which you do not appear to have" + echo "*** because the file extensions .$libext of this argument makes me believe" + echo "*** that it is just a static archive that I should not use here." + fi + ;; + esac + continue + ;; + prog) + if test link != "$pass"; then + deplibs="$deplib $deplibs" + else + compile_deplibs="$deplib $compile_deplibs" + finalize_deplibs="$deplib $finalize_deplibs" + fi + continue + ;; + esac # linkmode + ;; # *.$libext + *.lo | *.$objext) + if test conv = "$pass"; then + deplibs="$deplib $deplibs" + elif test prog = "$linkmode"; then + if test dlpreopen = "$pass" || test yes != "$dlopen_support" || test no = "$build_libtool_libs"; then + # If there is no dlopen support or we're linking statically, + # we need to preload. + func_append newdlprefiles " $deplib" + compile_deplibs="$deplib $compile_deplibs" + finalize_deplibs="$deplib $finalize_deplibs" + else + func_append newdlfiles " $deplib" + fi + fi + continue + ;; + %DEPLIBS%) + alldeplibs=: + continue + ;; + esac # case $deplib + + $found || test -f "$lib" \ + || func_fatal_error "cannot find the library '$lib' or unhandled argument '$deplib'" + + # Check to see that this really is a libtool archive. + func_lalib_unsafe_p "$lib" \ + || func_fatal_error "'$lib' is not a valid libtool archive" + + func_dirname "$lib" "" "." + ladir=$func_dirname_result + + dlname= + dlopen= + dlpreopen= + libdir= + library_names= + old_library= + inherited_linker_flags= + # If the library was installed with an old release of libtool, + # it will not redefine variables installed, or shouldnotlink + installed=yes + shouldnotlink=no + avoidtemprpath= + + + # Read the .la file + func_source "$lib" + + # Convert "-framework foo" to "foo.ltframework" + if test -n "$inherited_linker_flags"; then + tmp_inherited_linker_flags=`$ECHO "$inherited_linker_flags" | $SED 's/-framework \([^ $]*\)/\1.ltframework/g'` + for tmp_inherited_linker_flag in $tmp_inherited_linker_flags; do + case " $new_inherited_linker_flags " in + *" $tmp_inherited_linker_flag "*) ;; + *) func_append new_inherited_linker_flags " $tmp_inherited_linker_flag";; + esac + done + fi + dependency_libs=`$ECHO " $dependency_libs" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` + if test lib,link = "$linkmode,$pass" || + test prog,scan = "$linkmode,$pass" || + { test prog != "$linkmode" && test lib != "$linkmode"; }; then + test -n "$dlopen" && func_append dlfiles " $dlopen" + test -n "$dlpreopen" && func_append dlprefiles " $dlpreopen" + fi + + if test conv = "$pass"; then + # Only check for convenience libraries + deplibs="$lib $deplibs" + if test -z "$libdir"; then + if test -z "$old_library"; then + func_fatal_error "cannot find name of link library for '$lib'" + fi + # It is a libtool convenience library, so add in its objects. + func_append convenience " $ladir/$objdir/$old_library" + func_append old_convenience " $ladir/$objdir/$old_library" + elif test prog != "$linkmode" && test lib != "$linkmode"; then + func_fatal_error "'$lib' is not a convenience library" + fi + tmp_libs= + for deplib in $dependency_libs; do + deplibs="$deplib $deplibs" + if $opt_preserve_dup_deps; then + case "$tmp_libs " in + *" $deplib "*) func_append specialdeplibs " $deplib" ;; + esac + fi + func_append tmp_libs " $deplib" + done + continue + fi # $pass = conv + + + # Get the name of the library we link against. + linklib= + if test -n "$old_library" && + { test yes = "$prefer_static_libs" || + test built,no = "$prefer_static_libs,$installed"; }; then + linklib=$old_library + else + for l in $old_library $library_names; do + linklib=$l + done + fi + if test -z "$linklib"; then + func_fatal_error "cannot find name of link library for '$lib'" + fi + + # This library was specified with -dlopen. + if test dlopen = "$pass"; then + test -z "$libdir" \ + && func_fatal_error "cannot -dlopen a convenience library: '$lib'" + if test -z "$dlname" || + test yes != "$dlopen_support" || + test no = "$build_libtool_libs" + then + # If there is no dlname, no dlopen support or we're linking + # statically, we need to preload. We also need to preload any + # dependent libraries so libltdl's deplib preloader doesn't + # bomb out in the load deplibs phase. + func_append dlprefiles " $lib $dependency_libs" + else + func_append newdlfiles " $lib" + fi + continue + fi # $pass = dlopen + + # We need an absolute path. + case $ladir in + [\\/]* | [A-Za-z]:[\\/]*) abs_ladir=$ladir ;; + *) + abs_ladir=`cd "$ladir" && pwd` + if test -z "$abs_ladir"; then + func_warning "cannot determine absolute directory name of '$ladir'" + func_warning "passing it literally to the linker, although it might fail" + abs_ladir=$ladir + fi + ;; + esac + func_basename "$lib" + laname=$func_basename_result + + # Find the relevant object directory and library name. + if test yes = "$installed"; then + if test ! -f "$lt_sysroot$libdir/$linklib" && test -f "$abs_ladir/$linklib"; then + func_warning "library '$lib' was moved." + dir=$ladir + absdir=$abs_ladir + libdir=$abs_ladir + else + dir=$lt_sysroot$libdir + absdir=$lt_sysroot$libdir + fi + test yes = "$hardcode_automatic" && avoidtemprpath=yes + else + if test ! -f "$ladir/$objdir/$linklib" && test -f "$abs_ladir/$linklib"; then + dir=$ladir + absdir=$abs_ladir + # Remove this search path later + func_append notinst_path " $abs_ladir" + else + dir=$ladir/$objdir + absdir=$abs_ladir/$objdir + # Remove this search path later + func_append notinst_path " $abs_ladir" + fi + fi # $installed = yes + func_stripname 'lib' '.la' "$laname" + name=$func_stripname_result + + # This library was specified with -dlpreopen. + if test dlpreopen = "$pass"; then + if test -z "$libdir" && test prog = "$linkmode"; then + func_fatal_error "only libraries may -dlpreopen a convenience library: '$lib'" + fi + case $host in + # special handling for platforms with PE-DLLs. + *cygwin* | *mingw* | *cegcc* ) + # Linker will automatically link against shared library if both + # static and shared are present. Therefore, ensure we extract + # symbols from the import library if a shared library is present + # (otherwise, the dlopen module name will be incorrect). We do + # this by putting the import library name into $newdlprefiles. + # We recover the dlopen module name by 'saving' the la file + # name in a special purpose variable, and (later) extracting the + # dlname from the la file. + if test -n "$dlname"; then + func_tr_sh "$dir/$linklib" + eval "libfile_$func_tr_sh_result=\$abs_ladir/\$laname" + func_append newdlprefiles " $dir/$linklib" + else + func_append newdlprefiles " $dir/$old_library" + # Keep a list of preopened convenience libraries to check + # that they are being used correctly in the link pass. + test -z "$libdir" && \ + func_append dlpreconveniencelibs " $dir/$old_library" + fi + ;; + * ) + # Prefer using a static library (so that no silly _DYNAMIC symbols + # are required to link). + if test -n "$old_library"; then + func_append newdlprefiles " $dir/$old_library" + # Keep a list of preopened convenience libraries to check + # that they are being used correctly in the link pass. + test -z "$libdir" && \ + func_append dlpreconveniencelibs " $dir/$old_library" + # Otherwise, use the dlname, so that lt_dlopen finds it. + elif test -n "$dlname"; then + func_append newdlprefiles " $dir/$dlname" + else + func_append newdlprefiles " $dir/$linklib" + fi + ;; + esac + fi # $pass = dlpreopen + + if test -z "$libdir"; then + # Link the convenience library + if test lib = "$linkmode"; then + deplibs="$dir/$old_library $deplibs" + elif test prog,link = "$linkmode,$pass"; then + compile_deplibs="$dir/$old_library $compile_deplibs" + finalize_deplibs="$dir/$old_library $finalize_deplibs" + else + deplibs="$lib $deplibs" # used for prog,scan pass + fi + continue + fi + + + if test prog = "$linkmode" && test link != "$pass"; then + func_append newlib_search_path " $ladir" + deplibs="$lib $deplibs" + + linkalldeplibs=false + if test no != "$link_all_deplibs" || test -z "$library_names" || + test no = "$build_libtool_libs"; then + linkalldeplibs=: + fi + + tmp_libs= + for deplib in $dependency_libs; do + case $deplib in + -L*) func_stripname '-L' '' "$deplib" + func_resolve_sysroot "$func_stripname_result" + func_append newlib_search_path " $func_resolve_sysroot_result" + ;; + esac + # Need to link against all dependency_libs? + if $linkalldeplibs; then + deplibs="$deplib $deplibs" + else + # Need to hardcode shared library paths + # or/and link against static libraries + newdependency_libs="$deplib $newdependency_libs" + fi + if $opt_preserve_dup_deps; then + case "$tmp_libs " in + *" $deplib "*) func_append specialdeplibs " $deplib" ;; + esac + fi + func_append tmp_libs " $deplib" + done # for deplib + continue + fi # $linkmode = prog... + + if test prog,link = "$linkmode,$pass"; then + if test -n "$library_names" && + { { test no = "$prefer_static_libs" || + test built,yes = "$prefer_static_libs,$installed"; } || + test -z "$old_library"; }; then + # We need to hardcode the library path + if test -n "$shlibpath_var" && test -z "$avoidtemprpath"; then + # Make sure the rpath contains only unique directories. + case $temp_rpath: in + *"$absdir:"*) ;; + *) func_append temp_rpath "$absdir:" ;; + esac + fi + + # Hardcode the library path. + # Skip directories that are in the system default run-time + # search path. + case " $sys_lib_dlsearch_path " in + *" $absdir "*) ;; + *) + case "$compile_rpath " in + *" $absdir "*) ;; + *) func_append compile_rpath " $absdir" ;; + esac + ;; + esac + case " $sys_lib_dlsearch_path " in + *" $libdir "*) ;; + *) + case "$finalize_rpath " in + *" $libdir "*) ;; + *) func_append finalize_rpath " $libdir" ;; + esac + ;; + esac + fi # $linkmode,$pass = prog,link... + + if $alldeplibs && + { test pass_all = "$deplibs_check_method" || + { test yes = "$build_libtool_libs" && + test -n "$library_names"; }; }; then + # We only need to search for static libraries + continue + fi + fi + + link_static=no # Whether the deplib will be linked statically + use_static_libs=$prefer_static_libs + if test built = "$use_static_libs" && test yes = "$installed"; then + use_static_libs=no + fi + if test -n "$library_names" && + { test no = "$use_static_libs" || test -z "$old_library"; }; then + case $host in + *cygwin* | *mingw* | *cegcc* | *os2*) + # No point in relinking DLLs because paths are not encoded + func_append notinst_deplibs " $lib" + need_relink=no + ;; + *) + if test no = "$installed"; then + func_append notinst_deplibs " $lib" + need_relink=yes + fi + ;; + esac + # This is a shared library + + # Warn about portability, can't link against -module's on some + # systems (darwin). Don't bleat about dlopened modules though! + dlopenmodule= + for dlpremoduletest in $dlprefiles; do + if test "X$dlpremoduletest" = "X$lib"; then + dlopenmodule=$dlpremoduletest + break + fi + done + if test -z "$dlopenmodule" && test yes = "$shouldnotlink" && test link = "$pass"; then + echo + if test prog = "$linkmode"; then + $ECHO "*** Warning: Linking the executable $output against the loadable module" + else + $ECHO "*** Warning: Linking the shared library $output against the loadable module" + fi + $ECHO "*** $linklib is not portable!" + fi + if test lib = "$linkmode" && + test yes = "$hardcode_into_libs"; then + # Hardcode the library path. + # Skip directories that are in the system default run-time + # search path. + case " $sys_lib_dlsearch_path " in + *" $absdir "*) ;; + *) + case "$compile_rpath " in + *" $absdir "*) ;; + *) func_append compile_rpath " $absdir" ;; + esac + ;; + esac + case " $sys_lib_dlsearch_path " in + *" $libdir "*) ;; + *) + case "$finalize_rpath " in + *" $libdir "*) ;; + *) func_append finalize_rpath " $libdir" ;; + esac + ;; + esac + fi + + if test -n "$old_archive_from_expsyms_cmds"; then + # figure out the soname + set dummy $library_names + shift + realname=$1 + shift + libname=`eval "\\$ECHO \"$libname_spec\""` + # use dlname if we got it. it's perfectly good, no? + if test -n "$dlname"; then + soname=$dlname + elif test -n "$soname_spec"; then + # bleh windows + case $host in + *cygwin* | mingw* | *cegcc* | *os2*) + func_arith $current - $age + major=$func_arith_result + versuffix=-$major + ;; + esac + eval soname=\"$soname_spec\" + else + soname=$realname + fi + + # Make a new name for the extract_expsyms_cmds to use + soroot=$soname + func_basename "$soroot" + soname=$func_basename_result + func_stripname 'lib' '.dll' "$soname" + newlib=libimp-$func_stripname_result.a + + # If the library has no export list, then create one now + if test -f "$output_objdir/$soname-def"; then : + else + func_verbose "extracting exported symbol list from '$soname'" + func_execute_cmds "$extract_expsyms_cmds" 'exit $?' + fi + + # Create $newlib + if test -f "$output_objdir/$newlib"; then :; else + func_verbose "generating import library for '$soname'" + func_execute_cmds "$old_archive_from_expsyms_cmds" 'exit $?' + fi + # make sure the library variables are pointing to the new library + dir=$output_objdir + linklib=$newlib + fi # test -n "$old_archive_from_expsyms_cmds" + + if test prog = "$linkmode" || test relink != "$opt_mode"; then + add_shlibpath= + add_dir= + add= + lib_linked=yes + case $hardcode_action in + immediate | unsupported) + if test no = "$hardcode_direct"; then + add=$dir/$linklib + case $host in + *-*-sco3.2v5.0.[024]*) add_dir=-L$dir ;; + *-*-sysv4*uw2*) add_dir=-L$dir ;; + *-*-sysv5OpenUNIX* | *-*-sysv5UnixWare7.[01].[10]* | \ + *-*-unixware7*) add_dir=-L$dir ;; + *-*-darwin* ) + # if the lib is a (non-dlopened) module then we cannot + # link against it, someone is ignoring the earlier warnings + if /usr/bin/file -L $add 2> /dev/null | + $GREP ": [^:]* bundle" >/dev/null; then + if test "X$dlopenmodule" != "X$lib"; then + $ECHO "*** Warning: lib $linklib is a module, not a shared library" + if test -z "$old_library"; then + echo + echo "*** And there doesn't seem to be a static archive available" + echo "*** The link will probably fail, sorry" + else + add=$dir/$old_library + fi + elif test -n "$old_library"; then + add=$dir/$old_library + fi + fi + esac + elif test no = "$hardcode_minus_L"; then + case $host in + *-*-sunos*) add_shlibpath=$dir ;; + esac + add_dir=-L$dir + add=-l$name + elif test no = "$hardcode_shlibpath_var"; then + add_shlibpath=$dir + add=-l$name + else + lib_linked=no + fi + ;; + relink) + if test yes = "$hardcode_direct" && + test no = "$hardcode_direct_absolute"; then + add=$dir/$linklib + elif test yes = "$hardcode_minus_L"; then + add_dir=-L$absdir + # Try looking first in the location we're being installed to. + if test -n "$inst_prefix_dir"; then + case $libdir in + [\\/]*) + func_append add_dir " -L$inst_prefix_dir$libdir" + ;; + esac + fi + add=-l$name + elif test yes = "$hardcode_shlibpath_var"; then + add_shlibpath=$dir + add=-l$name + else + lib_linked=no + fi + ;; + *) lib_linked=no ;; + esac + + if test yes != "$lib_linked"; then + func_fatal_configuration "unsupported hardcode properties" + fi + + if test -n "$add_shlibpath"; then + case :$compile_shlibpath: in + *":$add_shlibpath:"*) ;; + *) func_append compile_shlibpath "$add_shlibpath:" ;; + esac + fi + if test prog = "$linkmode"; then + test -n "$add_dir" && compile_deplibs="$add_dir $compile_deplibs" + test -n "$add" && compile_deplibs="$add $compile_deplibs" + else + test -n "$add_dir" && deplibs="$add_dir $deplibs" + test -n "$add" && deplibs="$add $deplibs" + if test yes != "$hardcode_direct" && + test yes != "$hardcode_minus_L" && + test yes = "$hardcode_shlibpath_var"; then + case :$finalize_shlibpath: in + *":$libdir:"*) ;; + *) func_append finalize_shlibpath "$libdir:" ;; + esac + fi + fi + fi + + if test prog = "$linkmode" || test relink = "$opt_mode"; then + add_shlibpath= + add_dir= + add= + # Finalize command for both is simple: just hardcode it. + if test yes = "$hardcode_direct" && + test no = "$hardcode_direct_absolute"; then + add=$libdir/$linklib + elif test yes = "$hardcode_minus_L"; then + add_dir=-L$libdir + add=-l$name + elif test yes = "$hardcode_shlibpath_var"; then + case :$finalize_shlibpath: in + *":$libdir:"*) ;; + *) func_append finalize_shlibpath "$libdir:" ;; + esac + add=-l$name + elif test yes = "$hardcode_automatic"; then + if test -n "$inst_prefix_dir" && + test -f "$inst_prefix_dir$libdir/$linklib"; then + add=$inst_prefix_dir$libdir/$linklib + else + add=$libdir/$linklib + fi + else + # We cannot seem to hardcode it, guess we'll fake it. + add_dir=-L$libdir + # Try looking first in the location we're being installed to. + if test -n "$inst_prefix_dir"; then + case $libdir in + [\\/]*) + func_append add_dir " -L$inst_prefix_dir$libdir" + ;; + esac + fi + add=-l$name + fi + + if test prog = "$linkmode"; then + test -n "$add_dir" && finalize_deplibs="$add_dir $finalize_deplibs" + test -n "$add" && finalize_deplibs="$add $finalize_deplibs" + else + test -n "$add_dir" && deplibs="$add_dir $deplibs" + test -n "$add" && deplibs="$add $deplibs" + fi + fi + elif test prog = "$linkmode"; then + # Here we assume that one of hardcode_direct or hardcode_minus_L + # is not unsupported. This is valid on all known static and + # shared platforms. + if test unsupported != "$hardcode_direct"; then + test -n "$old_library" && linklib=$old_library + compile_deplibs="$dir/$linklib $compile_deplibs" + finalize_deplibs="$dir/$linklib $finalize_deplibs" + else + compile_deplibs="-l$name -L$dir $compile_deplibs" + finalize_deplibs="-l$name -L$dir $finalize_deplibs" + fi + elif test yes = "$build_libtool_libs"; then + # Not a shared library + if test pass_all != "$deplibs_check_method"; then + # We're trying link a shared library against a static one + # but the system doesn't support it. + + # Just print a warning and add the library to dependency_libs so + # that the program can be linked against the static library. + echo + $ECHO "*** Warning: This system cannot link to static lib archive $lib." + echo "*** I have the capability to make that library automatically link in when" + echo "*** you link to this library. But I can only do this if you have a" + echo "*** shared version of the library, which you do not appear to have." + if test yes = "$module"; then + echo "*** But as you try to build a module library, libtool will still create " + echo "*** a static module, that should work as long as the dlopening application" + echo "*** is linked with the -dlopen flag to resolve symbols at runtime." + if test -z "$global_symbol_pipe"; then + echo + echo "*** However, this would only work if libtool was able to extract symbol" + echo "*** lists from a program, using 'nm' or equivalent, but libtool could" + echo "*** not find such a program. So, this module is probably useless." + echo "*** 'nm' from GNU binutils and a full rebuild may help." + fi + if test no = "$build_old_libs"; then + build_libtool_libs=module + build_old_libs=yes + else + build_libtool_libs=no + fi + fi + else + deplibs="$dir/$old_library $deplibs" + link_static=yes + fi + fi # link shared/static library? + + if test lib = "$linkmode"; then + if test -n "$dependency_libs" && + { test yes != "$hardcode_into_libs" || + test yes = "$build_old_libs" || + test yes = "$link_static"; }; then + # Extract -R from dependency_libs + temp_deplibs= + for libdir in $dependency_libs; do + case $libdir in + -R*) func_stripname '-R' '' "$libdir" + temp_xrpath=$func_stripname_result + case " $xrpath " in + *" $temp_xrpath "*) ;; + *) func_append xrpath " $temp_xrpath";; + esac;; + *) func_append temp_deplibs " $libdir";; + esac + done + dependency_libs=$temp_deplibs + fi + + func_append newlib_search_path " $absdir" + # Link against this library + test no = "$link_static" && newdependency_libs="$abs_ladir/$laname $newdependency_libs" + # ... and its dependency_libs + tmp_libs= + for deplib in $dependency_libs; do + newdependency_libs="$deplib $newdependency_libs" + case $deplib in + -L*) func_stripname '-L' '' "$deplib" + func_resolve_sysroot "$func_stripname_result";; + *) func_resolve_sysroot "$deplib" ;; + esac + if $opt_preserve_dup_deps; then + case "$tmp_libs " in + *" $func_resolve_sysroot_result "*) + func_append specialdeplibs " $func_resolve_sysroot_result" ;; + esac + fi + func_append tmp_libs " $func_resolve_sysroot_result" + done + + if test no != "$link_all_deplibs"; then + # Add the search paths of all dependency libraries + for deplib in $dependency_libs; do + path= + case $deplib in + -L*) path=$deplib ;; + *.la) + func_resolve_sysroot "$deplib" + deplib=$func_resolve_sysroot_result + func_dirname "$deplib" "" "." + dir=$func_dirname_result + # We need an absolute path. + case $dir in + [\\/]* | [A-Za-z]:[\\/]*) absdir=$dir ;; + *) + absdir=`cd "$dir" && pwd` + if test -z "$absdir"; then + func_warning "cannot determine absolute directory name of '$dir'" + absdir=$dir + fi + ;; + esac + if $GREP "^installed=no" $deplib > /dev/null; then + case $host in + *-*-darwin*) + depdepl= + eval deplibrary_names=`$SED -n -e 's/^library_names=\(.*\)$/\1/p' $deplib` + if test -n "$deplibrary_names"; then + for tmp in $deplibrary_names; do + depdepl=$tmp + done + if test -f "$absdir/$objdir/$depdepl"; then + depdepl=$absdir/$objdir/$depdepl + darwin_install_name=`$OTOOL -L $depdepl | awk '{if (NR == 2) {print $1;exit}}'` + if test -z "$darwin_install_name"; then + darwin_install_name=`$OTOOL64 -L $depdepl | awk '{if (NR == 2) {print $1;exit}}'` + fi + func_append compiler_flags " $wl-dylib_file $wl$darwin_install_name:$depdepl" + func_append linker_flags " -dylib_file $darwin_install_name:$depdepl" + path= + fi + fi + ;; + *) + path=-L$absdir/$objdir + ;; + esac + else + eval libdir=`$SED -n -e 's/^libdir=\(.*\)$/\1/p' $deplib` + test -z "$libdir" && \ + func_fatal_error "'$deplib' is not a valid libtool archive" + test "$absdir" != "$libdir" && \ + func_warning "'$deplib' seems to be moved" + + path=-L$absdir + fi + ;; + esac + case " $deplibs " in + *" $path "*) ;; + *) deplibs="$path $deplibs" ;; + esac + done + fi # link_all_deplibs != no + fi # linkmode = lib + done # for deplib in $libs + if test link = "$pass"; then + if test prog = "$linkmode"; then + compile_deplibs="$new_inherited_linker_flags $compile_deplibs" + finalize_deplibs="$new_inherited_linker_flags $finalize_deplibs" + else + compiler_flags="$compiler_flags "`$ECHO " $new_inherited_linker_flags" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` + fi + fi + dependency_libs=$newdependency_libs + if test dlpreopen = "$pass"; then + # Link the dlpreopened libraries before other libraries + for deplib in $save_deplibs; do + deplibs="$deplib $deplibs" + done + fi + if test dlopen != "$pass"; then + test conv = "$pass" || { + # Make sure lib_search_path contains only unique directories. + lib_search_path= + for dir in $newlib_search_path; do + case "$lib_search_path " in + *" $dir "*) ;; + *) func_append lib_search_path " $dir" ;; + esac + done + newlib_search_path= + } + + if test prog,link = "$linkmode,$pass"; then + vars="compile_deplibs finalize_deplibs" + else + vars=deplibs + fi + for var in $vars dependency_libs; do + # Add libraries to $var in reverse order + eval tmp_libs=\"\$$var\" + new_libs= + for deplib in $tmp_libs; do + # FIXME: Pedantically, this is the right thing to do, so + # that some nasty dependency loop isn't accidentally + # broken: + #new_libs="$deplib $new_libs" + # Pragmatically, this seems to cause very few problems in + # practice: + case $deplib in + -L*) new_libs="$deplib $new_libs" ;; + -R*) ;; + *) + # And here is the reason: when a library appears more + # than once as an explicit dependence of a library, or + # is implicitly linked in more than once by the + # compiler, it is considered special, and multiple + # occurrences thereof are not removed. Compare this + # with having the same library being listed as a + # dependency of multiple other libraries: in this case, + # we know (pedantically, we assume) the library does not + # need to be listed more than once, so we keep only the + # last copy. This is not always right, but it is rare + # enough that we require users that really mean to play + # such unportable linking tricks to link the library + # using -Wl,-lname, so that libtool does not consider it + # for duplicate removal. + case " $specialdeplibs " in + *" $deplib "*) new_libs="$deplib $new_libs" ;; + *) + case " $new_libs " in + *" $deplib "*) ;; + *) new_libs="$deplib $new_libs" ;; + esac + ;; + esac + ;; + esac + done + tmp_libs= + for deplib in $new_libs; do + case $deplib in + -L*) + case " $tmp_libs " in + *" $deplib "*) ;; + *) func_append tmp_libs " $deplib" ;; + esac + ;; + *) func_append tmp_libs " $deplib" ;; + esac + done + eval $var=\"$tmp_libs\" + done # for var + fi + + # Add Sun CC postdeps if required: + test CXX = "$tagname" && { + case $host_os in + linux*) + case `$CC -V 2>&1 | $SED 5q` in + *Sun\ C*) # Sun C++ 5.9 + func_suncc_cstd_abi + + if test no != "$suncc_use_cstd_abi"; then + func_append postdeps ' -library=Cstd -library=Crun' + fi + ;; + esac + ;; + + solaris*) + func_cc_basename "$CC" + case $func_cc_basename_result in + CC* | sunCC*) + func_suncc_cstd_abi + + if test no != "$suncc_use_cstd_abi"; then + func_append postdeps ' -library=Cstd -library=Crun' + fi + ;; + esac + ;; + esac + } + + # Last step: remove runtime libs from dependency_libs + # (they stay in deplibs) + tmp_libs= + for i in $dependency_libs; do + case " $predeps $postdeps $compiler_lib_search_path " in + *" $i "*) + i= + ;; + esac + if test -n "$i"; then + func_append tmp_libs " $i" + fi + done + dependency_libs=$tmp_libs + done # for pass + if test prog = "$linkmode"; then + dlfiles=$newdlfiles + fi + if test prog = "$linkmode" || test lib = "$linkmode"; then + dlprefiles=$newdlprefiles + fi + + case $linkmode in + oldlib) + if test -n "$dlfiles$dlprefiles" || test no != "$dlself"; then + func_warning "'-dlopen' is ignored for archives" + fi + + case " $deplibs" in + *\ -l* | *\ -L*) + func_warning "'-l' and '-L' are ignored for archives" ;; + esac + + test -n "$rpath" && \ + func_warning "'-rpath' is ignored for archives" + + test -n "$xrpath" && \ + func_warning "'-R' is ignored for archives" + + test -n "$vinfo" && \ + func_warning "'-version-info/-version-number' is ignored for archives" + + test -n "$release" && \ + func_warning "'-release' is ignored for archives" + + test -n "$export_symbols$export_symbols_regex" && \ + func_warning "'-export-symbols' is ignored for archives" + + # Now set the variables for building old libraries. + build_libtool_libs=no + oldlibs=$output + func_append objs "$old_deplibs" + ;; + + lib) + # Make sure we only generate libraries of the form 'libNAME.la'. + case $outputname in + lib*) + func_stripname 'lib' '.la' "$outputname" + name=$func_stripname_result + eval shared_ext=\"$shrext_cmds\" + eval libname=\"$libname_spec\" + ;; + *) + test no = "$module" \ + && func_fatal_help "libtool library '$output' must begin with 'lib'" + + if test no != "$need_lib_prefix"; then + # Add the "lib" prefix for modules if required + func_stripname '' '.la' "$outputname" + name=$func_stripname_result + eval shared_ext=\"$shrext_cmds\" + eval libname=\"$libname_spec\" + else + func_stripname '' '.la' "$outputname" + libname=$func_stripname_result + fi + ;; + esac + + if test -n "$objs"; then + if test pass_all != "$deplibs_check_method"; then + func_fatal_error "cannot build libtool library '$output' from non-libtool objects on this host:$objs" + else + echo + $ECHO "*** Warning: Linking the shared library $output against the non-libtool" + $ECHO "*** objects $objs is not portable!" + func_append libobjs " $objs" + fi + fi + + test no = "$dlself" \ + || func_warning "'-dlopen self' is ignored for libtool libraries" + + set dummy $rpath + shift + test 1 -lt "$#" \ + && func_warning "ignoring multiple '-rpath's for a libtool library" + + install_libdir=$1 + + oldlibs= + if test -z "$rpath"; then + if test yes = "$build_libtool_libs"; then + # Building a libtool convenience library. + # Some compilers have problems with a '.al' extension so + # convenience libraries should have the same extension an + # archive normally would. + oldlibs="$output_objdir/$libname.$libext $oldlibs" + build_libtool_libs=convenience + build_old_libs=yes + fi + + test -n "$vinfo" && \ + func_warning "'-version-info/-version-number' is ignored for convenience libraries" + + test -n "$release" && \ + func_warning "'-release' is ignored for convenience libraries" + else + + # Parse the version information argument. + save_ifs=$IFS; IFS=: + set dummy $vinfo 0 0 0 + shift + IFS=$save_ifs + + test -n "$7" && \ + func_fatal_help "too many parameters to '-version-info'" + + # convert absolute version numbers to libtool ages + # this retains compatibility with .la files and attempts + # to make the code below a bit more comprehensible + + case $vinfo_number in + yes) + number_major=$1 + number_minor=$2 + number_revision=$3 + # + # There are really only two kinds -- those that + # use the current revision as the major version + # and those that subtract age and use age as + # a minor version. But, then there is irix + # that has an extra 1 added just for fun + # + case $version_type in + # correct linux to gnu/linux during the next big refactor + darwin|freebsd-elf|linux|midnightbsd-elf|osf|windows|none) + func_arith $number_major + $number_minor + current=$func_arith_result + age=$number_minor + revision=$number_revision + ;; + freebsd-aout|qnx|sunos) + current=$number_major + revision=$number_minor + age=0 + ;; + irix|nonstopux) + func_arith $number_major + $number_minor + current=$func_arith_result + age=$number_minor + revision=$number_minor + lt_irix_increment=no + ;; + esac + ;; + no) + current=$1 + revision=$2 + age=$3 + ;; + esac + + # Check that each of the things are valid numbers. + case $current in + 0|[1-9]|[1-9][0-9]|[1-9][0-9][0-9]|[1-9][0-9][0-9][0-9]|[1-9][0-9][0-9][0-9][0-9]) ;; + *) + func_error "CURRENT '$current' must be a nonnegative integer" + func_fatal_error "'$vinfo' is not valid version information" + ;; + esac + + case $revision in + 0|[1-9]|[1-9][0-9]|[1-9][0-9][0-9]|[1-9][0-9][0-9][0-9]|[1-9][0-9][0-9][0-9][0-9]) ;; + *) + func_error "REVISION '$revision' must be a nonnegative integer" + func_fatal_error "'$vinfo' is not valid version information" + ;; + esac + + case $age in + 0|[1-9]|[1-9][0-9]|[1-9][0-9][0-9]|[1-9][0-9][0-9][0-9]|[1-9][0-9][0-9][0-9][0-9]) ;; + *) + func_error "AGE '$age' must be a nonnegative integer" + func_fatal_error "'$vinfo' is not valid version information" + ;; + esac + + if test "$age" -gt "$current"; then + func_error "AGE '$age' is greater than the current interface number '$current'" + func_fatal_error "'$vinfo' is not valid version information" + fi + + # Calculate the version variables. + major= + versuffix= + verstring= + case $version_type in + none) ;; + + darwin) + # Like Linux, but with the current version available in + # verstring for coding it into the library header + func_arith $current - $age + major=.$func_arith_result + versuffix=$major.$age.$revision + # Darwin ld doesn't like 0 for these options... + func_arith $current + 1 + minor_current=$func_arith_result + xlcverstring="$wl-compatibility_version $wl$minor_current $wl-current_version $wl$minor_current.$revision" + verstring="-compatibility_version $minor_current -current_version $minor_current.$revision" + # On Darwin other compilers + case $CC in + nagfor*) + verstring="$wl-compatibility_version $wl$minor_current $wl-current_version $wl$minor_current.$revision" + ;; + *) + verstring="-compatibility_version $minor_current -current_version $minor_current.$revision" + ;; + esac + ;; + + freebsd-aout) + major=.$current + versuffix=.$current.$revision + ;; + + freebsd-elf | midnightbsd-elf) + func_arith $current - $age + major=.$func_arith_result + versuffix=$major.$age.$revision + ;; + + irix | nonstopux) + if test no = "$lt_irix_increment"; then + func_arith $current - $age + else + func_arith $current - $age + 1 + fi + major=$func_arith_result + + case $version_type in + nonstopux) verstring_prefix=nonstopux ;; + *) verstring_prefix=sgi ;; + esac + verstring=$verstring_prefix$major.$revision + + # Add in all the interfaces that we are compatible with. + loop=$revision + while test 0 -ne "$loop"; do + func_arith $revision - $loop + iface=$func_arith_result + func_arith $loop - 1 + loop=$func_arith_result + verstring=$verstring_prefix$major.$iface:$verstring + done + + # Before this point, $major must not contain '.'. + major=.$major + versuffix=$major.$revision + ;; + + linux) # correct to gnu/linux during the next big refactor + func_arith $current - $age + major=.$func_arith_result + versuffix=$major.$age.$revision + ;; + + osf) + func_arith $current - $age + major=.$func_arith_result + versuffix=.$current.$age.$revision + verstring=$current.$age.$revision + + # Add in all the interfaces that we are compatible with. + loop=$age + while test 0 -ne "$loop"; do + func_arith $current - $loop + iface=$func_arith_result + func_arith $loop - 1 + loop=$func_arith_result + verstring=$verstring:$iface.0 + done + + # Make executables depend on our current version. + func_append verstring ":$current.0" + ;; + + qnx) + major=.$current + versuffix=.$current + ;; + + sco) + major=.$current + versuffix=.$current + ;; + + sunos) + major=.$current + versuffix=.$current.$revision + ;; + + windows) + # Use '-' rather than '.', since we only want one + # extension on DOS 8.3 file systems. + func_arith $current - $age + major=$func_arith_result + versuffix=-$major + ;; + + *) + func_fatal_configuration "unknown library version type '$version_type'" + ;; + esac + + # Clear the version info if we defaulted, and they specified a release. + if test -z "$vinfo" && test -n "$release"; then + major= + case $version_type in + darwin) + # we can't check for "0.0" in archive_cmds due to quoting + # problems, so we reset it completely + verstring= + ;; + *) + verstring=0.0 + ;; + esac + if test no = "$need_version"; then + versuffix= + else + versuffix=.0.0 + fi + fi + + # Remove version info from name if versioning should be avoided + if test yes,no = "$avoid_version,$need_version"; then + major= + versuffix= + verstring= + fi + + # Check to see if the archive will have undefined symbols. + if test yes = "$allow_undefined"; then + if test unsupported = "$allow_undefined_flag"; then + if test yes = "$build_old_libs"; then + func_warning "undefined symbols not allowed in $host shared libraries; building static only" + build_libtool_libs=no + else + func_fatal_error "can't build $host shared library unless -no-undefined is specified" + fi + fi + else + # Don't allow undefined symbols. + allow_undefined_flag=$no_undefined_flag + fi + + fi + + func_generate_dlsyms "$libname" "$libname" : + func_append libobjs " $symfileobj" + test " " = "$libobjs" && libobjs= + + if test relink != "$opt_mode"; then + # Remove our outputs, but don't remove object files since they + # may have been created when compiling PIC objects. + removelist= + tempremovelist=`$ECHO "$output_objdir/*"` + for p in $tempremovelist; do + case $p in + *.$objext | *.gcno) + ;; + $output_objdir/$outputname | $output_objdir/$libname.* | $output_objdir/$libname$release.*) + if test -n "$precious_files_regex"; then + if $ECHO "$p" | $EGREP -e "$precious_files_regex" >/dev/null 2>&1 + then + continue + fi + fi + func_append removelist " $p" + ;; + *) ;; + esac + done + test -n "$removelist" && \ + func_show_eval "${RM}r \$removelist" + fi + + # Now set the variables for building old libraries. + if test yes = "$build_old_libs" && test convenience != "$build_libtool_libs"; then + func_append oldlibs " $output_objdir/$libname.$libext" + + # Transform .lo files to .o files. + oldobjs="$objs "`$ECHO "$libobjs" | $SP2NL | $SED "/\.$libext$/d; $lo2o" | $NL2SP` + fi + + # Eliminate all temporary directories. + #for path in $notinst_path; do + # lib_search_path=`$ECHO "$lib_search_path " | $SED "s% $path % %g"` + # deplibs=`$ECHO "$deplibs " | $SED "s% -L$path % %g"` + # dependency_libs=`$ECHO "$dependency_libs " | $SED "s% -L$path % %g"` + #done + + if test -n "$xrpath"; then + # If the user specified any rpath flags, then add them. + temp_xrpath= + for libdir in $xrpath; do + func_replace_sysroot "$libdir" + func_append temp_xrpath " -R$func_replace_sysroot_result" + case "$finalize_rpath " in + *" $libdir "*) ;; + *) func_append finalize_rpath " $libdir" ;; + esac + done + if test yes != "$hardcode_into_libs" || test yes = "$build_old_libs"; then + dependency_libs="$temp_xrpath $dependency_libs" + fi + fi + + # Make sure dlfiles contains only unique files that won't be dlpreopened + old_dlfiles=$dlfiles + dlfiles= + for lib in $old_dlfiles; do + case " $dlprefiles $dlfiles " in + *" $lib "*) ;; + *) func_append dlfiles " $lib" ;; + esac + done + + # Make sure dlprefiles contains only unique files + old_dlprefiles=$dlprefiles + dlprefiles= + for lib in $old_dlprefiles; do + case "$dlprefiles " in + *" $lib "*) ;; + *) func_append dlprefiles " $lib" ;; + esac + done + + if test yes = "$build_libtool_libs"; then + if test -n "$rpath"; then + case $host in + *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-*-beos* | *-cegcc* | *-*-haiku*) + # these systems don't actually have a c library (as such)! + ;; + *-*-rhapsody* | *-*-darwin1.[012]) + # Rhapsody C library is in the System framework + func_append deplibs " System.ltframework" + ;; + *-*-netbsd*) + # Don't link with libc until the a.out ld.so is fixed. + ;; + *-*-openbsd* | *-*-freebsd* | *-*-dragonfly* | *-*-midnightbsd*) + # Do not include libc due to us having libc/libc_r. + ;; + *-*-sco3.2v5* | *-*-sco5v6*) + # Causes problems with __ctype + ;; + *-*-sysv4.2uw2* | *-*-sysv5* | *-*-unixware* | *-*-OpenUNIX*) + # Compiler inserts libc in the correct place for threads to work + ;; + *) + # Add libc to deplibs on all other systems if necessary. + if test yes = "$build_libtool_need_lc"; then + func_append deplibs " -lc" + fi + ;; + esac + fi + + # Transform deplibs into only deplibs that can be linked in shared. + name_save=$name + libname_save=$libname + release_save=$release + versuffix_save=$versuffix + major_save=$major + # I'm not sure if I'm treating the release correctly. I think + # release should show up in the -l (ie -lgmp5) so we don't want to + # add it in twice. Is that correct? + release= + versuffix= + major= + newdeplibs= + droppeddeps=no + case $deplibs_check_method in + pass_all) + # Don't check for shared/static. Everything works. + # This might be a little naive. We might want to check + # whether the library exists or not. But this is on + # osf3 & osf4 and I'm not really sure... Just + # implementing what was already the behavior. + newdeplibs=$deplibs + ;; + test_compile) + # This code stresses the "libraries are programs" paradigm to its + # limits. Maybe even breaks it. We compile a program, linking it + # against the deplibs as a proxy for the library. Then we can check + # whether they linked in statically or dynamically with ldd. + $opt_dry_run || $RM conftest.c + cat > conftest.c </dev/null` + $nocaseglob + else + potential_libs=`ls $i/$libnameglob[.-]* 2>/dev/null` + fi + for potent_lib in $potential_libs; do + # Follow soft links. + if ls -lLd "$potent_lib" 2>/dev/null | + $GREP " -> " >/dev/null; then + continue + fi + # The statement above tries to avoid entering an + # endless loop below, in case of cyclic links. + # We might still enter an endless loop, since a link + # loop can be closed while we follow links, + # but so what? + potlib=$potent_lib + while test -h "$potlib" 2>/dev/null; do + potliblink=`ls -ld $potlib | $SED 's/.* -> //'` + case $potliblink in + [\\/]* | [A-Za-z]:[\\/]*) potlib=$potliblink;; + *) potlib=`$ECHO "$potlib" | $SED 's|[^/]*$||'`"$potliblink";; + esac + done + if eval $file_magic_cmd \"\$potlib\" 2>/dev/null | + $SED -e 10q | + $EGREP "$file_magic_regex" > /dev/null; then + func_append newdeplibs " $a_deplib" + a_deplib= + break 2 + fi + done + done + fi + if test -n "$a_deplib"; then + droppeddeps=yes + echo + $ECHO "*** Warning: linker path does not have real file for library $a_deplib." + echo "*** I have the capability to make that library automatically link in when" + echo "*** you link to this library. But I can only do this if you have a" + echo "*** shared version of the library, which you do not appear to have" + echo "*** because I did check the linker path looking for a file starting" + if test -z "$potlib"; then + $ECHO "*** with $libname but no candidates were found. (...for file magic test)" + else + $ECHO "*** with $libname and none of the candidates passed a file format test" + $ECHO "*** using a file magic. Last file checked: $potlib" + fi + fi + ;; + *) + # Add a -L argument. + func_append newdeplibs " $a_deplib" + ;; + esac + done # Gone through all deplibs. + ;; + match_pattern*) + set dummy $deplibs_check_method; shift + match_pattern_regex=`expr "$deplibs_check_method" : "$1 \(.*\)"` + for a_deplib in $deplibs; do + case $a_deplib in + -l*) + func_stripname -l '' "$a_deplib" + name=$func_stripname_result + if test yes = "$allow_libtool_libs_with_static_runtimes"; then + case " $predeps $postdeps " in + *" $a_deplib "*) + func_append newdeplibs " $a_deplib" + a_deplib= + ;; + esac + fi + if test -n "$a_deplib"; then + libname=`eval "\\$ECHO \"$libname_spec\""` + for i in $lib_search_path $sys_lib_search_path $shlib_search_path; do + potential_libs=`ls $i/$libname[.-]* 2>/dev/null` + for potent_lib in $potential_libs; do + potlib=$potent_lib # see symlink-check above in file_magic test + if eval "\$ECHO \"$potent_lib\"" 2>/dev/null | $SED 10q | \ + $EGREP "$match_pattern_regex" > /dev/null; then + func_append newdeplibs " $a_deplib" + a_deplib= + break 2 + fi + done + done + fi + if test -n "$a_deplib"; then + droppeddeps=yes + echo + $ECHO "*** Warning: linker path does not have real file for library $a_deplib." + echo "*** I have the capability to make that library automatically link in when" + echo "*** you link to this library. But I can only do this if you have a" + echo "*** shared version of the library, which you do not appear to have" + echo "*** because I did check the linker path looking for a file starting" + if test -z "$potlib"; then + $ECHO "*** with $libname but no candidates were found. (...for regex pattern test)" + else + $ECHO "*** with $libname and none of the candidates passed a file format test" + $ECHO "*** using a regex pattern. Last file checked: $potlib" + fi + fi + ;; + *) + # Add a -L argument. + func_append newdeplibs " $a_deplib" + ;; + esac + done # Gone through all deplibs. + ;; + none | unknown | *) + newdeplibs= + tmp_deplibs=`$ECHO " $deplibs" | $SED 's/ -lc$//; s/ -[LR][^ ]*//g'` + if test yes = "$allow_libtool_libs_with_static_runtimes"; then + for i in $predeps $postdeps; do + # can't use Xsed below, because $i might contain '/' + tmp_deplibs=`$ECHO " $tmp_deplibs" | $SED "s|$i||"` + done + fi + case $tmp_deplibs in + *[!\ \ ]*) + echo + if test none = "$deplibs_check_method"; then + echo "*** Warning: inter-library dependencies are not supported in this platform." + else + echo "*** Warning: inter-library dependencies are not known to be supported." + fi + echo "*** All declared inter-library dependencies are being dropped." + droppeddeps=yes + ;; + esac + ;; + esac + versuffix=$versuffix_save + major=$major_save + release=$release_save + libname=$libname_save + name=$name_save + + case $host in + *-*-rhapsody* | *-*-darwin1.[012]) + # On Rhapsody replace the C library with the System framework + newdeplibs=`$ECHO " $newdeplibs" | $SED 's/ -lc / System.ltframework /'` + ;; + esac + + if test yes = "$droppeddeps"; then + if test yes = "$module"; then + echo + echo "*** Warning: libtool could not satisfy all declared inter-library" + $ECHO "*** dependencies of module $libname. Therefore, libtool will create" + echo "*** a static module, that should work as long as the dlopening" + echo "*** application is linked with the -dlopen flag." + if test -z "$global_symbol_pipe"; then + echo + echo "*** However, this would only work if libtool was able to extract symbol" + echo "*** lists from a program, using 'nm' or equivalent, but libtool could" + echo "*** not find such a program. So, this module is probably useless." + echo "*** 'nm' from GNU binutils and a full rebuild may help." + fi + if test no = "$build_old_libs"; then + oldlibs=$output_objdir/$libname.$libext + build_libtool_libs=module + build_old_libs=yes + else + build_libtool_libs=no + fi + else + echo "*** The inter-library dependencies that have been dropped here will be" + echo "*** automatically added whenever a program is linked with this library" + echo "*** or is declared to -dlopen it." + + if test no = "$allow_undefined"; then + echo + echo "*** Since this library must not contain undefined symbols," + echo "*** because either the platform does not support them or" + echo "*** it was explicitly requested with -no-undefined," + echo "*** libtool will only create a static version of it." + if test no = "$build_old_libs"; then + oldlibs=$output_objdir/$libname.$libext + build_libtool_libs=module + build_old_libs=yes + else + build_libtool_libs=no + fi + fi + fi + fi + # Done checking deplibs! + deplibs=$newdeplibs + fi + # Time to change all our "foo.ltframework" stuff back to "-framework foo" + case $host in + *-*-darwin*) + newdeplibs=`$ECHO " $newdeplibs" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` + new_inherited_linker_flags=`$ECHO " $new_inherited_linker_flags" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` + deplibs=`$ECHO " $deplibs" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` + ;; + esac + + # move library search paths that coincide with paths to not yet + # installed libraries to the beginning of the library search list + new_libs= + for path in $notinst_path; do + case " $new_libs " in + *" -L$path/$objdir "*) ;; + *) + case " $deplibs " in + *" -L$path/$objdir "*) + func_append new_libs " -L$path/$objdir" ;; + esac + ;; + esac + done + for deplib in $deplibs; do + case $deplib in + -L*) + case " $new_libs " in + *" $deplib "*) ;; + *) func_append new_libs " $deplib" ;; + esac + ;; + *) func_append new_libs " $deplib" ;; + esac + done + deplibs=$new_libs + + # All the library-specific variables (install_libdir is set above). + library_names= + old_library= + dlname= + + # Test again, we may have decided not to build it any more + if test yes = "$build_libtool_libs"; then + # Remove $wl instances when linking with ld. + # FIXME: should test the right _cmds variable. + case $archive_cmds in + *\$LD\ *) wl= ;; + esac + if test yes = "$hardcode_into_libs"; then + # Hardcode the library paths + hardcode_libdirs= + dep_rpath= + rpath=$finalize_rpath + test relink = "$opt_mode" || rpath=$compile_rpath$rpath + for libdir in $rpath; do + if test -n "$hardcode_libdir_flag_spec"; then + if test -n "$hardcode_libdir_separator"; then + func_replace_sysroot "$libdir" + libdir=$func_replace_sysroot_result + if test -z "$hardcode_libdirs"; then + hardcode_libdirs=$libdir + else + # Just accumulate the unique libdirs. + case $hardcode_libdir_separator$hardcode_libdirs$hardcode_libdir_separator in + *"$hardcode_libdir_separator$libdir$hardcode_libdir_separator"*) + ;; + *) + func_append hardcode_libdirs "$hardcode_libdir_separator$libdir" + ;; + esac + fi + else + eval flag=\"$hardcode_libdir_flag_spec\" + func_append dep_rpath " $flag" + fi + elif test -n "$runpath_var"; then + case "$perm_rpath " in + *" $libdir "*) ;; + *) func_append perm_rpath " $libdir" ;; + esac + fi + done + # Substitute the hardcoded libdirs into the rpath. + if test -n "$hardcode_libdir_separator" && + test -n "$hardcode_libdirs"; then + libdir=$hardcode_libdirs + eval "dep_rpath=\"$hardcode_libdir_flag_spec\"" + fi + if test -n "$runpath_var" && test -n "$perm_rpath"; then + # We should set the runpath_var. + rpath= + for dir in $perm_rpath; do + func_append rpath "$dir:" + done + eval "$runpath_var='$rpath\$$runpath_var'; export $runpath_var" + fi + test -n "$dep_rpath" && deplibs="$dep_rpath $deplibs" + fi + + shlibpath=$finalize_shlibpath + test relink = "$opt_mode" || shlibpath=$compile_shlibpath$shlibpath + if test -n "$shlibpath"; then + eval "$shlibpath_var='$shlibpath\$$shlibpath_var'; export $shlibpath_var" + fi + + # Get the real and link names of the library. + eval shared_ext=\"$shrext_cmds\" + eval library_names=\"$library_names_spec\" + set dummy $library_names + shift + realname=$1 + shift + + if test -n "$soname_spec"; then + eval soname=\"$soname_spec\" + else + soname=$realname + fi + if test -z "$dlname"; then + dlname=$soname + fi + + lib=$output_objdir/$realname + linknames= + for link + do + func_append linknames " $link" + done + + # Use standard objects if they are pic + test -z "$pic_flag" && libobjs=`$ECHO "$libobjs" | $SP2NL | $SED "$lo2o" | $NL2SP` + test "X$libobjs" = "X " && libobjs= + + delfiles= + if test -n "$export_symbols" && test -n "$include_expsyms"; then + $opt_dry_run || cp "$export_symbols" "$output_objdir/$libname.uexp" + export_symbols=$output_objdir/$libname.uexp + func_append delfiles " $export_symbols" + fi + + orig_export_symbols= + case $host_os in + cygwin* | mingw* | cegcc*) + if test -n "$export_symbols" && test -z "$export_symbols_regex"; then + # exporting using user supplied symfile + func_dll_def_p "$export_symbols" || { + # and it's NOT already a .def file. Must figure out + # which of the given symbols are data symbols and tag + # them as such. So, trigger use of export_symbols_cmds. + # export_symbols gets reassigned inside the "prepare + # the list of exported symbols" if statement, so the + # include_expsyms logic still works. + orig_export_symbols=$export_symbols + export_symbols= + always_export_symbols=yes + } + fi + ;; + esac + + # Prepare the list of exported symbols + if test -z "$export_symbols"; then + if test yes = "$always_export_symbols" || test -n "$export_symbols_regex"; then + func_verbose "generating symbol list for '$libname.la'" + export_symbols=$output_objdir/$libname.exp + $opt_dry_run || $RM $export_symbols + cmds=$export_symbols_cmds + save_ifs=$IFS; IFS='~' + for cmd1 in $cmds; do + IFS=$save_ifs + # Take the normal branch if the nm_file_list_spec branch + # doesn't work or if tool conversion is not needed. + case $nm_file_list_spec~$to_tool_file_cmd in + *~func_convert_file_noop | *~func_convert_file_msys_to_w32 | ~*) + try_normal_branch=yes + eval cmd=\"$cmd1\" + func_len " $cmd" + len=$func_len_result + ;; + *) + try_normal_branch=no + ;; + esac + if test yes = "$try_normal_branch" \ + && { test "$len" -lt "$max_cmd_len" \ + || test "$max_cmd_len" -le -1; } + then + func_show_eval "$cmd" 'exit $?' + skipped_export=false + elif test -n "$nm_file_list_spec"; then + func_basename "$output" + output_la=$func_basename_result + save_libobjs=$libobjs + save_output=$output + output=$output_objdir/$output_la.nm + func_to_tool_file "$output" + libobjs=$nm_file_list_spec$func_to_tool_file_result + func_append delfiles " $output" + func_verbose "creating $NM input file list: $output" + for obj in $save_libobjs; do + func_to_tool_file "$obj" + $ECHO "$func_to_tool_file_result" + done > "$output" + eval cmd=\"$cmd1\" + func_show_eval "$cmd" 'exit $?' + output=$save_output + libobjs=$save_libobjs + skipped_export=false + else + # The command line is too long to execute in one step. + func_verbose "using reloadable object file for export list..." + skipped_export=: + # Break out early, otherwise skipped_export may be + # set to false by a later but shorter cmd. + break + fi + done + IFS=$save_ifs + if test -n "$export_symbols_regex" && test : != "$skipped_export"; then + func_show_eval '$EGREP -e "$export_symbols_regex" "$export_symbols" > "${export_symbols}T"' + func_show_eval '$MV "${export_symbols}T" "$export_symbols"' + fi + fi + fi + + if test -n "$export_symbols" && test -n "$include_expsyms"; then + tmp_export_symbols=$export_symbols + test -n "$orig_export_symbols" && tmp_export_symbols=$orig_export_symbols + $opt_dry_run || eval '$ECHO "$include_expsyms" | $SP2NL >> "$tmp_export_symbols"' + fi + + if test : != "$skipped_export" && test -n "$orig_export_symbols"; then + # The given exports_symbols file has to be filtered, so filter it. + func_verbose "filter symbol list for '$libname.la' to tag DATA exports" + # FIXME: $output_objdir/$libname.filter potentially contains lots of + # 's' commands, which not all seds can handle. GNU sed should be fine + # though. Also, the filter scales superlinearly with the number of + # global variables. join(1) would be nice here, but unfortunately + # isn't a blessed tool. + $opt_dry_run || $SED -e '/[ ,]DATA/!d;s,\(.*\)\([ \,].*\),s|^\1$|\1\2|,' < $export_symbols > $output_objdir/$libname.filter + func_append delfiles " $export_symbols $output_objdir/$libname.filter" + export_symbols=$output_objdir/$libname.def + $opt_dry_run || $SED -f $output_objdir/$libname.filter < $orig_export_symbols > $export_symbols + fi + + tmp_deplibs= + for test_deplib in $deplibs; do + case " $convenience " in + *" $test_deplib "*) ;; + *) + func_append tmp_deplibs " $test_deplib" + ;; + esac + done + deplibs=$tmp_deplibs + + if test -n "$convenience"; then + if test -n "$whole_archive_flag_spec" && + test yes = "$compiler_needs_object" && + test -z "$libobjs"; then + # extract the archives, so we have objects to list. + # TODO: could optimize this to just extract one archive. + whole_archive_flag_spec= + fi + if test -n "$whole_archive_flag_spec"; then + save_libobjs=$libobjs + eval libobjs=\"\$libobjs $whole_archive_flag_spec\" + test "X$libobjs" = "X " && libobjs= + else + gentop=$output_objdir/${outputname}x + func_append generated " $gentop" + + func_extract_archives $gentop $convenience + func_append libobjs " $func_extract_archives_result" + test "X$libobjs" = "X " && libobjs= + fi + fi + + if test yes = "$thread_safe" && test -n "$thread_safe_flag_spec"; then + eval flag=\"$thread_safe_flag_spec\" + func_append linker_flags " $flag" + fi + + # Make a backup of the uninstalled library when relinking + if test relink = "$opt_mode"; then + $opt_dry_run || eval '(cd $output_objdir && $RM ${realname}U && $MV $realname ${realname}U)' || exit $? + fi + + # Do each of the archive commands. + if test yes = "$module" && test -n "$module_cmds"; then + if test -n "$export_symbols" && test -n "$module_expsym_cmds"; then + eval test_cmds=\"$module_expsym_cmds\" + cmds=$module_expsym_cmds + else + eval test_cmds=\"$module_cmds\" + cmds=$module_cmds + fi + else + if test -n "$export_symbols" && test -n "$archive_expsym_cmds"; then + eval test_cmds=\"$archive_expsym_cmds\" + cmds=$archive_expsym_cmds + else + eval test_cmds=\"$archive_cmds\" + cmds=$archive_cmds + fi + fi + + if test : != "$skipped_export" && + func_len " $test_cmds" && + len=$func_len_result && + test "$len" -lt "$max_cmd_len" || test "$max_cmd_len" -le -1; then + : + else + # The command line is too long to link in one step, link piecewise + # or, if using GNU ld and skipped_export is not :, use a linker + # script. + + # Save the value of $output and $libobjs because we want to + # use them later. If we have whole_archive_flag_spec, we + # want to use save_libobjs as it was before + # whole_archive_flag_spec was expanded, because we can't + # assume the linker understands whole_archive_flag_spec. + # This may have to be revisited, in case too many + # convenience libraries get linked in and end up exceeding + # the spec. + if test -z "$convenience" || test -z "$whole_archive_flag_spec"; then + save_libobjs=$libobjs + fi + save_output=$output + func_basename "$output" + output_la=$func_basename_result + + # Clear the reloadable object creation command queue and + # initialize k to one. + test_cmds= + concat_cmds= + objlist= + last_robj= + k=1 + + if test -n "$save_libobjs" && test : != "$skipped_export" && test yes = "$with_gnu_ld"; then + output=$output_objdir/$output_la.lnkscript + func_verbose "creating GNU ld script: $output" + echo 'INPUT (' > $output + for obj in $save_libobjs + do + func_to_tool_file "$obj" + $ECHO "$func_to_tool_file_result" >> $output + done + echo ')' >> $output + func_append delfiles " $output" + func_to_tool_file "$output" + output=$func_to_tool_file_result + elif test -n "$save_libobjs" && test : != "$skipped_export" && test -n "$file_list_spec"; then + output=$output_objdir/$output_la.lnk + func_verbose "creating linker input file list: $output" + : > $output + set x $save_libobjs + shift + firstobj= + if test yes = "$compiler_needs_object"; then + firstobj="$1 " + shift + fi + for obj + do + func_to_tool_file "$obj" + $ECHO "$func_to_tool_file_result" >> $output + done + func_append delfiles " $output" + func_to_tool_file "$output" + output=$firstobj\"$file_list_spec$func_to_tool_file_result\" + else + if test -n "$save_libobjs"; then + func_verbose "creating reloadable object files..." + output=$output_objdir/$output_la-$k.$objext + eval test_cmds=\"$reload_cmds\" + func_len " $test_cmds" + len0=$func_len_result + len=$len0 + + # Loop over the list of objects to be linked. + for obj in $save_libobjs + do + func_len " $obj" + func_arith $len + $func_len_result + len=$func_arith_result + if test -z "$objlist" || + test "$len" -lt "$max_cmd_len"; then + func_append objlist " $obj" + else + # The command $test_cmds is almost too long, add a + # command to the queue. + if test 1 -eq "$k"; then + # The first file doesn't have a previous command to add. + reload_objs=$objlist + eval concat_cmds=\"$reload_cmds\" + else + # All subsequent reloadable object files will link in + # the last one created. + reload_objs="$objlist $last_robj" + eval concat_cmds=\"\$concat_cmds~$reload_cmds~\$RM $last_robj\" + fi + last_robj=$output_objdir/$output_la-$k.$objext + func_arith $k + 1 + k=$func_arith_result + output=$output_objdir/$output_la-$k.$objext + objlist=" $obj" + func_len " $last_robj" + func_arith $len0 + $func_len_result + len=$func_arith_result + fi + done + # Handle the remaining objects by creating one last + # reloadable object file. All subsequent reloadable object + # files will link in the last one created. + test -z "$concat_cmds" || concat_cmds=$concat_cmds~ + reload_objs="$objlist $last_robj" + eval concat_cmds=\"\$concat_cmds$reload_cmds\" + if test -n "$last_robj"; then + eval concat_cmds=\"\$concat_cmds~\$RM $last_robj\" + fi + func_append delfiles " $output" + + else + output= + fi + + ${skipped_export-false} && { + func_verbose "generating symbol list for '$libname.la'" + export_symbols=$output_objdir/$libname.exp + $opt_dry_run || $RM $export_symbols + libobjs=$output + # Append the command to create the export file. + test -z "$concat_cmds" || concat_cmds=$concat_cmds~ + eval concat_cmds=\"\$concat_cmds$export_symbols_cmds\" + if test -n "$last_robj"; then + eval concat_cmds=\"\$concat_cmds~\$RM $last_robj\" + fi + } + + test -n "$save_libobjs" && + func_verbose "creating a temporary reloadable object file: $output" + + # Loop through the commands generated above and execute them. + save_ifs=$IFS; IFS='~' + for cmd in $concat_cmds; do + IFS=$save_ifs + $opt_quiet || { + func_quote_arg expand,pretty "$cmd" + eval "func_echo $func_quote_arg_result" + } + $opt_dry_run || eval "$cmd" || { + lt_exit=$? + + # Restore the uninstalled library and exit + if test relink = "$opt_mode"; then + ( cd "$output_objdir" && \ + $RM "${realname}T" && \ + $MV "${realname}U" "$realname" ) + fi + + exit $lt_exit + } + done + IFS=$save_ifs + + if test -n "$export_symbols_regex" && ${skipped_export-false}; then + func_show_eval '$EGREP -e "$export_symbols_regex" "$export_symbols" > "${export_symbols}T"' + func_show_eval '$MV "${export_symbols}T" "$export_symbols"' + fi + fi + + ${skipped_export-false} && { + if test -n "$export_symbols" && test -n "$include_expsyms"; then + tmp_export_symbols=$export_symbols + test -n "$orig_export_symbols" && tmp_export_symbols=$orig_export_symbols + $opt_dry_run || eval '$ECHO "$include_expsyms" | $SP2NL >> "$tmp_export_symbols"' + fi + + if test -n "$orig_export_symbols"; then + # The given exports_symbols file has to be filtered, so filter it. + func_verbose "filter symbol list for '$libname.la' to tag DATA exports" + # FIXME: $output_objdir/$libname.filter potentially contains lots of + # 's' commands, which not all seds can handle. GNU sed should be fine + # though. Also, the filter scales superlinearly with the number of + # global variables. join(1) would be nice here, but unfortunately + # isn't a blessed tool. + $opt_dry_run || $SED -e '/[ ,]DATA/!d;s,\(.*\)\([ \,].*\),s|^\1$|\1\2|,' < $export_symbols > $output_objdir/$libname.filter + func_append delfiles " $export_symbols $output_objdir/$libname.filter" + export_symbols=$output_objdir/$libname.def + $opt_dry_run || $SED -f $output_objdir/$libname.filter < $orig_export_symbols > $export_symbols + fi + } + + libobjs=$output + # Restore the value of output. + output=$save_output + + if test -n "$convenience" && test -n "$whole_archive_flag_spec"; then + eval libobjs=\"\$libobjs $whole_archive_flag_spec\" + test "X$libobjs" = "X " && libobjs= + fi + # Expand the library linking commands again to reset the + # value of $libobjs for piecewise linking. + + # Do each of the archive commands. + if test yes = "$module" && test -n "$module_cmds"; then + if test -n "$export_symbols" && test -n "$module_expsym_cmds"; then + cmds=$module_expsym_cmds + else + cmds=$module_cmds + fi + else + if test -n "$export_symbols" && test -n "$archive_expsym_cmds"; then + cmds=$archive_expsym_cmds + else + cmds=$archive_cmds + fi + fi + fi + + if test -n "$delfiles"; then + # Append the command to remove temporary files to $cmds. + eval cmds=\"\$cmds~\$RM $delfiles\" + fi + + # Add any objects from preloaded convenience libraries + if test -n "$dlprefiles"; then + gentop=$output_objdir/${outputname}x + func_append generated " $gentop" + + func_extract_archives $gentop $dlprefiles + func_append libobjs " $func_extract_archives_result" + test "X$libobjs" = "X " && libobjs= + fi + + save_ifs=$IFS; IFS='~' + for cmd in $cmds; do + IFS=$sp$nl + eval cmd=\"$cmd\" + IFS=$save_ifs + $opt_quiet || { + func_quote_arg expand,pretty "$cmd" + eval "func_echo $func_quote_arg_result" + } + $opt_dry_run || eval "$cmd" || { + lt_exit=$? + + # Restore the uninstalled library and exit + if test relink = "$opt_mode"; then + ( cd "$output_objdir" && \ + $RM "${realname}T" && \ + $MV "${realname}U" "$realname" ) + fi + + exit $lt_exit + } + done + IFS=$save_ifs + + # Restore the uninstalled library and exit + if test relink = "$opt_mode"; then + $opt_dry_run || eval '(cd $output_objdir && $RM ${realname}T && $MV $realname ${realname}T && $MV ${realname}U $realname)' || exit $? + + if test -n "$convenience"; then + if test -z "$whole_archive_flag_spec"; then + func_show_eval '${RM}r "$gentop"' + fi + fi + + exit $EXIT_SUCCESS + fi + + # Create links to the real library. + for linkname in $linknames; do + if test "$realname" != "$linkname"; then + func_show_eval '(cd "$output_objdir" && $RM "$linkname" && $LN_S "$realname" "$linkname")' 'exit $?' + fi + done + + # If -module or -export-dynamic was specified, set the dlname. + if test yes = "$module" || test yes = "$export_dynamic"; then + # On all known operating systems, these are identical. + dlname=$soname + fi + fi + ;; + + obj) + if test -n "$dlfiles$dlprefiles" || test no != "$dlself"; then + func_warning "'-dlopen' is ignored for objects" + fi + + case " $deplibs" in + *\ -l* | *\ -L*) + func_warning "'-l' and '-L' are ignored for objects" ;; + esac + + test -n "$rpath" && \ + func_warning "'-rpath' is ignored for objects" + + test -n "$xrpath" && \ + func_warning "'-R' is ignored for objects" + + test -n "$vinfo" && \ + func_warning "'-version-info' is ignored for objects" + + test -n "$release" && \ + func_warning "'-release' is ignored for objects" + + case $output in + *.lo) + test -n "$objs$old_deplibs" && \ + func_fatal_error "cannot build library object '$output' from non-libtool objects" + + libobj=$output + func_lo2o "$libobj" + obj=$func_lo2o_result + ;; + *) + libobj= + obj=$output + ;; + esac + + # Delete the old objects. + $opt_dry_run || $RM $obj $libobj + + # Objects from convenience libraries. This assumes + # single-version convenience libraries. Whenever we create + # different ones for PIC/non-PIC, this we'll have to duplicate + # the extraction. + reload_conv_objs= + gentop= + # if reload_cmds runs $LD directly, get rid of -Wl from + # whole_archive_flag_spec and hope we can get by with turning comma + # into space. + case $reload_cmds in + *\$LD[\ \$]*) wl= ;; + esac + if test -n "$convenience"; then + if test -n "$whole_archive_flag_spec"; then + eval tmp_whole_archive_flags=\"$whole_archive_flag_spec\" + test -n "$wl" || tmp_whole_archive_flags=`$ECHO "$tmp_whole_archive_flags" | $SED 's|,| |g'` + reload_conv_objs=$reload_objs\ $tmp_whole_archive_flags + else + gentop=$output_objdir/${obj}x + func_append generated " $gentop" + + func_extract_archives $gentop $convenience + reload_conv_objs="$reload_objs $func_extract_archives_result" + fi + fi + + # If we're not building shared, we need to use non_pic_objs + test yes = "$build_libtool_libs" || libobjs=$non_pic_objects + + # Create the old-style object. + reload_objs=$objs$old_deplibs' '`$ECHO "$libobjs" | $SP2NL | $SED "/\.$libext$/d; /\.lib$/d; $lo2o" | $NL2SP`' '$reload_conv_objs + + output=$obj + func_execute_cmds "$reload_cmds" 'exit $?' + + # Exit if we aren't doing a library object file. + if test -z "$libobj"; then + if test -n "$gentop"; then + func_show_eval '${RM}r "$gentop"' + fi + + exit $EXIT_SUCCESS + fi + + test yes = "$build_libtool_libs" || { + if test -n "$gentop"; then + func_show_eval '${RM}r "$gentop"' + fi + + # Create an invalid libtool object if no PIC, so that we don't + # accidentally link it into a program. + # $show "echo timestamp > $libobj" + # $opt_dry_run || eval "echo timestamp > $libobj" || exit $? + exit $EXIT_SUCCESS + } + + if test -n "$pic_flag" || test default != "$pic_mode"; then + # Only do commands if we really have different PIC objects. + reload_objs="$libobjs $reload_conv_objs" + output=$libobj + func_execute_cmds "$reload_cmds" 'exit $?' + fi + + if test -n "$gentop"; then + func_show_eval '${RM}r "$gentop"' + fi + + exit $EXIT_SUCCESS + ;; + + prog) + case $host in + *cygwin*) func_stripname '' '.exe' "$output" + output=$func_stripname_result.exe;; + esac + test -n "$vinfo" && \ + func_warning "'-version-info' is ignored for programs" + + test -n "$release" && \ + func_warning "'-release' is ignored for programs" + + $preload \ + && test unknown,unknown,unknown = "$dlopen_support,$dlopen_self,$dlopen_self_static" \ + && func_warning "'LT_INIT([dlopen])' not used. Assuming no dlopen support." + + case $host in + *-*-rhapsody* | *-*-darwin1.[012]) + # On Rhapsody replace the C library is the System framework + compile_deplibs=`$ECHO " $compile_deplibs" | $SED 's/ -lc / System.ltframework /'` + finalize_deplibs=`$ECHO " $finalize_deplibs" | $SED 's/ -lc / System.ltframework /'` + ;; + esac + + case $host in + *-*-darwin*) + # Don't allow lazy linking, it breaks C++ global constructors + # But is supposedly fixed on 10.4 or later (yay!). + if test CXX = "$tagname"; then + case ${MACOSX_DEPLOYMENT_TARGET-10.0} in + 10.[0123]) + func_append compile_command " $wl-bind_at_load" + func_append finalize_command " $wl-bind_at_load" + ;; + esac + fi + # Time to change all our "foo.ltframework" stuff back to "-framework foo" + compile_deplibs=`$ECHO " $compile_deplibs" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` + finalize_deplibs=`$ECHO " $finalize_deplibs" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` + ;; + esac + + + # move library search paths that coincide with paths to not yet + # installed libraries to the beginning of the library search list + new_libs= + for path in $notinst_path; do + case " $new_libs " in + *" -L$path/$objdir "*) ;; + *) + case " $compile_deplibs " in + *" -L$path/$objdir "*) + func_append new_libs " -L$path/$objdir" ;; + esac + ;; + esac + done + for deplib in $compile_deplibs; do + case $deplib in + -L*) + case " $new_libs " in + *" $deplib "*) ;; + *) func_append new_libs " $deplib" ;; + esac + ;; + *) func_append new_libs " $deplib" ;; + esac + done + compile_deplibs=$new_libs + + + func_append compile_command " $compile_deplibs" + func_append finalize_command " $finalize_deplibs" + + if test -n "$rpath$xrpath"; then + # If the user specified any rpath flags, then add them. + for libdir in $rpath $xrpath; do + # This is the magic to use -rpath. + case "$finalize_rpath " in + *" $libdir "*) ;; + *) func_append finalize_rpath " $libdir" ;; + esac + done + fi + + # Now hardcode the library paths + rpath= + hardcode_libdirs= + for libdir in $compile_rpath $finalize_rpath; do + if test -n "$hardcode_libdir_flag_spec"; then + if test -n "$hardcode_libdir_separator"; then + if test -z "$hardcode_libdirs"; then + hardcode_libdirs=$libdir + else + # Just accumulate the unique libdirs. + case $hardcode_libdir_separator$hardcode_libdirs$hardcode_libdir_separator in + *"$hardcode_libdir_separator$libdir$hardcode_libdir_separator"*) + ;; + *) + func_append hardcode_libdirs "$hardcode_libdir_separator$libdir" + ;; + esac + fi + else + eval flag=\"$hardcode_libdir_flag_spec\" + func_append rpath " $flag" + fi + elif test -n "$runpath_var"; then + case "$perm_rpath " in + *" $libdir "*) ;; + *) func_append perm_rpath " $libdir" ;; + esac + fi + case $host in + *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-cegcc*) + testbindir=`$ECHO "$libdir" | $SED -e 's*/lib$*/bin*'` + case :$dllsearchpath: in + *":$libdir:"*) ;; + ::) dllsearchpath=$libdir;; + *) func_append dllsearchpath ":$libdir";; + esac + case :$dllsearchpath: in + *":$testbindir:"*) ;; + ::) dllsearchpath=$testbindir;; + *) func_append dllsearchpath ":$testbindir";; + esac + ;; + esac + done + # Substitute the hardcoded libdirs into the rpath. + if test -n "$hardcode_libdir_separator" && + test -n "$hardcode_libdirs"; then + libdir=$hardcode_libdirs + eval rpath=\" $hardcode_libdir_flag_spec\" + fi + compile_rpath=$rpath + + rpath= + hardcode_libdirs= + for libdir in $finalize_rpath; do + if test -n "$hardcode_libdir_flag_spec"; then + if test -n "$hardcode_libdir_separator"; then + if test -z "$hardcode_libdirs"; then + hardcode_libdirs=$libdir + else + # Just accumulate the unique libdirs. + case $hardcode_libdir_separator$hardcode_libdirs$hardcode_libdir_separator in + *"$hardcode_libdir_separator$libdir$hardcode_libdir_separator"*) + ;; + *) + func_append hardcode_libdirs "$hardcode_libdir_separator$libdir" + ;; + esac + fi + else + eval flag=\"$hardcode_libdir_flag_spec\" + func_append rpath " $flag" + fi + elif test -n "$runpath_var"; then + case "$finalize_perm_rpath " in + *" $libdir "*) ;; + *) func_append finalize_perm_rpath " $libdir" ;; + esac + fi + done + # Substitute the hardcoded libdirs into the rpath. + if test -n "$hardcode_libdir_separator" && + test -n "$hardcode_libdirs"; then + libdir=$hardcode_libdirs + eval rpath=\" $hardcode_libdir_flag_spec\" + fi + finalize_rpath=$rpath + + if test -n "$libobjs" && test yes = "$build_old_libs"; then + # Transform all the library objects into standard objects. + compile_command=`$ECHO "$compile_command" | $SP2NL | $SED "$lo2o" | $NL2SP` + finalize_command=`$ECHO "$finalize_command" | $SP2NL | $SED "$lo2o" | $NL2SP` + fi + + func_generate_dlsyms "$outputname" "@PROGRAM@" false + + # template prelinking step + if test -n "$prelink_cmds"; then + func_execute_cmds "$prelink_cmds" 'exit $?' + fi + + wrappers_required=: + case $host in + *cegcc* | *mingw32ce*) + # Disable wrappers for cegcc and mingw32ce hosts, we are cross compiling anyway. + wrappers_required=false + ;; + *cygwin* | *mingw* ) + test yes = "$build_libtool_libs" || wrappers_required=false + ;; + *) + if test no = "$need_relink" || test yes != "$build_libtool_libs"; then + wrappers_required=false + fi + ;; + esac + $wrappers_required || { + # Replace the output file specification. + compile_command=`$ECHO "$compile_command" | $SED 's%@OUTPUT@%'"$output"'%g'` + link_command=$compile_command$compile_rpath + + # We have no uninstalled library dependencies, so finalize right now. + exit_status=0 + func_show_eval "$link_command" 'exit_status=$?' + + if test -n "$postlink_cmds"; then + func_to_tool_file "$output" + postlink_cmds=`func_echo_all "$postlink_cmds" | $SED -e 's%@OUTPUT@%'"$output"'%g' -e 's%@TOOL_OUTPUT@%'"$func_to_tool_file_result"'%g'` + func_execute_cmds "$postlink_cmds" 'exit $?' + fi + + # Delete the generated files. + if test -f "$output_objdir/${outputname}S.$objext"; then + func_show_eval '$RM "$output_objdir/${outputname}S.$objext"' + fi + + exit $exit_status + } + + if test -n "$compile_shlibpath$finalize_shlibpath"; then + compile_command="$shlibpath_var=\"$compile_shlibpath$finalize_shlibpath\$$shlibpath_var\" $compile_command" + fi + if test -n "$finalize_shlibpath"; then + finalize_command="$shlibpath_var=\"$finalize_shlibpath\$$shlibpath_var\" $finalize_command" + fi + + compile_var= + finalize_var= + if test -n "$runpath_var"; then + if test -n "$perm_rpath"; then + # We should set the runpath_var. + rpath= + for dir in $perm_rpath; do + func_append rpath "$dir:" + done + compile_var="$runpath_var=\"$rpath\$$runpath_var\" " + fi + if test -n "$finalize_perm_rpath"; then + # We should set the runpath_var. + rpath= + for dir in $finalize_perm_rpath; do + func_append rpath "$dir:" + done + finalize_var="$runpath_var=\"$rpath\$$runpath_var\" " + fi + fi + + if test yes = "$no_install"; then + # We don't need to create a wrapper script. + link_command=$compile_var$compile_command$compile_rpath + # Replace the output file specification. + link_command=`$ECHO "$link_command" | $SED 's%@OUTPUT@%'"$output"'%g'` + # Delete the old output file. + $opt_dry_run || $RM $output + # Link the executable and exit + func_show_eval "$link_command" 'exit $?' + + if test -n "$postlink_cmds"; then + func_to_tool_file "$output" + postlink_cmds=`func_echo_all "$postlink_cmds" | $SED -e 's%@OUTPUT@%'"$output"'%g' -e 's%@TOOL_OUTPUT@%'"$func_to_tool_file_result"'%g'` + func_execute_cmds "$postlink_cmds" 'exit $?' + fi + + exit $EXIT_SUCCESS + fi + + case $hardcode_action,$fast_install in + relink,*) + # Fast installation is not supported + link_command=$compile_var$compile_command$compile_rpath + relink_command=$finalize_var$finalize_command$finalize_rpath + + func_warning "this platform does not like uninstalled shared libraries" + func_warning "'$output' will be relinked during installation" + ;; + *,yes) + link_command=$finalize_var$compile_command$finalize_rpath + relink_command=`$ECHO "$compile_var$compile_command$compile_rpath" | $SED 's%@OUTPUT@%\$progdir/\$file%g'` + ;; + *,no) + link_command=$compile_var$compile_command$compile_rpath + relink_command=$finalize_var$finalize_command$finalize_rpath + ;; + *,needless) + link_command=$finalize_var$compile_command$finalize_rpath + relink_command= + ;; + esac + + # Replace the output file specification. + link_command=`$ECHO "$link_command" | $SED 's%@OUTPUT@%'"$output_objdir/$outputname"'%g'` + + # Delete the old output files. + $opt_dry_run || $RM $output $output_objdir/$outputname $output_objdir/lt-$outputname + + func_show_eval "$link_command" 'exit $?' + + if test -n "$postlink_cmds"; then + func_to_tool_file "$output_objdir/$outputname" + postlink_cmds=`func_echo_all "$postlink_cmds" | $SED -e 's%@OUTPUT@%'"$output_objdir/$outputname"'%g' -e 's%@TOOL_OUTPUT@%'"$func_to_tool_file_result"'%g'` + func_execute_cmds "$postlink_cmds" 'exit $?' + fi + + # Now create the wrapper script. + func_verbose "creating $output" + + # Quote the relink command for shipping. + if test -n "$relink_command"; then + # Preserve any variables that may affect compiler behavior + for var in $variables_saved_for_relink; do + if eval test -z \"\${$var+set}\"; then + relink_command="{ test -z \"\${$var+set}\" || $lt_unset $var || { $var=; export $var; }; }; $relink_command" + elif eval var_value=\$$var; test -z "$var_value"; then + relink_command="$var=; export $var; $relink_command" + else + func_quote_arg pretty "$var_value" + relink_command="$var=$func_quote_arg_result; export $var; $relink_command" + fi + done + func_quote eval cd "`pwd`" + func_quote_arg pretty,unquoted "($func_quote_result; $relink_command)" + relink_command=$func_quote_arg_unquoted_result + fi + + # Only actually do things if not in dry run mode. + $opt_dry_run || { + # win32 will think the script is a binary if it has + # a .exe suffix, so we strip it off here. + case $output in + *.exe) func_stripname '' '.exe' "$output" + output=$func_stripname_result ;; + esac + # test for cygwin because mv fails w/o .exe extensions + case $host in + *cygwin*) + exeext=.exe + func_stripname '' '.exe' "$outputname" + outputname=$func_stripname_result ;; + *) exeext= ;; + esac + case $host in + *cygwin* | *mingw* ) + func_dirname_and_basename "$output" "" "." + output_name=$func_basename_result + output_path=$func_dirname_result + cwrappersource=$output_path/$objdir/lt-$output_name.c + cwrapper=$output_path/$output_name.exe + $RM $cwrappersource $cwrapper + trap "$RM $cwrappersource $cwrapper; exit $EXIT_FAILURE" 1 2 15 + + func_emit_cwrapperexe_src > $cwrappersource + + # The wrapper executable is built using the $host compiler, + # because it contains $host paths and files. If cross- + # compiling, it, like the target executable, must be + # executed on the $host or under an emulation environment. + $opt_dry_run || { + $LTCC $LTCFLAGS -o $cwrapper $cwrappersource + $STRIP $cwrapper + } + + # Now, create the wrapper script for func_source use: + func_ltwrapper_scriptname $cwrapper + $RM $func_ltwrapper_scriptname_result + trap "$RM $func_ltwrapper_scriptname_result; exit $EXIT_FAILURE" 1 2 15 + $opt_dry_run || { + # note: this script will not be executed, so do not chmod. + if test "x$build" = "x$host"; then + $cwrapper --lt-dump-script > $func_ltwrapper_scriptname_result + else + func_emit_wrapper no > $func_ltwrapper_scriptname_result + fi + } + ;; + * ) + $RM $output + trap "$RM $output; exit $EXIT_FAILURE" 1 2 15 + + func_emit_wrapper no > $output + chmod +x $output + ;; + esac + } + exit $EXIT_SUCCESS + ;; + esac + + # See if we need to build an old-fashioned archive. + for oldlib in $oldlibs; do + + case $build_libtool_libs in + convenience) + oldobjs="$libobjs_save $symfileobj" + addlibs=$convenience + build_libtool_libs=no + ;; + module) + oldobjs=$libobjs_save + addlibs=$old_convenience + build_libtool_libs=no + ;; + *) + oldobjs="$old_deplibs $non_pic_objects" + $preload && test -f "$symfileobj" \ + && func_append oldobjs " $symfileobj" + addlibs=$old_convenience + ;; + esac + + if test -n "$addlibs"; then + gentop=$output_objdir/${outputname}x + func_append generated " $gentop" + + func_extract_archives $gentop $addlibs + func_append oldobjs " $func_extract_archives_result" + fi + + # Do each command in the archive commands. + if test -n "$old_archive_from_new_cmds" && test yes = "$build_libtool_libs"; then + cmds=$old_archive_from_new_cmds + else + + # Add any objects from preloaded convenience libraries + if test -n "$dlprefiles"; then + gentop=$output_objdir/${outputname}x + func_append generated " $gentop" + + func_extract_archives $gentop $dlprefiles + func_append oldobjs " $func_extract_archives_result" + fi + + # POSIX demands no paths to be encoded in archives. We have + # to avoid creating archives with duplicate basenames if we + # might have to extract them afterwards, e.g., when creating a + # static archive out of a convenience library, or when linking + # the entirety of a libtool archive into another (currently + # not supported by libtool). + if (for obj in $oldobjs + do + func_basename "$obj" + $ECHO "$func_basename_result" + done | sort | sort -uc >/dev/null 2>&1); then + : + else + echo "copying selected object files to avoid basename conflicts..." + gentop=$output_objdir/${outputname}x + func_append generated " $gentop" + func_mkdir_p "$gentop" + save_oldobjs=$oldobjs + oldobjs= + counter=1 + for obj in $save_oldobjs + do + func_basename "$obj" + objbase=$func_basename_result + case " $oldobjs " in + " ") oldobjs=$obj ;; + *[\ /]"$objbase "*) + while :; do + # Make sure we don't pick an alternate name that also + # overlaps. + newobj=lt$counter-$objbase + func_arith $counter + 1 + counter=$func_arith_result + case " $oldobjs " in + *[\ /]"$newobj "*) ;; + *) if test ! -f "$gentop/$newobj"; then break; fi ;; + esac + done + func_show_eval "ln $obj $gentop/$newobj || cp $obj $gentop/$newobj" + func_append oldobjs " $gentop/$newobj" + ;; + *) func_append oldobjs " $obj" ;; + esac + done + fi + func_to_tool_file "$oldlib" func_convert_file_msys_to_w32 + tool_oldlib=$func_to_tool_file_result + eval cmds=\"$old_archive_cmds\" + + func_len " $cmds" + len=$func_len_result + if test "$len" -lt "$max_cmd_len" || test "$max_cmd_len" -le -1; then + cmds=$old_archive_cmds + elif test -n "$archiver_list_spec"; then + func_verbose "using command file archive linking..." + for obj in $oldobjs + do + func_to_tool_file "$obj" + $ECHO "$func_to_tool_file_result" + done > $output_objdir/$libname.libcmd + func_to_tool_file "$output_objdir/$libname.libcmd" + oldobjs=" $archiver_list_spec$func_to_tool_file_result" + cmds=$old_archive_cmds + else + # the command line is too long to link in one step, link in parts + func_verbose "using piecewise archive linking..." + save_RANLIB=$RANLIB + RANLIB=: + objlist= + concat_cmds= + save_oldobjs=$oldobjs + oldobjs= + # Is there a better way of finding the last object in the list? + for obj in $save_oldobjs + do + last_oldobj=$obj + done + eval test_cmds=\"$old_archive_cmds\" + func_len " $test_cmds" + len0=$func_len_result + len=$len0 + for obj in $save_oldobjs + do + func_len " $obj" + func_arith $len + $func_len_result + len=$func_arith_result + func_append objlist " $obj" + if test "$len" -lt "$max_cmd_len"; then + : + else + # the above command should be used before it gets too long + oldobjs=$objlist + if test "$obj" = "$last_oldobj"; then + RANLIB=$save_RANLIB + fi + test -z "$concat_cmds" || concat_cmds=$concat_cmds~ + eval concat_cmds=\"\$concat_cmds$old_archive_cmds\" + objlist= + len=$len0 + fi + done + RANLIB=$save_RANLIB + oldobjs=$objlist + if test -z "$oldobjs"; then + eval cmds=\"\$concat_cmds\" + else + eval cmds=\"\$concat_cmds~\$old_archive_cmds\" + fi + fi + fi + func_execute_cmds "$cmds" 'exit $?' + done + + test -n "$generated" && \ + func_show_eval "${RM}r$generated" + + # Now create the libtool archive. + case $output in + *.la) + old_library= + test yes = "$build_old_libs" && old_library=$libname.$libext + func_verbose "creating $output" + + # Preserve any variables that may affect compiler behavior + for var in $variables_saved_for_relink; do + if eval test -z \"\${$var+set}\"; then + relink_command="{ test -z \"\${$var+set}\" || $lt_unset $var || { $var=; export $var; }; }; $relink_command" + elif eval var_value=\$$var; test -z "$var_value"; then + relink_command="$var=; export $var; $relink_command" + else + func_quote_arg pretty,unquoted "$var_value" + relink_command="$var=$func_quote_arg_unquoted_result; export $var; $relink_command" + fi + done + # Quote the link command for shipping. + func_quote eval cd "`pwd`" + relink_command="($func_quote_result; $SHELL \"$progpath\" $preserve_args --mode=relink $libtool_args @inst_prefix_dir@)" + func_quote_arg pretty,unquoted "$relink_command" + relink_command=$func_quote_arg_unquoted_result + if test yes = "$hardcode_automatic"; then + relink_command= + fi + + # Only create the output if not a dry run. + $opt_dry_run || { + for installed in no yes; do + if test yes = "$installed"; then + if test -z "$install_libdir"; then + break + fi + output=$output_objdir/${outputname}i + # Replace all uninstalled libtool libraries with the installed ones + newdependency_libs= + for deplib in $dependency_libs; do + case $deplib in + *.la) + func_basename "$deplib" + name=$func_basename_result + func_resolve_sysroot "$deplib" + eval libdir=`$SED -n -e 's/^libdir=\(.*\)$/\1/p' $func_resolve_sysroot_result` + test -z "$libdir" && \ + func_fatal_error "'$deplib' is not a valid libtool archive" + func_append newdependency_libs " ${lt_sysroot:+=}$libdir/$name" + ;; + -L*) + func_stripname -L '' "$deplib" + func_replace_sysroot "$func_stripname_result" + func_append newdependency_libs " -L$func_replace_sysroot_result" + ;; + -R*) + func_stripname -R '' "$deplib" + func_replace_sysroot "$func_stripname_result" + func_append newdependency_libs " -R$func_replace_sysroot_result" + ;; + *) func_append newdependency_libs " $deplib" ;; + esac + done + dependency_libs=$newdependency_libs + newdlfiles= + + for lib in $dlfiles; do + case $lib in + *.la) + func_basename "$lib" + name=$func_basename_result + eval libdir=`$SED -n -e 's/^libdir=\(.*\)$/\1/p' $lib` + test -z "$libdir" && \ + func_fatal_error "'$lib' is not a valid libtool archive" + func_append newdlfiles " ${lt_sysroot:+=}$libdir/$name" + ;; + *) func_append newdlfiles " $lib" ;; + esac + done + dlfiles=$newdlfiles + newdlprefiles= + for lib in $dlprefiles; do + case $lib in + *.la) + # Only pass preopened files to the pseudo-archive (for + # eventual linking with the app. that links it) if we + # didn't already link the preopened objects directly into + # the library: + func_basename "$lib" + name=$func_basename_result + eval libdir=`$SED -n -e 's/^libdir=\(.*\)$/\1/p' $lib` + test -z "$libdir" && \ + func_fatal_error "'$lib' is not a valid libtool archive" + func_append newdlprefiles " ${lt_sysroot:+=}$libdir/$name" + ;; + esac + done + dlprefiles=$newdlprefiles + else + newdlfiles= + for lib in $dlfiles; do + case $lib in + [\\/]* | [A-Za-z]:[\\/]*) abs=$lib ;; + *) abs=`pwd`"/$lib" ;; + esac + func_append newdlfiles " $abs" + done + dlfiles=$newdlfiles + newdlprefiles= + for lib in $dlprefiles; do + case $lib in + [\\/]* | [A-Za-z]:[\\/]*) abs=$lib ;; + *) abs=`pwd`"/$lib" ;; + esac + func_append newdlprefiles " $abs" + done + dlprefiles=$newdlprefiles + fi + $RM $output + # place dlname in correct position for cygwin + # In fact, it would be nice if we could use this code for all target + # systems that can't hard-code library paths into their executables + # and that have no shared library path variable independent of PATH, + # but it turns out we can't easily determine that from inspecting + # libtool variables, so we have to hard-code the OSs to which it + # applies here; at the moment, that means platforms that use the PE + # object format with DLL files. See the long comment at the top of + # tests/bindir.at for full details. + tdlname=$dlname + case $host,$output,$installed,$module,$dlname in + *cygwin*,*lai,yes,no,*.dll | *mingw*,*lai,yes,no,*.dll | *cegcc*,*lai,yes,no,*.dll) + # If a -bindir argument was supplied, place the dll there. + if test -n "$bindir"; then + func_relative_path "$install_libdir" "$bindir" + tdlname=$func_relative_path_result/$dlname + else + # Otherwise fall back on heuristic. + tdlname=../bin/$dlname + fi + ;; + esac + $ECHO > $output "\ +# $outputname - a libtool library file +# Generated by $PROGRAM (GNU $PACKAGE) $VERSION +# +# Please DO NOT delete this file! +# It is necessary for linking the library. + +# The name that we can dlopen(3). +dlname='$tdlname' + +# Names of this library. +library_names='$library_names' + +# The name of the static archive. +old_library='$old_library' + +# Linker flags that cannot go in dependency_libs. +inherited_linker_flags='$new_inherited_linker_flags' + +# Libraries that this one depends upon. +dependency_libs='$dependency_libs' + +# Names of additional weak libraries provided by this library +weak_library_names='$weak_libs' + +# Version information for $libname. +current=$current +age=$age +revision=$revision + +# Is this an already installed library? +installed=$installed + +# Should we warn about portability when linking against -modules? +shouldnotlink=$module + +# Files to dlopen/dlpreopen +dlopen='$dlfiles' +dlpreopen='$dlprefiles' + +# Directory that this library needs to be installed in: +libdir='$install_libdir'" + if test no,yes = "$installed,$need_relink"; then + $ECHO >> $output "\ +relink_command=\"$relink_command\"" + fi + done + } + + # Do a symbolic link so that the libtool archive can be found in + # LD_LIBRARY_PATH before the program is installed. + func_show_eval '( cd "$output_objdir" && $RM "$outputname" && $LN_S "../$outputname" "$outputname" )' 'exit $?' + ;; + esac + exit $EXIT_SUCCESS +} + +if test link = "$opt_mode" || test relink = "$opt_mode"; then + func_mode_link ${1+"$@"} +fi + + +# func_mode_uninstall arg... +func_mode_uninstall () +{ + $debug_cmd + + RM=$nonopt + files= + rmforce=false + exit_status=0 + + # This variable tells wrapper scripts just to set variables rather + # than running their programs. + libtool_install_magic=$magic + + for arg + do + case $arg in + -f) func_append RM " $arg"; rmforce=: ;; + -*) func_append RM " $arg" ;; + *) func_append files " $arg" ;; + esac + done + + test -z "$RM" && \ + func_fatal_help "you must specify an RM program" + + rmdirs= + + for file in $files; do + func_dirname "$file" "" "." + dir=$func_dirname_result + if test . = "$dir"; then + odir=$objdir + else + odir=$dir/$objdir + fi + func_basename "$file" + name=$func_basename_result + test uninstall = "$opt_mode" && odir=$dir + + # Remember odir for removal later, being careful to avoid duplicates + if test clean = "$opt_mode"; then + case " $rmdirs " in + *" $odir "*) ;; + *) func_append rmdirs " $odir" ;; + esac + fi + + # Don't error if the file doesn't exist and rm -f was used. + if { test -L "$file"; } >/dev/null 2>&1 || + { test -h "$file"; } >/dev/null 2>&1 || + test -f "$file"; then + : + elif test -d "$file"; then + exit_status=1 + continue + elif $rmforce; then + continue + fi + + rmfiles=$file + + case $name in + *.la) + # Possibly a libtool archive, so verify it. + if func_lalib_p "$file"; then + func_source $dir/$name + + # Delete the libtool libraries and symlinks. + for n in $library_names; do + func_append rmfiles " $odir/$n" + done + test -n "$old_library" && func_append rmfiles " $odir/$old_library" + + case $opt_mode in + clean) + case " $library_names " in + *" $dlname "*) ;; + *) test -n "$dlname" && func_append rmfiles " $odir/$dlname" ;; + esac + test -n "$libdir" && func_append rmfiles " $odir/$name $odir/${name}i" + ;; + uninstall) + if test -n "$library_names"; then + # Do each command in the postuninstall commands. + func_execute_cmds "$postuninstall_cmds" '$rmforce || exit_status=1' + fi + + if test -n "$old_library"; then + # Do each command in the old_postuninstall commands. + func_execute_cmds "$old_postuninstall_cmds" '$rmforce || exit_status=1' + fi + # FIXME: should reinstall the best remaining shared library. + ;; + esac + fi + ;; + + *.lo) + # Possibly a libtool object, so verify it. + if func_lalib_p "$file"; then + + # Read the .lo file + func_source $dir/$name + + # Add PIC object to the list of files to remove. + if test -n "$pic_object" && test none != "$pic_object"; then + func_append rmfiles " $dir/$pic_object" + fi + + # Add non-PIC object to the list of files to remove. + if test -n "$non_pic_object" && test none != "$non_pic_object"; then + func_append rmfiles " $dir/$non_pic_object" + fi + fi + ;; + + *) + if test clean = "$opt_mode"; then + noexename=$name + case $file in + *.exe) + func_stripname '' '.exe' "$file" + file=$func_stripname_result + func_stripname '' '.exe' "$name" + noexename=$func_stripname_result + # $file with .exe has already been added to rmfiles, + # add $file without .exe + func_append rmfiles " $file" + ;; + esac + # Do a test to see if this is a libtool program. + if func_ltwrapper_p "$file"; then + if func_ltwrapper_executable_p "$file"; then + func_ltwrapper_scriptname "$file" + relink_command= + func_source $func_ltwrapper_scriptname_result + func_append rmfiles " $func_ltwrapper_scriptname_result" + else + relink_command= + func_source $dir/$noexename + fi + + # note $name still contains .exe if it was in $file originally + # as does the version of $file that was added into $rmfiles + func_append rmfiles " $odir/$name $odir/${name}S.$objext" + if test yes = "$fast_install" && test -n "$relink_command"; then + func_append rmfiles " $odir/lt-$name" + fi + if test "X$noexename" != "X$name"; then + func_append rmfiles " $odir/lt-$noexename.c" + fi + fi + fi + ;; + esac + func_show_eval "$RM $rmfiles" 'exit_status=1' + done + + # Try to remove the $objdir's in the directories where we deleted files + for dir in $rmdirs; do + if test -d "$dir"; then + func_show_eval "rmdir $dir >/dev/null 2>&1" + fi + done + + exit $exit_status +} + +if test uninstall = "$opt_mode" || test clean = "$opt_mode"; then + func_mode_uninstall ${1+"$@"} +fi + +test -z "$opt_mode" && { + help=$generic_help + func_fatal_help "you must specify a MODE" +} + +test -z "$exec_cmd" && \ + func_fatal_help "invalid operation mode '$opt_mode'" + +if test -n "$exec_cmd"; then + eval exec "$exec_cmd" + exit $EXIT_FAILURE +fi + +exit $exit_status + + +# The TAGs below are defined such that we never get into a situation +# where we disable both kinds of libraries. Given conflicting +# choices, we go for a static library, that is the most portable, +# since we can't tell whether shared libraries were disabled because +# the user asked for that or because the platform doesn't support +# them. This is particularly important on AIX, because we don't +# support having both static and shared libraries enabled at the same +# time on that platform, so we default to a shared-only configuration. +# If a disable-shared tag is given, we'll fallback to a static-only +# configuration. But we'll never go from static-only to shared-only. + +# ### BEGIN LIBTOOL TAG CONFIG: disable-shared +build_libtool_libs=no +build_old_libs=yes +# ### END LIBTOOL TAG CONFIG: disable-shared + +# ### BEGIN LIBTOOL TAG CONFIG: disable-static +build_old_libs=`case $build_libtool_libs in yes) echo no;; *) echo yes;; esac` +# ### END LIBTOOL TAG CONFIG: disable-static + +# Local Variables: +# mode:shell-script +# sh-indentation:2 +# End: diff --git a/3rdparty/freetype-2.13.2/builds/unix/pkg.m4 b/3rdparty/freetype-2.13.2/builds/unix/pkg.m4 new file mode 100644 index 000000000..260e1fb92 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/pkg.m4 @@ -0,0 +1,199 @@ +# pkg.m4 - Macros to locate and utilise pkg-config. -*- Autoconf -*- +# serial 1 (pkg-config-0.24) +# +# Copyright © 2004 Scott James Remnant . +# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +# +# As a special exception to the GNU General Public License, if you +# distribute this file as part of a program that contains a +# configuration script generated by Autoconf, you may include it under +# the same distribution terms that you use for the rest of that program. + +# PKG_PROG_PKG_CONFIG([MIN-VERSION]) +# ---------------------------------- +AC_DEFUN([PKG_PROG_PKG_CONFIG], +[m4_pattern_forbid([^_?PKG_[A-Z_]+$]) +m4_pattern_allow([^PKG_CONFIG(_(PATH|LIBDIR|SYSROOT_DIR|ALLOW_SYSTEM_(CFLAGS|LIBS)))?$]) +m4_pattern_allow([^PKG_CONFIG_(DISABLE_UNINSTALLED|TOP_BUILD_DIR|DEBUG_SPEW)$]) +AC_ARG_VAR([PKG_CONFIG], [path to pkg-config utility]) +AC_ARG_VAR([PKG_CONFIG_PATH], [directories to add to pkg-config's search path]) +AC_ARG_VAR([PKG_CONFIG_LIBDIR], [path overriding pkg-config's built-in search path]) + +if test "x$ac_cv_env_PKG_CONFIG_set" != "xset"; then + AC_PATH_TOOL([PKG_CONFIG], [pkg-config]) +fi +if test -n "$PKG_CONFIG"; then + _pkg_min_version=m4_default([$1], [0.9.0]) + AC_MSG_CHECKING([pkg-config is at least version $_pkg_min_version]) + if $PKG_CONFIG --atleast-pkgconfig-version $_pkg_min_version; then + AC_MSG_RESULT([yes]) + else + AC_MSG_RESULT([no]) + PKG_CONFIG="" + fi +fi[]dnl +])# PKG_PROG_PKG_CONFIG + +# PKG_CHECK_EXISTS(MODULES, [ACTION-IF-FOUND], [ACTION-IF-NOT-FOUND]) +# +# Check to see whether a particular set of modules exists. Similar +# to PKG_CHECK_MODULES(), but does not set variables or print errors. +# +# Please remember that m4 expands AC_REQUIRE([PKG_PROG_PKG_CONFIG]) +# only at the first occurrence in configure.ac, so if the first place +# it's called might be skipped (such as if it is within an "if", you +# have to call PKG_CHECK_EXISTS manually +# -------------------------------------------------------------- +AC_DEFUN([PKG_CHECK_EXISTS], +[AC_REQUIRE([PKG_PROG_PKG_CONFIG])dnl +if test -n "$PKG_CONFIG" && \ + AC_RUN_LOG([$PKG_CONFIG --exists --print-errors "$1"]); then + m4_default([$2], [:]) +m4_ifvaln([$3], [else + $3])dnl +fi]) + +# _PKG_CONFIG([VARIABLE], [COMMAND], [MODULES]) +# --------------------------------------------- +m4_define([_PKG_CONFIG], +[if test -n "$$1"; then + pkg_cv_[]$1="$$1" + elif test -n "$PKG_CONFIG"; then + PKG_CHECK_EXISTS([$3], + [pkg_cv_[]$1=`$PKG_CONFIG --[]$2 "$3" 2>/dev/null` + test "x$?" != "x0" && pkg_failed=yes ], + [pkg_failed=yes]) + else + pkg_failed=untried +fi[]dnl +])# _PKG_CONFIG + +# _PKG_SHORT_ERRORS_SUPPORTED +# ----------------------------- +AC_DEFUN([_PKG_SHORT_ERRORS_SUPPORTED], +[AC_REQUIRE([PKG_PROG_PKG_CONFIG]) +if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then + _pkg_short_errors_supported=yes +else + _pkg_short_errors_supported=no +fi[]dnl +])# _PKG_SHORT_ERRORS_SUPPORTED + + +# PKG_CHECK_MODULES(VARIABLE-PREFIX, MODULES, [ACTION-IF-FOUND], +# [ACTION-IF-NOT-FOUND]) +# +# +# Note that if there is a possibility the first call to +# PKG_CHECK_MODULES might not happen, you should be sure to include an +# explicit call to PKG_PROG_PKG_CONFIG in your configure.ac +# +# +# -------------------------------------------------------------- +AC_DEFUN([PKG_CHECK_MODULES], +[AC_REQUIRE([PKG_PROG_PKG_CONFIG])dnl +AC_ARG_VAR([$1][_CFLAGS], [C compiler flags for $1, overriding pkg-config])dnl +AC_ARG_VAR([$1][_LIBS], [linker flags for $1, overriding pkg-config])dnl + +pkg_failed=no +AC_MSG_CHECKING([for $1]) + +_PKG_CONFIG([$1][_CFLAGS], [cflags], [$2]) +_PKG_CONFIG([$1][_LIBS], [libs], [$2]) + +m4_define([_PKG_TEXT], [Alternatively, you may set the environment variables $1[]_CFLAGS +and $1[]_LIBS to avoid the need to call pkg-config. +See the pkg-config man page for more details.]) + +if test $pkg_failed = yes; then + AC_MSG_RESULT([no]) + _PKG_SHORT_ERRORS_SUPPORTED + if test $_pkg_short_errors_supported = yes; then + $1[]_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "$2" 2>&1` + else + $1[]_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "$2" 2>&1` + fi + # Put the nasty error message in config.log where it belongs + echo "$$1[]_PKG_ERRORS" >&AS_MESSAGE_LOG_FD + + m4_default([$4], [AC_MSG_ERROR( +[Package requirements ($2) were not met: + +$$1_PKG_ERRORS + +Consider adjusting the PKG_CONFIG_PATH environment variable if you +installed software in a non-standard prefix. + +_PKG_TEXT])[]dnl + ]) +elif test $pkg_failed = untried; then + AC_MSG_RESULT([no]) + m4_default([$4], [AC_MSG_FAILURE( +[The pkg-config script could not be found or is too old. Make sure it +is in your PATH or set the PKG_CONFIG environment variable to the full +path to pkg-config. + +_PKG_TEXT + +To get pkg-config, see .])[]dnl + ]) +else + $1[]_CFLAGS=$pkg_cv_[]$1[]_CFLAGS + $1[]_LIBS=$pkg_cv_[]$1[]_LIBS + AC_MSG_RESULT([yes]) + $3 +fi[]dnl +])# PKG_CHECK_MODULES + + +# PKG_INSTALLDIR(DIRECTORY) +# ------------------------- +# Substitutes the variable pkgconfigdir as the location where a module +# should install pkg-config .pc files. By default the directory is +# $libdir/pkgconfig, but the default can be changed by passing +# DIRECTORY. The user can override through the --with-pkgconfigdir +# parameter. +AC_DEFUN([PKG_INSTALLDIR], +[m4_pushdef([pkg_default], [m4_default([$1], ['${libdir}/pkgconfig'])]) +m4_pushdef([pkg_description], + [pkg-config installation directory @<:@]pkg_default[@:>@]) +AC_ARG_WITH([pkgconfigdir], + [AS_HELP_STRING([--with-pkgconfigdir], pkg_description)],, + [with_pkgconfigdir=]pkg_default) +AC_SUBST([pkgconfigdir], [$with_pkgconfigdir]) +m4_popdef([pkg_default]) +m4_popdef([pkg_description]) +]) dnl PKG_INSTALLDIR + + +# PKG_NOARCH_INSTALLDIR(DIRECTORY) +# ------------------------- +# Substitutes the variable noarch_pkgconfigdir as the location where a +# module should install arch-independent pkg-config .pc files. By +# default the directory is $datadir/pkgconfig, but the default can be +# changed by passing DIRECTORY. The user can override through the +# --with-noarch-pkgconfigdir parameter. +AC_DEFUN([PKG_NOARCH_INSTALLDIR], +[m4_pushdef([pkg_default], [m4_default([$1], ['${datadir}/pkgconfig'])]) +m4_pushdef([pkg_description], + [pkg-config arch-independent installation directory @<:@]pkg_default[@:>@]) +AC_ARG_WITH([noarch-pkgconfigdir], + [AS_HELP_STRING([--with-noarch-pkgconfigdir], pkg_description)],, + [with_noarch_pkgconfigdir=]pkg_default) +AC_SUBST([noarch_pkgconfigdir], [$with_noarch_pkgconfigdir]) +m4_popdef([pkg_default]) +m4_popdef([pkg_description]) +]) dnl PKG_NOARCH_INSTALLDIR diff --git a/3rdparty/freetype-2.13.2/builds/unix/unix-cc.in b/3rdparty/freetype-2.13.2/builds/unix/unix-cc.in new file mode 100644 index 000000000..802016dda --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/unix-cc.in @@ -0,0 +1,130 @@ +# +# FreeType 2 template for Unix-specific compiler definitions +# + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + + +CC := @CC@ +COMPILER_SEP := $(SEP) +FT_LIBTOOL_DIR ?= $(PLATFORM_DIR) + +LIBTOOL := $(FT_LIBTOOL_DIR)/libtool + + +# The object file extension (for standard and static libraries). This can be +# .o, .tco, .obj, etc., depending on the platform. +# +O := lo +SO := o + + +# The executable file extension. Although most Unix platforms use no +# extension, we copy the extension detected by autoconf. Useful for cross +# building on Unix systems for non-Unix systems. +# +E := @EXEEXT@ + + +# The library file extension (for standard and static libraries). This can +# be .a, .lib, etc., depending on the platform. +# +A := la +SA := a + + +# The name of the final library file. Note that the DOS-specific Makefile +# uses a shorter (8.3) name. +# +LIBRARY := lib$(PROJECT) + + +# Path inclusion flag. Some compilers use a different flag than `-I' to +# specify an additional include path. Examples are `/i=' or `-J'. +# +I := -I + + +# C flag used to define a macro before the compilation of a given source +# object. Usually it is `-D' like in `-DDEBUG'. +# +D := -D + + +# The link flag used to specify a given library file on link. Note that +# this is only used to compile the demo programs, not the library itself. +# +L := -l + + +# Target flag. +# +T := -o$(space) + + +# C flags +# +# These should concern: debug output, optimization & warnings. +# +# Use the ANSIFLAGS variable to define the compiler flags used to enforce +# ANSI compliance. +# +# We use our own FreeType configuration files overriding defaults. +# +CPPFLAGS := @CPPFLAGS@ +CFLAGS := -c @XX_CFLAGS@ @CFLAGS@ \ + $DFT_CONFIG_CONFIG_H="" \ + $DFT_CONFIG_MODULES_H="" \ + $DFT_CONFIG_OPTIONS_H="" + +# ANSIFLAGS: Put there the flags used to make your compiler ANSI-compliant. +# +ANSIFLAGS := @XX_ANSIFLAGS@ + +# C compiler to use -- we use libtool! +# +# CC might be set on the command line; we store this value in `CCraw'. +# Consequently, we use the `override' directive to ensure that the +# libtool call is always prepended. +# +CCraw := $(CC) +override CC := $(LIBTOOL) --mode=compile $(CCraw) + +# Resource compiler to use on Cygwin/MinGW, usually windres. +# +RCraw := @RC@ +ifneq ($(RCraw),) + RC := $(LIBTOOL) --tag=RC --mode=compile $(RCraw) +endif + +# Linker flags. +# +LDFLAGS := @LDFLAGS@ + +# export symbols +# +CCraw_build := @CC_BUILD@ # native CC of building system +E_BUILD := @EXEEXT_BUILD@ # extension for executable on building system +EXPORTS_LIST := $(OBJ_DIR)/ftexport.sym +CCexe := $(CCraw_build) # used to compile `apinames' only + + +# Library linking. +# +LINK_LIBRARY = $(LIBTOOL) --mode=link $(CCraw) -o $@ $(OBJECTS_LIST) \ + -rpath $(libdir) -version-info $(version_info) \ + $(LDFLAGS) -no-undefined \ + -export-symbols $(EXPORTS_LIST) + +# For the demo programs. +FT_DEMO_CFLAGS := @FT_DEMO_CFLAGS@ +FT_DEMO_LDFLAGS := @FT_DEMO_LDFLAGS@ + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/unix/unix-def.in b/3rdparty/freetype-2.13.2/builds/unix/unix-def.in new file mode 100644 index 000000000..d50994f3c --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/unix-def.in @@ -0,0 +1,163 @@ +# +# FreeType 2 configuration rules templates for Unix + configure +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + +SHELL := @SHELL@ + +TOP_DIR := $(shell cd $(TOP_DIR); pwd) + +DELETE := rm -f +DELDIR := rm -rf +CAT := cat +SEP := / + +# This is used for `make refdoc' and `make refdoc-venv' +# +PYTHON := @PYTHON@ +BIN := bin + +# this is used for `make distclean' and `make install' +OBJ_BUILD ?= $(PLATFORM_DIR) + +# don't use `:=' here since the path stuff will be included after this file +# +FTSYS_SRC = @FTSYS_SRC@ + +INSTALL := @INSTALL@ +INSTALL_DATA := @INSTALL_DATA@ +INSTALL_PROGRAM := @INSTALL_PROGRAM@ +INSTALL_SCRIPT := @INSTALL_SCRIPT@ +MKINSTALLDIRS := @MKDIR_P@ + +CLEAN += $(OBJ_BUILD)/freetype-config \ + $(OBJ_BUILD)/freetype2.pc + +DISTCLEAN += $(OBJ_BUILD)/config.cache \ + $(OBJ_BUILD)/config.log \ + $(OBJ_BUILD)/config.status \ + $(OBJ_BUILD)/unix-def.mk \ + $(OBJ_BUILD)/unix-cc.mk \ + $(OBJ_BUILD)/ftconfig.h \ + $(OBJ_BUILD)/ftoption.h \ + $(LIBTOOL) \ + $(OBJ_BUILD)/Makefile + + +# Standard installation variables. +# +prefix := @prefix@ +exec_prefix := @exec_prefix@ +libdir := @libdir@ +bindir := @bindir@ +includedir := @includedir@ +datarootdir := @datarootdir@ +datadir := @datadir@ +mandir := @mandir@ + +version_info := @version_info@ + +# Variables needed for `freetype-config' and `freetype.pc'. +# +PKG_CONFIG := @PKG_CONFIG@ +PKGCONFIG_REQUIRES := @PKGCONFIG_REQUIRES@ +PKGCONFIG_REQUIRES_PRIVATE := @PKGCONFIG_REQUIRES_PRIVATE@ +PKGCONFIG_LIBS := @PKGCONFIG_LIBS@ +PKGCONFIG_LIBS_PRIVATE := @PKGCONFIG_LIBS_PRIVATE@ +LIBSSTATIC_CONFIG := @LIBSSTATIC_CONFIG@ +build_libtool_libs := @build_libtool_libs@ +ft_version := @ft_version@ + +# The directory where all library files are placed. +# +# By default, this is the same as $(OBJ_DIR); however, this can be changed +# to suit particular needs. +# +LIB_DIR := $(OBJ_DIR) + +# The BASE_SRC macro lists all source files that should be included in +# src/base/ftbase.c. When configure sets up CFLAGS to build ftmac.c, +# ftmac.c should be added to BASE_SRC. +ftmac_c := @ftmac_c@ + +# The SYSTEM_ZLIB macro is defined if the user wishes to link dynamically +# with its system wide zlib. If SYSTEM_ZLIB is 'yes', the zlib part of the +# ftgzip module is not compiled in. +SYSTEM_ZLIB := @SYSTEM_ZLIB@ + + +# The NO_OUTPUT macro is appended to command lines in order to ignore +# the output of some programs. +# +NO_OUTPUT := 2> /dev/null + + +# To support calls like +# +# configure --includedir='${libdir}'/freetype2/include +# +# we generate `freetype-config' and `freetype.pc' at compile time so that +# those variables are properly expanded. + +$(OBJ_BUILD)/freetype-config: $(TOP_DIR)/builds/unix/freetype-config.in + rm -f $@ $@.tmp + sed -e 's|%LIBSSTATIC_CONFIG%|$(LIBSSTATIC_CONFIG)|' \ + -e 's|%PKG_CONFIG%|$(PKG_CONFIG)|' \ + -e 's|%build_libtool_libs%|$(build_libtool_libs)|' \ + -e 's|%exec_prefix%|$(exec_prefix)|' \ + -e 's|%ft_version%|$(ft_version)|' \ + -e 's|%includedir%|$(includedir)|' \ + -e 's|%libdir%|$(libdir)|' \ + -e 's|%prefix%|$(prefix)|' \ + $< \ + > $@.tmp + chmod +x $@.tmp + chmod go-w $@.tmp + mv $@.tmp $@ + +# To support directory names with spaces (as might easily happen on Windows +# platforms), the right solution would be to surround the pkg-variables in +# `freetype2.pc' with double quotes. However, doing so ironically disables +# the prefix override mechanism especially written for Windows. This is a +# bug in pkg-config version 0.28 and earlier. +# +# For this reason, we escape spaces with backslashes. + +exec_prefix_x := $(subst $(space),\\$(space),$(exec_prefix)) +includedir_x := $(subst $(space),\\$(space),$(includedir)) +libdir_x := $(subst $(space),\\$(space),$(libdir)) +prefix_x := $(subst $(space),\\$(space),$(prefix)) + +$(OBJ_BUILD)/freetype2.pc: $(TOP_DIR)/builds/unix/freetype2.in + rm -f $@ $@.tmp + sed -e 's|%PKGCONFIG_REQUIRES%|$(PKGCONFIG_REQUIRES)|' \ + -e 's|%PKGCONFIG_REQUIRES_PRIVATE%|$(PKGCONFIG_REQUIRES_PRIVATE)|' \ + -e 's|%PKGCONFIG_LIBS%|$(PKGCONFIG_LIBS)|' \ + -e 's|%PKGCONFIG_LIBS_PRIVATE%|$(PKGCONFIG_LIBS_PRIVATE)|' \ + -e 's|%build_libtool_libs%|$(build_libtool_libs)|' \ + -e 's|%exec_prefix%|$(exec_prefix_x)|' \ + -e 's|%ft_version%|$(ft_version)|' \ + -e 's|%includedir%|$(includedir_x)|' \ + -e 's|%libdir%|$(libdir_x)|' \ + -e 's|%prefix%|$(prefix_x)|' \ + $< \ + > $@.tmp + chmod a-w $@.tmp + mv $@.tmp $@ + +# defines whether we should install `freetype-config' or not +INSTALL_FT2_CONFIG = @INSTALL_FT2_CONFIG@ + +all install: $(OBJ_BUILD)/freetype-config \ + $(OBJ_BUILD)/freetype2.pc + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/unix/unix-dev.mk b/3rdparty/freetype-2.13.2/builds/unix/unix-dev.mk new file mode 100644 index 000000000..9dd8ad6ae --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/unix-dev.mk @@ -0,0 +1,26 @@ +# +# FreeType 2 Configuration rules for Unix + GCC +# +# Development version without optimizations & libtool +# and no installation. +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + + +DEVEL_DIR := $(TOP_DIR)/devel + +include $(TOP_DIR)/builds/unix/unixddef.mk +include $(TOP_DIR)/builds/compiler/gcc-dev.mk +include $(TOP_DIR)/builds/link_std.mk + + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/unix/unix-lcc.mk b/3rdparty/freetype-2.13.2/builds/unix/unix-lcc.mk new file mode 100644 index 000000000..ded24f486 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/unix-lcc.mk @@ -0,0 +1,24 @@ +# +# FreeType 2 Configuration rules for Unix + LCC +# +# Development version without optimizations & libtool +# and no installation. +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + + +include $(TOP_DIR)/builds/unix/unixddef.mk +include $(TOP_DIR)/builds/compiler/unix-lcc.mk +include $(TOP_DIR)/builds/link_std.mk + + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/unix/unix.mk b/3rdparty/freetype-2.13.2/builds/unix/unix.mk new file mode 100644 index 000000000..3505175b5 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/unix.mk @@ -0,0 +1,62 @@ +# +# FreeType 2 configuration rules for UNIX platforms +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + +# We need these declarations here since unix-def.mk is a generated file. +PLATFORM_DIR := $(TOP_DIR)/builds/unix +PLATFORM := unix + +have_mk := $(wildcard $(OBJ_DIR)/unix-def.mk) +ifneq ($(have_mk),) + # We are building FreeType 2 not in the src tree. + include $(OBJ_DIR)/unix-def.mk + include $(OBJ_DIR)/unix-cc.mk +else + include $(PLATFORM_DIR)/unix-def.mk + include $(PLATFORM_DIR)/unix-cc.mk +endif + +ifdef BUILD_PROJECT + + .PHONY: clean_project distclean_project + + # Now include the main sub-makefile. It contains all the rules used to + # build the library with the previous variables defined. + # + include $(TOP_DIR)/builds/$(PROJECT).mk + + + # The cleanup targets. + # + clean_project: clean_project_unix + distclean_project: distclean_project_unix + + + # This final rule is used to link all object files into a single library. + # It is part of the system-specific sub-Makefile because not all + # librarians accept a simple syntax like + # + # librarian library_file {list of object files} + # + $(PROJECT_LIBRARY): $(OBJECTS_LIST) + ifdef CLEAN_LIBRARY + -$(CLEAN_LIBRARY) $(NO_OUTPUT) + endif + $(LINK_LIBRARY) + + include $(TOP_DIR)/builds/unix/install.mk + +endif + + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/unix/unixddef.mk b/3rdparty/freetype-2.13.2/builds/unix/unixddef.mk new file mode 100644 index 000000000..71973471d --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/unix/unixddef.mk @@ -0,0 +1,46 @@ +# +# FreeType 2 configuration rules templates for +# development under Unix with no configure script (gcc only) +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + + +TOP_DIR := $(shell cd $(TOP_DIR); pwd) +OBJ_DIR := $(shell cd $(OBJ_DIR); pwd) + +PLATFORM := unix + +DELETE := rm -f +CAT := cat +SEP := / + +# This is used for `make refdoc' and `make refdoc-venv' +# +BIN := bin + + +# library file name +# +LIBRARY := lib$(PROJECT) + + +# The directory where all library files are placed. +# +# By default, this is the same as $(OBJ_DIR); however, this can be changed +# to suit particular needs. +# +LIB_DIR := $(OBJ_DIR) + + +NO_OUTPUT := 2> /dev/null + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/windows/detect.mk b/3rdparty/freetype-2.13.2/builds/windows/detect.mk new file mode 100644 index 000000000..d7908bee5 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/detect.mk @@ -0,0 +1,202 @@ +# +# FreeType 2 configuration file to detect a Win32 host platform. +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + + +.PHONY: setup + + +ifeq ($(PLATFORM),ansi) + + # Detecting Windows NT is easy, as the OS variable must be defined and + # contains `Windows_NT'. This also works with Windows 2000 and XP. + # + ifeq ($(OS),Windows_NT) + + PLATFORM := windows + + else + + # Detecting Windows 9X + + # We used to run the `ver' command to see if its output contains the + # word `Windows'. If this is true, we are running Windows 95 or later: + # + # ifdef COMSPEC + # # First, check if we have the COMSPEC environment variable, which + # # indicates we can use COMMAND.COM's internal commands + # is_windows := $(findstring Windows,$(strip $(shell ver))) + # endif + # + # Unfortunately, this also detects the case when one is running + # DOS 7.x (the MS-DOS version that lies below Windows) without actually + # launching the GUI. + # + # A better test is to check whether there are both the environment + # variables `winbootdir' and `windir'. The first indicates an + # underlying DOS 7.x, while the second is set only if windows is + # available. + # + # Note that on Windows NT, such an environment variable will not be seen + # from DOS-based tools like DJGPP's make; this is not actually a problem + # since NT is detected independently above. But do not try to be clever! + # + ifdef winbootdir + ifdef windir + + PLATFORM := windows + + endif + endif + + endif # test NT + +endif # test PLATFORM ansi + +ifeq ($(PLATFORM),windows) + + DELETE := del + CAT := type + SEP := $(BACKSLASH) + + # Setting COPY is a bit trickier. Plain COPY on NT will not work + # correctly, because it will uppercase 8.3 filenames, creating a + # `CONFIG.MK' file which isn't found later on by `make'. + # Since we do not want that, we need to force execution of CMD.EXE. + # Unfortunately, CMD.EXE is not available on Windows 9X. + # So we need to hack. + # + # Kudos to Eli Zaretskii (DJGPP guru) that helped debug it. + # Details are available in threads of the FreeType mailing list + # (2004-11-11), and then in the devel mailing list (2004-11-20 to -23). + # + ifeq ($(OS),Windows_NT) + COPY := >nul cmd.exe /c copy + else + COPY := >nul copy + endif # test NT + + + # gcc Makefile by default + CONFIG_FILE := w32-gcc.mk + ifeq ($(firstword $(CC)),cc) + CC := gcc + endif + + ifneq ($(findstring list,$(MAKECMDGOALS)),) # test for the "list" target + dump_target_list: + $(info ) + $(info $(PROJECT_TITLE) build system -- supported compilers) + $(info ) + $(info Several command-line compilers are supported on Win32:) + $(info ) + $(info $(empty) make setup gcc (with Mingw)) + $(info $(empty) make setup visualc Microsoft Visual C++) + $(info $(empty) make setup bcc32 Borland C/C++) + $(info $(empty) make setup lcc Win32-LCC) + $(info $(empty) make setup intelc Intel C/C++) + $(info ) + + setup: dump_target_list + .PHONY: dump_target_list list + else + setup: std_setup + endif + + # additionally, we provide hooks for various other compilers + # + ifneq ($(findstring visualc,$(MAKECMDGOALS)),) # Visual C/C++ + CONFIG_FILE := w32-vcc.mk + CC := cl + + .PHONY: visualc + visualc: setup + @cd . + endif + + ifneq ($(findstring intelc,$(MAKECMDGOALS)),) # Intel C/C++ + CONFIG_FILE := w32-intl.mk + CC := cl + + .PHONY: intelc + visualc: setup + @cd . + endif + + ifneq ($(findstring watcom,$(MAKECMDGOALS)),) # Watcom C/C++ + CONFIG_FILE := w32-wat.mk + CC := wcc386 + + .PHONY: watcom + watcom: setup + @cd . + endif + + ifneq ($(findstring visualage,$(MAKECMDGOALS)),) # Visual Age C++ + CONFIG_FILE := w32-icc.mk + CC := icc + + .PHONY: visualage + visualage: setup + @cd . + endif + + ifneq ($(findstring lcc,$(MAKECMDGOALS)),) # LCC-Win32 + CONFIG_FILE := w32-lcc.mk + CC := lcc + + .PHONY: lcc + lcc: setup + @cd . + endif + + ifneq ($(findstring mingw32,$(MAKECMDGOALS)),) # mingw32 + CONFIG_FILE := w32-mingw32.mk + CC := gcc + + .PHONY: mingw32 + mingw32: setup + @cd . + endif + + ifneq ($(findstring bcc32,$(MAKECMDGOALS)),) # Borland C++ + CONFIG_FILE := w32-bcc.mk + CC := bcc32 + + .PHONY: bcc32 + bcc32: setup + @cd . + endif + + ifneq ($(findstring devel-bcc,$(MAKECMDGOALS)),) # development target + CONFIG_FILE := w32-bccd.mk + CC := bcc32 + + .PHONY: devel-bcc + devel-bcc: setup + @cd . + endif + + ifneq ($(findstring devel-gcc,$(MAKECMDGOALS)),) # development target + CONFIG_FILE := w32-dev.mk + CC := gcc + + .PHONY: devel-gcc + devel-gcc: setup + @cd . + endif + +endif # test PLATFORM windows + + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/windows/ftdebug.c b/3rdparty/freetype-2.13.2/builds/windows/ftdebug.c new file mode 100644 index 000000000..360f8c7e3 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/ftdebug.c @@ -0,0 +1,698 @@ +/**************************************************************************** + * + * ftdebug.c + * + * Debugging and logging component for Win32 (body). + * + * Copyright (C) 1996-2023 by + * David Turner, Robert Wilhelm, and Werner Lemberg. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + + /************************************************************************** + * + * This component contains various macros and functions used to ease the + * debugging of the FreeType engine. Its main purpose is in assertion + * checking, tracing, and error detection. + * + * There are now three debugging modes: + * + * - trace mode + * + * Error and trace messages are sent to the log file (which can be the + * standard error output). + * + * - error mode + * + * Only error messages are generated. + * + * - release mode: + * + * No error message is sent or generated. The code is free from any + * debugging parts. + * + */ + + +#include +#include +#include +#include + + +#ifdef FT_DEBUG_LOGGING + + /************************************************************************** + * + * Variables used to control logging. + * + * 1. `ft_default_trace_level` stores the value of trace levels, which are + * provided to FreeType using the `FT2_DEBUG` environment variable. + * + * 2. `ft_fileptr` stores the `FILE*` handle. + * + * 3. `ft_component` is a string that holds the name of `FT_COMPONENT`. + * + * 4. The flag `ft_component_flag` prints the name of `FT_COMPONENT` along + * with the actual log message if set to true. + * + * 5. The flag `ft_timestamp_flag` prints time along with the actual log + * message if set to ture. + * + * 6. `ft_have_newline_char` is used to differentiate between a log + * message with and without a trailing newline character. + * + * 7. `ft_custom_trace_level` stores the custom trace level value, which + * is provided by the user at run-time. + * + * We use `static` to avoid 'unused variable' warnings. + * + */ + static const char* ft_default_trace_level = NULL; + static FILE* ft_fileptr = NULL; + static const char* ft_component = NULL; + static FT_Bool ft_component_flag = FALSE; + static FT_Bool ft_timestamp_flag = FALSE; + static FT_Bool ft_have_newline_char = TRUE; + static const char* ft_custom_trace_level = NULL; + + /* declared in ftdebug.h */ + + dlg_handler ft_default_log_handler = NULL; + FT_Custom_Log_Handler custom_output_handler = NULL; + +#endif /* FT_DEBUG_LOGGING */ + + +#ifdef FT_DEBUG_LEVEL_ERROR + +#define WIN32_LEAN_AND_MEAN +#include + + +#ifdef _WIN32_WCE + + FT_LOACAL_DEF( void ) + OutputDebugStringA( LPCSTR lpOutputString ) + { + int len; + LPWSTR lpOutputStringW; + + + /* allocate memory space for converted string */ + len = MultiByteToWideChar( CP_ACP, MB_ERR_INVALID_CHARS, + lpOutputString, -1, NULL, 0 ); + + lpOutputStringW = (LPWSTR)_alloca( len * sizeof ( WCHAR ) ); + + if ( !len || !lpOutputStringW ) + return; + + /* now it is safe to do the translation */ + MultiByteToWideChar( CP_ACP, MB_ERR_INVALID_CHARS, + lpOutputString, -1, lpOutputStringW, len ); + + OutputDebugStringW( lpOutputStringW ); + } + +#endif /* _WIN32_WCE */ + + + /* documentation is in ftdebug.h */ + + FT_BASE_DEF( void ) + FT_Message( const char* fmt, + ... ) + { + va_list ap; + + + va_start( ap, fmt ); + vfprintf( stderr, fmt, ap ); +#if ( defined( _WIN32_WINNT ) && _WIN32_WINNT >= 0x0400 ) || \ + ( defined( _WIN32_WCE ) && _WIN32_WCE >= 0x0600 ) + if ( IsDebuggerPresent() ) + { + static char buf[1024]; + + + vsnprintf( buf, sizeof buf, fmt, ap ); + OutputDebugStringA( buf ); + } +#endif + va_end( ap ); + } + + + /* documentation is in ftdebug.h */ + + FT_BASE_DEF( void ) + FT_Panic( const char* fmt, + ... ) + { + va_list ap; + + + va_start( ap, fmt ); + vfprintf( stderr, fmt, ap ); +#if ( defined( _WIN32_WINNT ) && _WIN32_WINNT >= 0x0400 ) || \ + ( defined( _WIN32_WCE ) && _WIN32_WCE >= 0x0600 ) + if ( IsDebuggerPresent() ) + { + static char buf[1024]; + + + vsnprintf( buf, sizeof buf, fmt, ap ); + OutputDebugStringA( buf ); + } +#endif + va_end( ap ); + + exit( EXIT_FAILURE ); + } + + + /* documentation is in ftdebug.h */ + + FT_BASE_DEF( int ) + FT_Throw( FT_Error error, + int line, + const char* file ) + { +#if 0 + /* activating the code in this block makes FreeType very chatty */ + fprintf( stderr, + "%s:%d: error 0x%02x: %s\n", + file, + line, + error, + FT_Error_String( error ) ); +#else + FT_UNUSED( error ); + FT_UNUSED( line ); + FT_UNUSED( file ); +#endif + + return 0; + } + +#endif /* FT_DEBUG_LEVEL_ERROR */ + + +#ifdef FT_DEBUG_LEVEL_TRACE + + /* array of trace levels, initialized to 0; */ + /* this gets adjusted at run-time */ + static int ft_trace_levels_enabled[trace_count]; + + /* array of trace levels, always initialized to 0 */ + static int ft_trace_levels_disabled[trace_count]; + + /* a pointer to either `ft_trace_levels_enabled' */ + /* or `ft_trace_levels_disabled' */ + int* ft_trace_levels; + + /* define array of trace toggle names */ +#define FT_TRACE_DEF( x ) #x , + + static const char* ft_trace_toggles[trace_count + 1] = + { +#include + NULL + }; + +#undef FT_TRACE_DEF + + + /* documentation is in ftdebug.h */ + + FT_BASE_DEF( FT_Int ) + FT_Trace_Get_Count( void ) + { + return trace_count; + } + + + /* documentation is in ftdebug.h */ + + FT_BASE_DEF( const char * ) + FT_Trace_Get_Name( FT_Int idx ) + { + int max = FT_Trace_Get_Count(); + + + if ( idx < max ) + return ft_trace_toggles[idx]; + else + return NULL; + } + + + /* documentation is in ftdebug.h */ + + FT_BASE_DEF( void ) + FT_Trace_Disable( void ) + { + ft_trace_levels = ft_trace_levels_disabled; + } + + + /* documentation is in ftdebug.h */ + + FT_BASE_DEF( void ) + FT_Trace_Enable( void ) + { + ft_trace_levels = ft_trace_levels_enabled; + } + + + /************************************************************************** + * + * Initialize the tracing sub-system. This is done by retrieving the + * value of the `FT2_DEBUG' environment variable. It must be a list of + * toggles, separated by spaces, `;', or `,'. Example: + * + * export FT2_DEBUG="any:3 memory:7 stream:5" + * + * This requests that all levels be set to 3, except the trace level for + * the memory and stream components which are set to 7 and 5, + * respectively. + * + * See the file `include/freetype/internal/fttrace.h' for details of + * the available toggle names. + * + * The level must be between 0 and 7; 0 means quiet (except for serious + * runtime errors), and 7 means _very_ verbose. + */ + FT_BASE_DEF( void ) + ft_debug_init( void ) + { + const char* ft2_debug = NULL; + + +#ifdef FT_DEBUG_LOGGING + if ( ft_custom_trace_level != NULL ) + ft2_debug = ft_custom_trace_level; + else + ft2_debug = ft_default_trace_level; +#else + ft2_debug = ft_getenv( "FT2_DEBUG" ); +#endif + + if ( ft2_debug ) + { + const char* p = ft2_debug; + const char* q; + + + for ( ; *p; p++ ) + { + /* skip leading whitespace and separators */ + if ( *p == ' ' || *p == '\t' || *p == ',' || *p == ';' || *p == '=' ) + continue; + +#ifdef FT_DEBUG_LOGGING + + /* check extra arguments for logging */ + if ( *p == '-' ) + { + const char* r = ++p; + + + if ( *r == 'v' ) + { + const char* s = ++r; + + + ft_component_flag = TRUE; + + if ( *s == 't' ) + { + ft_timestamp_flag = TRUE; + p++; + } + + p++; + } + + else if ( *r == 't' ) + { + const char* s = ++r; + + + ft_timestamp_flag = TRUE; + + if ( *s == 'v' ) + { + ft_component_flag = TRUE; + p++; + } + + p++; + } + } + +#endif /* FT_DEBUG_LOGGING */ + + /* read toggle name, followed by ':' */ + q = p; + while ( *p && *p != ':' ) + p++; + + if ( !*p ) + break; + + if ( *p == ':' && p > q ) + { + FT_Int n, i, len = (FT_Int)( p - q ); + FT_Int level = -1, found = -1; + + + for ( n = 0; n < trace_count; n++ ) + { + const char* toggle = ft_trace_toggles[n]; + + + for ( i = 0; i < len; i++ ) + { + if ( toggle[i] != q[i] ) + break; + } + + if ( i == len && toggle[i] == 0 ) + { + found = n; + break; + } + } + + /* read level */ + p++; + if ( *p ) + { + level = *p - '0'; + if ( level < 0 || level > 7 ) + level = -1; + } + + if ( found >= 0 && level >= 0 ) + { + if ( found == trace_any ) + { + /* special case for `any' */ + for ( n = 0; n < trace_count; n++ ) + ft_trace_levels_enabled[n] = level; + } + else + ft_trace_levels_enabled[found] = level; + } + } + } + } + + ft_trace_levels = ft_trace_levels_enabled; + } + + +#else /* !FT_DEBUG_LEVEL_TRACE */ + + + FT_BASE_DEF( void ) + ft_debug_init( void ) + { + /* nothing */ + } + + + FT_BASE_DEF( FT_Int ) + FT_Trace_Get_Count( void ) + { + return 0; + } + + + FT_BASE_DEF( const char * ) + FT_Trace_Get_Name( FT_Int idx ) + { + FT_UNUSED( idx ); + + return NULL; + } + + + FT_BASE_DEF( void ) + FT_Trace_Disable( void ) + { + /* nothing */ + } + + + /* documentation is in ftdebug.h */ + + FT_BASE_DEF( void ) + FT_Trace_Enable( void ) + { + /* nothing */ + } + +#endif /* !FT_DEBUG_LEVEL_TRACE */ + + +#ifdef FT_DEBUG_LOGGING + + /************************************************************************** + * + * Initialize and de-initialize 'dlg' library. + * + */ + + FT_BASE_DEF( void ) + ft_logging_init( void ) + { + ft_default_log_handler = ft_log_handler; + ft_default_trace_level = ft_getenv( "FT2_DEBUG" ); + + if ( ft_getenv( "FT_LOGGING_FILE" ) ) + ft_fileptr = ft_fopen( ft_getenv( "FT_LOGGING_FILE" ), "w" ); + else + ft_fileptr = stderr; + + ft_debug_init(); + + /* Set the default output handler for 'dlg'. */ + dlg_set_handler( ft_default_log_handler, NULL ); + } + + + FT_BASE_DEF( void ) + ft_logging_deinit( void ) + { + if ( ft_fileptr != stderr ) + ft_fclose( ft_fileptr ); + } + + + /************************************************************************** + * + * An output log handler for FreeType. + * + */ + FT_BASE_DEF( void ) + ft_log_handler( const struct dlg_origin* origin, + const char* string, + void* data ) + { + char features_buf[128]; + char* bufp = features_buf; + + FT_UNUSED( data ); + + + if ( ft_have_newline_char ) + { + const char* features = NULL; + size_t features_length = 0; + + +#define FEATURES_TIMESTAMP "[%h:%m] " +#define FEATURES_COMPONENT "[%t] " +#define FEATURES_TIMESTAMP_COMPONENT "[%h:%m %t] " + + if ( ft_timestamp_flag && ft_component_flag ) + { + features = FEATURES_TIMESTAMP_COMPONENT; + features_length = sizeof ( FEATURES_TIMESTAMP_COMPONENT ); + } + else if ( ft_timestamp_flag ) + { + features = FEATURES_TIMESTAMP; + features_length = sizeof ( FEATURES_TIMESTAMP ); + } + else if ( ft_component_flag ) + { + features = FEATURES_COMPONENT; + features_length = sizeof ( FEATURES_COMPONENT ); + } + + if ( ft_component_flag || ft_timestamp_flag ) + { + ft_strncpy( features_buf, features, features_length ); + bufp += features_length - 1; + } + + if ( ft_component_flag ) + { + size_t tag_length = ft_strlen( *origin->tags ); + size_t i; + + + /* To vertically align tracing messages we compensate the */ + /* different FT_COMPONENT string lengths by inserting an */ + /* appropriate amount of space characters. */ + for ( i = 0; + i < FT_MAX_TRACE_LEVEL_LENGTH - tag_length; + i++ ) + *bufp++ = ' '; + } + } + + /* Finally add the format string for the tracing message. */ + *bufp++ = '%'; + *bufp++ = 'c'; + *bufp = '\0'; + + dlg_generic_outputf_stream( ft_fileptr, + (const char*)features_buf, + origin, + string, + dlg_default_output_styles, + true ); + + if ( ft_strrchr( string, '\n' ) ) + ft_have_newline_char = TRUE; + else + ft_have_newline_char = FALSE; + } + + + /* documentation is in ftdebug.h */ + FT_BASE_DEF( void ) + ft_add_tag( const char* tag ) + { + ft_component = tag; + + dlg_add_tag( tag, NULL ); + } + + + /* documentation is in ftdebug.h */ + FT_BASE_DEF( void ) + ft_remove_tag( const char* tag ) + { + dlg_remove_tag( tag, NULL ); + } + + + /* documentation is in ftlogging.h */ + + FT_EXPORT_DEF( void ) + FT_Trace_Set_Level( const char* level ) + { + ft_component_flag = FALSE; + ft_timestamp_flag = FALSE; + ft_custom_trace_level = level; + + ft_debug_init(); + } + + + /* documentation is in ftlogging.h */ + + FT_EXPORT_DEF( void ) + FT_Trace_Set_Default_Level( void ) + { + ft_component_flag = FALSE; + ft_timestamp_flag = FALSE; + ft_custom_trace_level = NULL; + + ft_debug_init(); + } + + + /************************************************************************** + * + * Functions to handle a custom log handler. + * + */ + + /* documentation is in ftlogging.h */ + + FT_EXPORT_DEF( void ) + FT_Set_Log_Handler( FT_Custom_Log_Handler handler ) + { + custom_output_handler = handler; + } + + + /* documentation is in ftlogging.h */ + + FT_EXPORT_DEF( void ) + FT_Set_Default_Log_Handler( void ) + { + custom_output_handler = NULL; + } + + + /* documentation is in ftdebug.h */ + FT_BASE_DEF( void ) + FT_Logging_Callback( const char* fmt, + ... ) + { + va_list ap; + + + va_start( ap, fmt ); + custom_output_handler( ft_component, fmt, ap ); + va_end( ap ); + } + +#else /* !FT_DEBUG_LOGGING */ + + FT_EXPORT_DEF( void ) + FT_Trace_Set_Level( const char* level ) + { + FT_UNUSED( level ); + } + + + FT_EXPORT_DEF( void ) + FT_Trace_Set_Default_Level( void ) + { + /* nothing */ + } + + + FT_EXPORT_DEF( void ) + FT_Set_Log_Handler( FT_Custom_Log_Handler handler ) + { + FT_UNUSED( handler ); + } + + + FT_EXPORT_DEF( void ) + FT_Set_Default_Log_Handler( void ) + { + /* nothing */ + } + +#endif /* !FT_DEBUG_LOGGING */ + + +/* END */ diff --git a/3rdparty/freetype-2.13.2/builds/windows/ftsystem.c b/3rdparty/freetype-2.13.2/builds/windows/ftsystem.c new file mode 100644 index 000000000..418d7995e --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/ftsystem.c @@ -0,0 +1,499 @@ +/**************************************************************************** + * + * ftsystem.c + * + * Windows-specific FreeType low-level system interface (body). + * + * Copyright (C) 2021-2023 by + * David Turner, Robert Wilhelm, and Werner Lemberg. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + +#include + /* we use our special ftconfig.h file, not the standard one */ +#include FT_CONFIG_CONFIG_H +#include +#include +#include +#include +#include + + /* memory mapping and allocation includes and definitions */ +#define WIN32_LEAN_AND_MEAN +#include + + + /************************************************************************** + * + * MEMORY MANAGEMENT INTERFACE + * + */ + + + /************************************************************************** + * + * It is not necessary to do any error checking for the + * allocation-related functions. This will be done by the higher level + * routines like ft_mem_alloc() or ft_mem_realloc(). + * + */ + + + /************************************************************************** + * + * @Function: + * ft_alloc + * + * @Description: + * The memory allocation function. + * + * @Input: + * memory :: + * A pointer to the memory object. + * + * size :: + * The requested size in bytes. + * + * @Return: + * The address of newly allocated block. + */ + FT_CALLBACK_DEF( void* ) + ft_alloc( FT_Memory memory, + long size ) + { + return HeapAlloc( memory->user, 0, size ); + } + + + /************************************************************************** + * + * @Function: + * ft_realloc + * + * @Description: + * The memory reallocation function. + * + * @Input: + * memory :: + * A pointer to the memory object. + * + * cur_size :: + * The current size of the allocated memory block. + * + * new_size :: + * The newly requested size in bytes. + * + * block :: + * The current address of the block in memory. + * + * @Return: + * The address of the reallocated memory block. + */ + FT_CALLBACK_DEF( void* ) + ft_realloc( FT_Memory memory, + long cur_size, + long new_size, + void* block ) + { + FT_UNUSED( cur_size ); + + return HeapReAlloc( memory->user, 0, block, new_size ); + } + + + /************************************************************************** + * + * @Function: + * ft_free + * + * @Description: + * The memory release function. + * + * @Input: + * memory :: + * A pointer to the memory object. + * + * block :: + * The address of block in memory to be freed. + */ + FT_CALLBACK_DEF( void ) + ft_free( FT_Memory memory, + void* block ) + { + HeapFree( memory->user, 0, block ); + } + + + /************************************************************************** + * + * RESOURCE MANAGEMENT INTERFACE + * + */ + + + /************************************************************************** + * + * The macro FT_COMPONENT is used in trace mode. It is an implicit + * parameter of the FT_TRACE() and FT_ERROR() macros, used to print/log + * messages during execution. + */ +#undef FT_COMPONENT +#define FT_COMPONENT io + + /* We use the macro STREAM_FILE for convenience to extract the */ + /* system-specific stream handle from a given FreeType stream object */ +#define STREAM_FILE( stream ) ( (FILE*)stream->descriptor.pointer ) + + + /************************************************************************** + * + * @Function: + * ft_close_stream_by_munmap + * + * @Description: + * The function to close a stream which is opened by mmap. + * + * @Input: + * stream :: A pointer to the stream object. + */ + FT_CALLBACK_DEF( void ) + ft_close_stream_by_munmap( FT_Stream stream ) + { + UnmapViewOfFile( (LPCVOID)stream->descriptor.pointer ); + + stream->descriptor.pointer = NULL; + stream->size = 0; + stream->base = NULL; + } + + + /************************************************************************** + * + * @Function: + * ft_close_stream_by_free + * + * @Description: + * The function to close a stream which is created by ft_alloc. + * + * @Input: + * stream :: A pointer to the stream object. + */ + FT_CALLBACK_DEF( void ) + ft_close_stream_by_free( FT_Stream stream ) + { + ft_free( stream->memory, stream->descriptor.pointer ); + + stream->descriptor.pointer = NULL; + stream->size = 0; + stream->base = NULL; + } + + + /* non-desktop Universal Windows Platform */ +#if defined( WINAPI_FAMILY ) && WINAPI_FAMILY != WINAPI_FAMILY_DESKTOP_APP + +#define PACK_DWORD64( hi, lo ) ( ( (DWORD64)(hi) << 32 ) | (DWORD)(lo) ) + +#define CreateFileMapping( a, b, c, d, e, f ) \ + CreateFileMappingFromApp( a, b, c, PACK_DWORD64( d, e ), f ) +#define MapViewOfFile( a, b, c, d, e ) \ + MapViewOfFileFromApp( a, b, PACK_DWORD64( c, d ), e ) + + FT_LOCAL_DEF( HANDLE ) + CreateFileA( LPCSTR lpFileName, + DWORD dwDesiredAccess, + DWORD dwShareMode, + LPSECURITY_ATTRIBUTES lpSecurityAttributes, + DWORD dwCreationDisposition, + DWORD dwFlagsAndAttributes, + HANDLE hTemplateFile ) + { + int len; + LPWSTR lpFileNameW; + + CREATEFILE2_EXTENDED_PARAMETERS createExParams = { + sizeof ( CREATEFILE2_EXTENDED_PARAMETERS ), + dwFlagsAndAttributes & 0x0000FFFF, + dwFlagsAndAttributes & 0xFFF00000, + dwFlagsAndAttributes & 0x000F0000, + lpSecurityAttributes, + hTemplateFile }; + + + /* allocate memory space for converted path name */ + len = MultiByteToWideChar( CP_ACP, MB_ERR_INVALID_CHARS, + lpFileName, -1, NULL, 0 ); + + lpFileNameW = (LPWSTR)_alloca( len * sizeof ( WCHAR ) ); + + if ( !len || !lpFileNameW ) + { + FT_ERROR(( "FT_Stream_Open: cannot convert file name to LPWSTR\n" )); + return INVALID_HANDLE_VALUE; + } + + /* now it is safe to do the translation */ + MultiByteToWideChar( CP_ACP, MB_ERR_INVALID_CHARS, + lpFileName, -1, lpFileNameW, len ); + + /* open the file */ + return CreateFile2( lpFileNameW, dwDesiredAccess, dwShareMode, + dwCreationDisposition, &createExParams ); + } + +#endif + + +#if defined( _WIN32_WCE ) + + /* malloc.h provides implementation of alloca()/_alloca() */ + #include + + FT_LOCAL_DEF( HANDLE ) + CreateFileA( LPCSTR lpFileName, + DWORD dwDesiredAccess, + DWORD dwShareMode, + LPSECURITY_ATTRIBUTES lpSecurityAttributes, + DWORD dwCreationDisposition, + DWORD dwFlagsAndAttributes, + HANDLE hTemplateFile ) + { + int len; + LPWSTR lpFileNameW; + + + /* allocate memory space for converted path name */ + len = MultiByteToWideChar( CP_ACP, MB_ERR_INVALID_CHARS, + lpFileName, -1, NULL, 0 ); + + lpFileNameW = (LPWSTR)_alloca( len * sizeof ( WCHAR ) ); + + if ( !len || !lpFileNameW ) + { + FT_ERROR(( "FT_Stream_Open: cannot convert file name to LPWSTR\n" )); + return INVALID_HANDLE_VALUE; + } + + /* now it is safe to do the translation */ + MultiByteToWideChar( CP_ACP, MB_ERR_INVALID_CHARS, + lpFileName, -1, lpFileNameW, len ); + + /* open the file */ + return CreateFileW( lpFileNameW, dwDesiredAccess, dwShareMode, + lpSecurityAttributes, dwCreationDisposition, + dwFlagsAndAttributes, hTemplateFile ); + } + +#endif + + +#if defined( _WIN32_WCE ) || defined ( _WIN32_WINDOWS ) || \ + !defined( _WIN32_WINNT ) || _WIN32_WINNT <= 0x0400 + + FT_LOCAL_DEF( BOOL ) + GetFileSizeEx( HANDLE hFile, + PLARGE_INTEGER lpFileSize ) + { + lpFileSize->u.LowPart = GetFileSize( hFile, + (DWORD *)&lpFileSize->u.HighPart ); + + if ( lpFileSize->u.LowPart == INVALID_FILE_SIZE && + GetLastError() != NO_ERROR ) + return FALSE; + else + return TRUE; + } + +#endif + + + /* documentation is in ftobjs.h */ + + FT_BASE_DEF( FT_Error ) + FT_Stream_Open( FT_Stream stream, + const char* filepathname ) + { + HANDLE file; + HANDLE fm; + LARGE_INTEGER size; + + + if ( !stream ) + return FT_THROW( Invalid_Stream_Handle ); + + /* open the file */ + file = CreateFileA( (LPCSTR)filepathname, GENERIC_READ, FILE_SHARE_READ, + NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, 0 ); + if ( file == INVALID_HANDLE_VALUE ) + { + FT_ERROR(( "FT_Stream_Open:" )); + FT_ERROR(( " could not open `%s'\n", filepathname )); + return FT_THROW( Cannot_Open_Resource ); + } + + if ( GetFileSizeEx( file, &size ) == FALSE ) + { + FT_ERROR(( "FT_Stream_Open:" )); + FT_ERROR(( " could not retrieve size of file `%s'\n", filepathname )); + goto Fail_Open; + } + + /* `stream->size' is typedef'd to unsigned long (in `ftsystem.h'); */ + /* So avoid overflow caused by fonts in huge files larger than */ + /* 2GB, do a test. */ + if ( size.QuadPart > LONG_MAX ) + { + FT_ERROR(( "FT_Stream_Open: file is too big\n" )); + goto Fail_Open; + } + else if ( size.QuadPart == 0 ) + { + FT_ERROR(( "FT_Stream_Open: zero-length file\n" )); + goto Fail_Open; + } + + fm = CreateFileMapping( file, NULL, PAGE_READONLY, 0, 0, NULL ); + if ( fm == NULL ) + { + FT_ERROR(( "FT_Stream_Open: can not map file\n" )); + goto Fail_Open; + } + + /* Store only the low part of this 64 bits integer because long is */ + /* a 32 bits type. Anyway, a check has been done above to forbid */ + /* a size greater than LONG_MAX */ + stream->size = size.LowPart; + stream->pos = 0; + stream->base = (unsigned char *) + MapViewOfFile( fm, FILE_MAP_READ, 0, 0, 0 ); + + CloseHandle( fm ); + + if ( stream->base != NULL ) + stream->close = ft_close_stream_by_munmap; + else + { + DWORD total_read_count; + + + FT_ERROR(( "FT_Stream_Open:" )); + FT_ERROR(( " could not `mmap' file `%s'\n", filepathname )); + + stream->base = (unsigned char*)ft_alloc( stream->memory, stream->size ); + + if ( !stream->base ) + { + FT_ERROR(( "FT_Stream_Open:" )); + FT_ERROR(( " could not `alloc' memory\n" )); + goto Fail_Open; + } + + total_read_count = 0; + do + { + DWORD read_count; + + + if ( ReadFile( file, + stream->base + total_read_count, + stream->size - total_read_count, + &read_count, NULL ) == FALSE ) + { + FT_ERROR(( "FT_Stream_Open:" )); + FT_ERROR(( " error while `read'ing file `%s'\n", filepathname )); + goto Fail_Read; + } + + total_read_count += read_count; + + } while ( total_read_count != stream->size ); + + stream->close = ft_close_stream_by_free; + } + + CloseHandle( file ); + + stream->descriptor.pointer = stream->base; + stream->pathname.pointer = (char*)filepathname; + + stream->read = NULL; + + FT_TRACE1(( "FT_Stream_Open:" )); + FT_TRACE1(( " opened `%s' (%ld bytes) successfully\n", + filepathname, stream->size )); + + return FT_Err_Ok; + + Fail_Read: + ft_free( stream->memory, stream->base ); + + Fail_Open: + CloseHandle( file ); + + stream->base = NULL; + stream->size = 0; + stream->pos = 0; + + return FT_THROW( Cannot_Open_Stream ); + } + + +#ifdef FT_DEBUG_MEMORY + + extern FT_Int + ft_mem_debug_init( FT_Memory memory ); + + extern void + ft_mem_debug_done( FT_Memory memory ); + +#endif + + + /* documentation is in ftobjs.h */ + + FT_BASE_DEF( FT_Memory ) + FT_New_Memory( void ) + { + HANDLE heap; + FT_Memory memory; + + + heap = GetProcessHeap(); + memory = heap ? (FT_Memory)HeapAlloc( heap, 0, sizeof ( *memory ) ) + : NULL; + + if ( memory ) + { + memory->user = heap; + memory->alloc = ft_alloc; + memory->realloc = ft_realloc; + memory->free = ft_free; +#ifdef FT_DEBUG_MEMORY + ft_mem_debug_init( memory ); +#endif + } + + return memory; + } + + + /* documentation is in ftobjs.h */ + + FT_BASE_DEF( void ) + FT_Done_Memory( FT_Memory memory ) + { +#ifdef FT_DEBUG_MEMORY + ft_mem_debug_done( memory ); +#endif + memory->free( memory, memory ); + } + + +/* END */ diff --git a/3rdparty/freetype-2.13.2/builds/windows/vc2010/freetype.sln b/3rdparty/freetype-2.13.2/builds/windows/vc2010/freetype.sln new file mode 100644 index 000000000..d88d70a26 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/vc2010/freetype.sln @@ -0,0 +1,52 @@ +Microsoft Visual Studio Solution File, Format Version 11.00 +# Visual Studio Express 2012 for Windows Desktop +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "freetype", "freetype.vcxproj", "{78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|x64 = Debug|x64 + Debug|ARM64 = Debug|ARM64 + Debug|Win32 = Debug|Win32 + Debug Static|x64 = Debug Static|x64 + Debug Static|ARM64 = Debug Static|ARM64 + Debug Static|Win32 = Debug Static|Win32 + Release|x64 = Release|x64 + Release|ARM64 = Release|ARM64 + Release|Win32 = Release|Win32 + Release Static|x64 = Release Static|x64 + Release Static|ARM64 = Release Static|ARM64 + Release Static|Win32 = Release Static|Win32 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Debug|x64.ActiveCfg = Debug|x64 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Debug|x64.Build.0 = Debug|x64 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Debug|ARM64.ActiveCfg = Debug|ARM64 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Debug|ARM64.Build.0 = Debug|ARM64 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Debug|Win32.ActiveCfg = Debug|Win32 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Debug|Win32.Build.0 = Debug|Win32 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Debug Static|x64.ActiveCfg = Debug Static|x64 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Debug Static|x64.Build.0 = Debug Static|x64 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Debug Static|ARM64.ActiveCfg = Debug Static|ARM64 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Debug Static|ARM64.Build.0 = Debug Static|ARM64 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Debug Static|Win32.ActiveCfg = Debug Static|Win32 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Debug Static|Win32.Build.0 = Debug Static|Win32 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Release|x64.ActiveCfg = Release|x64 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Release|x64.Build.0 = Release|x64 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Release|ARM64.ActiveCfg = Release|ARM64 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Release|ARM64.Build.0 = Release|ARM64 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Release|Win32.ActiveCfg = Release|Win32 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Release|Win32.Build.0 = Release|Win32 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Release Static|x64.ActiveCfg = Release Static|x64 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Release Static|x64.Build.0 = Release Static|x64 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Release Static|ARM64.ActiveCfg = Release Static|ARM64 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Release Static|ARM64.Build.0 = Release Static|ARM64 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Release Static|Win32.ActiveCfg = Release Static|Win32 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Release Static|Win32.Build.0 = Release Static|Win32 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection + GlobalSection(ExtensibilityGlobals) = postSolution + SolutionGuid = {90811697-0889-4381-80BC-C3FE8FA4931F} + EndGlobalSection +EndGlobal diff --git a/3rdparty/freetype-2.13.2/builds/windows/vc2010/freetype.user.props b/3rdparty/freetype-2.13.2/builds/windows/vc2010/freetype.user.props new file mode 100644 index 000000000..234dd5d79 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/vc2010/freetype.user.props @@ -0,0 +1,68 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/3rdparty/freetype-2.13.2/builds/windows/vc2010/freetype.vcxproj b/3rdparty/freetype-2.13.2/builds/windows/vc2010/freetype.vcxproj new file mode 100644 index 000000000..671d12450 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/vc2010/freetype.vcxproj @@ -0,0 +1,525 @@ + + + + + + Debug + Win32 + + + Debug + ARM64 + + + Debug + x64 + + + Debug Static + Win32 + + + Debug Static + ARM64 + + + Debug Static + x64 + + + Release + Win32 + + + Release + ARM64 + + + Release + x64 + + + Release Static + Win32 + + + Release Static + ARM64 + + + Release Static + x64 + + + + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B} + FreeType + + + + $(DefaultPlatformToolset) + + + DynamicLibrary + NotSet + + + DynamicLibrary + NotSet + + + DynamicLibrary + NotSet + + + StaticLibrary + NotSet + + + StaticLibrary + NotSet + + + StaticLibrary + NotSet + + + DynamicLibrary + NotSet + + + DynamicLibrary + NotSet + + + DynamicLibrary + NotSet + + + StaticLibrary + NotSet + + + StaticLibrary + NotSet + + + StaticLibrary + NotSet + + + + + + ..\..\..\objs\$(Platform)\$(Configuration)\ + ..\..\..\objs\$(Platform)\$(Configuration)\ + AllRules.ruleset + + + freetype + + + + + Disabled + $(UserOptionDirectory);..\..\..\include;$(UserIncludeDirectories);%(AdditionalIncludeDirectories) + WIN32;_DEBUG;_LIB;_CRT_SECURE_NO_WARNINGS;FT_DEBUG_LEVEL_ERROR;FT_DEBUG_LEVEL_TRACE;FT2_BUILD_LIBRARY;DLL_EXPORT;$(UserDefines);%(PreprocessorDefinitions) + EnableFastChecks + MultiThreadedDebugDLL + false + Level4 + ProgramDatabase + Default + 4001 + true + $(OutDir)$(TargetName).pdb + Disabled + + + _DEBUG;DLL_EXPORT;$(UserDefines);%(PreprocessorDefinitions) + 0x0409 + + + true + MachineX86 + $(UserLibraryDirectories);%(AdditionalLibraryDirectories) + $(UserDependencies);%(AdditionalDependencies) + + + + + Disabled + $(UserOptionDirectory);..\..\..\include;$(UserIncludeDirectories);%(AdditionalIncludeDirectories) + WIN32;_DEBUG;_LIB;_CRT_SECURE_NO_WARNINGS;FT_DEBUG_LEVEL_ERROR;FT_DEBUG_LEVEL_TRACE;FT2_BUILD_LIBRARY;DLL_EXPORT;$(UserDefines);%(PreprocessorDefinitions) + EnableFastChecks + MultiThreadedDebugDLL + false + Level4 + ProgramDatabase + Default + 4001;4267 + true + $(OutDir)$(TargetName).pdb + Disabled + + + _DEBUG;DLL_EXPORT;$(UserDefines);%(PreprocessorDefinitions) + 0x0409 + + + true + MachineARM64 + $(UserLibraryDirectories);%(AdditionalLibraryDirectories) + $(UserDependencies);%(AdditionalDependencies) + + + + + Disabled + $(UserOptionDirectory);..\..\..\include;$(UserIncludeDirectories);%(AdditionalIncludeDirectories) + WIN32;_DEBUG;_LIB;_CRT_SECURE_NO_WARNINGS;FT_DEBUG_LEVEL_ERROR;FT_DEBUG_LEVEL_TRACE;FT2_BUILD_LIBRARY;DLL_EXPORT;$(UserDefines);%(PreprocessorDefinitions) + EnableFastChecks + MultiThreadedDebugDLL + false + Level4 + ProgramDatabase + Default + 4001;4267 + true + $(OutDir)$(TargetName).pdb + Disabled + + + _DEBUG;DLL_EXPORT;$(UserDefines);%(PreprocessorDefinitions) + 0x0409 + + + true + MachineX64 + $(UserLibraryDirectories);%(AdditionalLibraryDirectories) + $(UserDependencies);%(AdditionalDependencies) + + + + + Disabled + $(UserOptionDirectory);..\..\..\include;$(UserIncludeDirectories);%(AdditionalIncludeDirectories) + WIN32;_DEBUG;_LIB;_CRT_SECURE_NO_WARNINGS;FT_DEBUG_LEVEL_ERROR;FT_DEBUG_LEVEL_TRACE;FT2_BUILD_LIBRARY;$(UserDefines);%(PreprocessorDefinitions) + EnableFastChecks + MultiThreadedDebug + false + Level4 + ProgramDatabase + Default + 4001 + true + $(OutDir)$(TargetName).pdb + Disabled + + + _DEBUG;$(UserDefines);%(PreprocessorDefinitions) + 0x0409 + + + MachineX86 + $(UserLibraryDirectories);%(AdditionalLibraryDirectories) + $(UserDependencies);%(AdditionalDependencies) + + + + + Disabled + $(UserOptionDirectory);..\..\..\include;$(UserIncludeDirectories);%(AdditionalIncludeDirectories) + WIN32;_DEBUG;_LIB;_CRT_SECURE_NO_WARNINGS;FT_DEBUG_LEVEL_ERROR;FT_DEBUG_LEVEL_TRACE;FT2_BUILD_LIBRARY;$(UserDefines);%(PreprocessorDefinitions) + EnableFastChecks + MultiThreadedDebug + false + Level4 + ProgramDatabase + Default + 4001;4267 + true + $(OutDir)$(TargetName).pdb + Disabled + + + _DEBUG;$(UserDefines);%(PreprocessorDefinitions) + 0x0409 + + + MachineARM64 + $(UserLibraryDirectories);%(AdditionalLibraryDirectories) + $(UserDependencies);%(AdditionalDependencies) + + + + + Disabled + $(UserOptionDirectory);..\..\..\include;$(UserIncludeDirectories);%(AdditionalIncludeDirectories) + WIN32;_DEBUG;_LIB;_CRT_SECURE_NO_WARNINGS;FT_DEBUG_LEVEL_ERROR;FT_DEBUG_LEVEL_TRACE;FT2_BUILD_LIBRARY;$(UserDefines);%(PreprocessorDefinitions) + EnableFastChecks + MultiThreadedDebug + false + Level4 + ProgramDatabase + Default + 4001;4267 + true + $(OutDir)$(TargetName).pdb + Disabled + + + _DEBUG;$(UserDefines);%(PreprocessorDefinitions) + 0x0409 + + + MachineX64 + $(UserLibraryDirectories);%(AdditionalLibraryDirectories) + $(UserDependencies);%(AdditionalDependencies) + + + + + MaxSpeed + AnySuitable + $(UserOptionDirectory);..\..\..\include;$(UserIncludeDirectories);%(AdditionalIncludeDirectories) + WIN32;NDEBUG;_LIB;_CRT_SECURE_NO_WARNINGS;FT2_BUILD_LIBRARY;DLL_EXPORT;$(UserDefines);%(PreprocessorDefinitions) + MultiThreadedDLL + true + true + Level4 + Default + 4001 + true + StreamingSIMDExtensions2 + true + + + NDEBUG;DLL_EXPORT;$(UserDefines);%(PreprocessorDefinitions) + 0x0409 + + + true + true + MachineX86 + $(UserLibraryDirectories);%(AdditionalLibraryDirectories) + $(UserDependencies);%(AdditionalDependencies) + + + + + MaxSpeed + AnySuitable + $(UserOptionDirectory);..\..\..\include;$(UserIncludeDirectories);%(AdditionalIncludeDirectories) + WIN32;NDEBUG;_LIB;_CRT_SECURE_NO_WARNINGS;FT2_BUILD_LIBRARY;DLL_EXPORT;$(UserDefines);%(PreprocessorDefinitions) + MultiThreadedDLL + true + true + Level4 + Default + 4001;4267 + true + NotSet + true + + + NDEBUG;DLL_EXPORT;$(UserDefines);%(PreprocessorDefinitions) + 0x0409 + + + true + true + MachineARM64 + $(UserLibraryDirectories);%(AdditionalLibraryDirectories) + $(UserDependencies);%(AdditionalDependencies) + + + + + MaxSpeed + AnySuitable + $(UserOptionDirectory);..\..\..\include;$(UserIncludeDirectories);%(AdditionalIncludeDirectories) + WIN32;NDEBUG;_LIB;_CRT_SECURE_NO_WARNINGS;FT2_BUILD_LIBRARY;DLL_EXPORT;$(UserDefines);%(PreprocessorDefinitions) + MultiThreadedDLL + true + true + Level4 + Default + 4001;4267 + true + true + + + NDEBUG;DLL_EXPORT;$(UserDefines);%(PreprocessorDefinitions) + 0x0409 + + + true + true + MachineX64 + $(UserLibraryDirectories);%(AdditionalLibraryDirectories) + $(UserDependencies);%(AdditionalDependencies) + + + + + MaxSpeed + AnySuitable + $(UserOptionDirectory);..\..\..\include;$(UserIncludeDirectories);%(AdditionalIncludeDirectories) + WIN32;NDEBUG;_LIB;_CRT_SECURE_NO_WARNINGS;FT2_BUILD_LIBRARY;$(UserDefines);%(PreprocessorDefinitions) + MultiThreaded + true + true + Level4 + Default + 4001 + true + StreamingSIMDExtensions2 + true + + + NDEBUG;$(UserDefines);%(PreprocessorDefinitions) + 0x0409 + + + MachineX86 + $(UserLibraryDirectories);%(AdditionalLibraryDirectories) + $(UserDependencies);%(AdditionalDependencies) + + + + + MaxSpeed + AnySuitable + $(UserOptionDirectory);..\..\..\include;$(UserIncludeDirectories);%(AdditionalIncludeDirectories) + WIN32;NDEBUG;_LIB;_CRT_SECURE_NO_WARNINGS;FT2_BUILD_LIBRARY;$(UserDefines);%(PreprocessorDefinitions) + MultiThreaded + true + true + Level4 + Default + 4001;4267 + true + NotSet + true + + + NDEBUG;$(UserDefines);%(PreprocessorDefinitions) + 0x0409 + + + MachineARM64 + $(UserLibraryDirectories);%(AdditionalLibraryDirectories) + $(UserDependencies);%(AdditionalDependencies) + + + + + MaxSpeed + AnySuitable + $(UserOptionDirectory);..\..\..\include;$(UserIncludeDirectories);%(AdditionalIncludeDirectories) + WIN32;NDEBUG;_LIB;_CRT_SECURE_NO_WARNINGS;FT2_BUILD_LIBRARY;$(UserDefines);%(PreprocessorDefinitions) + MultiThreaded + true + true + Level4 + Default + 4001;4267 + true + true + + + NDEBUG;$(UserDefines);%(PreprocessorDefinitions) + 0x0409 + + + MachineX64 + $(UserLibraryDirectories);%(AdditionalLibraryDirectories) + $(UserDependencies);%(AdditionalDependencies) + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + false + + + false + + + + + + + + + ..\..\..\include\dlg\output.h + + + ..\..\..\include\dlg\dlg.h + + + ..\..\..\src\dlg\dlg.c + + + + + + + + + + + + + diff --git a/3rdparty/freetype-2.13.2/builds/windows/vc2010/freetype.vcxproj.filters b/3rdparty/freetype-2.13.2/builds/windows/vc2010/freetype.vcxproj.filters new file mode 100644 index 000000000..4085f6c4d --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/vc2010/freetype.vcxproj.filters @@ -0,0 +1,149 @@ + + + + + {b4c15893-ec11-491d-9507-0ac184f9cc78} + cpp;c;cxx;rc;def;r;odl;idl;hpj;bat + + + {4d3e4eff-3fbc-4b20-b413-2743b23b7109} + + + {e6cf6a0f-0404-4024-8bf8-ff5b29f35657} + h;hpp;hxx;hm;inl + + + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files\FT_MODULES + + + Source Files\FT_MODULES + + + Source Files\FT_MODULES + + + Source Files\FT_MODULES + + + Source Files\FT_MODULES + + + Source Files\FT_MODULES + + + Source Files\FT_MODULES + + + Source Files\FT_MODULES + + + Source Files\FT_MODULES + + + Source Files\FT_MODULES + + + Source Files\FT_MODULES + + + Source Files\FT_MODULES + + + Source Files\FT_MODULES + + + Source Files\FT_MODULES + + + Source Files\FT_MODULES + + + Source Files\FT_MODULES + + + Source Files + + + Source Files + + + + + Source Files + + + diff --git a/3rdparty/freetype-2.13.2/builds/windows/vc2010/index.html b/3rdparty/freetype-2.13.2/builds/windows/vc2010/index.html new file mode 100644 index 000000000..ee9b59a2b --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/vc2010/index.html @@ -0,0 +1,40 @@ + +
+ + FreeType 2 Project Files for Visual C++ 2010 or newer + + + +

+ FreeType 2 Project Files for Visual C++ 2010 or newer +

+ +

This directory contains solution and project files for +Visual C++ 2010 or newer, named freetype.sln, +and freetype.vcxproj. It compiles the following libraries +from the FreeType 2.13.2 sources:

+ +
    +
  • freetype.dll using 'Release' or 'Debug' configurations
  • +
  • freetype.lib using 'Release Static' or 'Debug Static' configurations
  • +
+ +

Both Win32 and x64 builds are supported. Build directories and target +files are placed in the top-level objs directory.

+ +

Customization of the FreeType library is done by editing the +ftoption.h header file in the top-level devel path. +Alternatively, you may copy the file to another directory and change the +include directory in freetype.users.props.

+ +

To configure library dependencies like zlib and libpng, +edit the freetype.users.props file in this directory. It also +simplifies automated (command-line) builds using msbuild.

+ +

To link your executable with FreeType DLL, you may want to define +DLL_IMPORT so that the imported functions are appropriately +attributed with dllimport.

+ + + diff --git a/3rdparty/freetype-2.13.2/builds/windows/visualc/freetype.dsp b/3rdparty/freetype-2.13.2/builds/windows/visualc/freetype.dsp new file mode 100644 index 000000000..540f5b9ad --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/visualc/freetype.dsp @@ -0,0 +1,354 @@ +# Microsoft Developer Studio Project File - Name="freetype" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Dynamic-Link Library" 0x0102 +# TARGTYPE "Win32 (x86) Static Library" 0x0104 + +CFG=freetype - Win32 Release +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "freetype.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "freetype.mak" CFG="freetype - Win32 Release" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "freetype - Win32 Release" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE "freetype - Win32 Debug" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE "freetype - Win32 Release Static" (based on "Win32 (x86) Static Library") +!MESSAGE "freetype - Win32 Debug Static" (based on "Win32 (x86) Static Library") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" + +!IF "$(CFG)" == "freetype - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "..\..\..\objs\Win32\Release" +# PROP Intermediate_Dir "..\..\..\objs\Win32\Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +CPP=cl.exe +# ADD BASE CPP /nologo /MD /W3 /O2 /D "WIN32" /D "NDEBUG" /FD /c +# SUBTRACT BASE CPP /YX /Yc /Yu +# ADD CPP /nologo /Za /MD /W3 /O2 /Oi /D "WIN32" /I "..\..\..\include" /D "_CRT_SECURE_NO_WARNINGS" /D "NDEBUG" /D "FT2_BUILD_LIBRARY" /D "DLL_EXPORT" /FD /c +# SUBTRACT CPP /YX /Yc /Yu +MTL=midl.exe +# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +RSC=rc.exe +# ADD BASE RSC /l 0x409 /d "NDEBUG" +# ADD RSC /l 0x409 /d "NDEBUG" /d "DLL_EXPORT" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 +# ADD LINK32 /nologo /dll /machine:I386 /opt:REF,ICF /out:"$(OutDir)\freetype.dll" + +!ELSEIF "$(CFG)" == "freetype - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "..\..\..\objs\Win32\Debug" +# PROP Intermediate_Dir "..\..\..\objs\Win32\Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +CPP=cl.exe +# ADD BASE CPP /nologo /MDd /W3 /Gm /ZI /Od /D "WIN32" /D "_DEBUG" /FD /GZ /c +# SUBTRACT BASE CPP /YX /Yc /Yu +# ADD CPP /nologo /Za /MDd /W3 /Gm /ZI /Od /I "..\..\..\include" /D "WIN32" /D "_CRT_SECURE_NO_WARNINGS" /D "_DEBUG" /D "FT_DEBUG_LEVEL_ERROR" /D "FT_DEBUG_LEVEL_TRACE" /D "FT2_BUILD_LIBRARY" /D "DLL_EXPORT" /FR /FD /GZ /c +# SUBTRACT CPP /YX /Yc /Yu +MTL=midl.exe +# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +RSC=rc.exe +# ADD BASE RSC /l 0x409 /d "_DEBUG" +# ADD RSC /l 0x409 /d "_DEBUG" /d "DLL_EXPORT" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept +# ADD LINK32 /nologo /dll /debug /machine:I386 /out:"$(OutDir)\freetype.dll" /pdbtype:sept + +!ELSEIF "$(CFG)" == "freetype - Win32 Release Static" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release Static" +# PROP BASE Intermediate_Dir "Release Static" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "..\..\..\objs\Win32\Release Static" +# PROP Intermediate_Dir "..\..\..\objs\Win32\Release Static" +# PROP Target_Dir "" +CPP=cl.exe +# ADD BASE CPP /nologo /MD /W3 /O2 /D "WIN32" /D "NDEBUG" /FD /c +# SUBTRACT BASE CPP /YX /Yc /Yu +# ADD CPP /nologo /Za /MD /W3 /O2 /Oi /D "WIN32" /I "..\..\..\include" /D "_CRT_SECURE_NO_WARNINGS" /D "NDEBUG" /D "FT2_BUILD_LIBRARY" /FD /c +# SUBTRACT CPP /YX /Yc /Yu +RSC=rc.exe +# ADD BASE RSC /l 0x409 /d "NDEBUG" +# ADD RSC /l 0x409 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LIB32=link.exe -lib +# ADD BASE LIB32 /nologo +# ADD LIB32 /nologo /out:"$(OutDir)\freetype.lib" + +!ELSEIF "$(CFG)" == "freetype - Win32 Debug Static" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug Static" +# PROP BASE Intermediate_Dir "Debug Static" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "..\..\..\objs\Win32\Debug Static" +# PROP Intermediate_Dir "..\..\..\objs\Win32\Debug Static" +# PROP Target_Dir "" +CPP=cl.exe +# ADD BASE CPP /nologo /MDd /W3 /Gm /ZI /Od /D "WIN32" /D "_DEBUG" /FD /GZ /c +# SUBTRACT BASE CPP /YX /Yc /Yu +# ADD CPP /nologo /Za /MDd /W3 /Gm /ZI /Od /I "..\..\..\include" /D "WIN32" /D "_CRT_SECURE_NO_WARNINGS" /D "_DEBUG" /D "FT_DEBUG_LEVEL_ERROR" /D "FT_DEBUG_LEVEL_TRACE" /D "FT2_BUILD_LIBRARY" /FR /FD /GZ /c +# SUBTRACT CPP /YX /Yc /Yu +RSC=rc.exe +# ADD BASE RSC /l 0x409 /d "_DEBUG" +# ADD RSC /l 0x409 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LIB32=link.exe -lib +# ADD BASE LIB32 /nologo +# ADD LIB32 /nologo /out:"$(OutDir)\freetype.lib" + +!ENDIF + +# Begin Target + +# Name "freetype - Win32 Release" +# Name "freetype - Win32 Debug" +# Name "freetype - Win32 Release Static" +# Name "freetype - Win32 Debug Static" +# Begin Group "Source Files" + +# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat" +# Begin Source File + +SOURCE=..\..\..\src\autofit\autofit.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\bdf\bdf.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\cff\cff.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftbase.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftbbox.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftbdf.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftbitmap.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftcid.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftpatent.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftfstype.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftgasp.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\cache\ftcache.c +# End Source File +# Begin Source File + +SOURCE=..\ftdebug.c +# ADD CPP /Ze +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftglyph.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftgxval.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\gzip\ftgzip.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftinit.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\lzw\ftlzw.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftmm.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftotval.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftpfr.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftstroke.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftsynth.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftsystem.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\fttype1.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftwinfnt.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\pcf\pcf.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\pfr\pfr.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\psaux\psaux.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\pshinter\pshinter.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\psnames\psmodule.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\raster\raster.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\sfnt\sfnt.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\smooth\smooth.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\truetype\truetype.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\type1\type1.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\cid\type1cid.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\type42\type42.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\winfonts\winfnt.c +# End Source File +# End Group +# Begin Group "Header Files" + +# PROP Default_Filter "h;hpp;hxx;hm;inl" +# Begin Source File + +SOURCE=..\..\..\include\ft2build.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\include\freetype\config\ftconfig.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\include\freetype\config\ftheader.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\include\freetype\config\ftmodule.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\include\freetype\config\ftoption.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\include\freetype\config\ftstdlib.h +# End Source File +# End Group +# Begin Group "Resource Files" + +# PROP Default_Filter "rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx" +# Begin Source File + +SOURCE=..\..\..\src\base\ftver.rc +# End Source File +# End Group +# End Target +# End Project diff --git a/3rdparty/freetype-2.13.2/builds/windows/visualc/freetype.dsw b/3rdparty/freetype-2.13.2/builds/windows/visualc/freetype.dsw new file mode 100644 index 000000000..b149e769b --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/visualc/freetype.dsw @@ -0,0 +1,29 @@ +Microsoft Developer Studio Workspace File, Format Version 6.00 +# WARNING: DO NOT EDIT OR DELETE THIS WORKSPACE FILE! + +############################################################################### + +Project: "freetype"=.\freetype.dsp - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ +}}} + +############################################################################### + +Global: + +Package=<5> +{{{ +}}} + +Package=<3> +{{{ +}}} + +############################################################################### + diff --git a/3rdparty/freetype-2.13.2/builds/windows/visualc/freetype.sln b/3rdparty/freetype-2.13.2/builds/windows/visualc/freetype.sln new file mode 100644 index 000000000..9054d0abe --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/visualc/freetype.sln @@ -0,0 +1,25 @@ +Microsoft Visual Studio Solution File, Format Version 7.00 +# Visual C++ 2002-2008 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "freetype", "freetype.vcproj", "{78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug Static|Win32 = Debug Static|Win32 + Debug|Win32 = Debug|Win32 + Release Static|Win32 = Release Static|Win32 + Release|Win32 = Release|Win32 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Debug Static|Win32.ActiveCfg = Debug Static|Win32 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Debug Static|Win32.Build.0 = Debug Static|Win32 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Debug|Win32.ActiveCfg = Debug|Win32 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Debug|Win32.Build.0 = Debug|Win32 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Release Static|Win32.ActiveCfg = Release Static|Win32 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Release Static|Win32.Build.0 = Release Static|Win32 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Release|Win32.ActiveCfg = Release|Win32 + {78B079BD-9FC7-4B9E-B4A6-96DA0F00248B}.Release|Win32.Build.0 = Release|Win32 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection +EndGlobal diff --git a/3rdparty/freetype-2.13.2/builds/windows/visualc/freetype.vcproj b/3rdparty/freetype-2.13.2/builds/windows/visualc/freetype.vcproj new file mode 100644 index 000000000..a16782c23 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/visualc/freetype.vcproj @@ -0,0 +1,587 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/3rdparty/freetype-2.13.2/builds/windows/visualc/index.html b/3rdparty/freetype-2.13.2/builds/windows/visualc/index.html new file mode 100644 index 000000000..816605e07 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/visualc/index.html @@ -0,0 +1,38 @@ + +
+ + FreeType 2 Project Files for Visual C++ 6.0 and 2002-2008 + + + +

+ FreeType 2 Project Files for Visual C++ 6.0 and 2002-2008 +

+ +

This directory contains project files freetype.dsp for +Visual C++ 6.0, and freetype.vcproj for Visual C++ 2002 +through 2008, which you might need to upgrade automatically. +It compiles the following libraries from the FreeType 2.13.2 sources:

+ +
    +
  • freetype.dll using 'Release' or 'Debug' configurations
  • +
  • freetype.lib using 'Release Static' or 'Debug Static' configurations
  • +
+ +

Build directories and target files are placed in the top-level +objs directory.

+ +

Be sure to extract the files with the Windows (CR+LF) line endings. ZIP +archives are already stored this way, so no further action is required. If +you use some .tar.*z archives, be sure to configure your extracting +tool to convert the line endings. For example, with WinZip, you should activate the TAR +file smart CR/LF Conversion option. Alternatively, you may consider +using the unix2dos or u2d utilities that are floating +around, which specifically deal with this particular problem. + +

Build directories are placed in the top-level objs +directory.

+ + + diff --git a/3rdparty/freetype-2.13.2/builds/windows/visualce/freetype.dsp b/3rdparty/freetype-2.13.2/builds/windows/visualce/freetype.dsp new file mode 100644 index 000000000..714c42257 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/visualce/freetype.dsp @@ -0,0 +1,391 @@ +# Microsoft Developer Studio Project File - Name="freetype" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Static Library" 0x0104 + +CFG=freetype - Win32 Debug Singlethreaded +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "freetype.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "freetype.mak" CFG="freetype - Win32 Debug Singlethreaded" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "freetype - Win32 Release" (based on "Win32 (x86) Static Library") +!MESSAGE "freetype - Win32 Debug" (based on "Win32 (x86) Static Library") +!MESSAGE "freetype - Win32 Debug Multithreaded" (based on "Win32 (x86) Static Library") +!MESSAGE "freetype - Win32 Release Multithreaded" (based on "Win32 (x86) Static Library") +!MESSAGE "freetype - Win32 Release Singlethreaded" (based on "Win32 (x86) Static Library") +!MESSAGE "freetype - Win32 Debug Singlethreaded" (based on "Win32 (x86) Static Library") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +RSC=rc.exe + +!IF "$(CFG)" == "freetype - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "..\..\..\objs\release" +# PROP Intermediate_Dir "..\..\..\objs\release" +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_MBCS" /D "_LIB" /YX /FD /c +# ADD CPP /MD /Za /W4 /GX /O2 /I "..\..\..\include" /D "NDEBUG" /D "WIN32" /D "_MBCS" /D "_LIB" /D "FT2_BUILD_LIBRARY" /FD /c +# SUBTRACT CPP /nologo /Z /YX +# ADD BASE RSC /l 0x409 /d "NDEBUG" +# ADD RSC /l 0x409 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LIB32=link.exe -lib +# ADD BASE LIB32 /nologo +# ADD LIB32 /nologo /out:"..\..\..\objs\freetype.lib" + +!ELSEIF "$(CFG)" == "freetype - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "..\..\..\objs\debug" +# PROP Intermediate_Dir "..\..\..\objs\debug" +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_MBCS" /D "_LIB" /YX /FD /GZ /c +# ADD CPP /MDd /Za /W4 /GX /Z7 /Od /I "..\..\..\include" /D "_DEBUG" /D "FT_DEBUG_LEVEL_ERROR" /D "FT_DEBUG_LEVEL_TRACE" /D "WIN32" /D "_MBCS" /D "_LIB" /D "FT2_BUILD_LIBRARY" /FD /GZ /c +# SUBTRACT CPP /nologo /X /YX +# ADD BASE RSC /l 0x409 /d "_DEBUG" +# ADD RSC /l 0x409 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LIB32=link.exe -lib +# ADD BASE LIB32 /nologo +# ADD LIB32 /nologo /out:"..\..\..\objs\freetype_D.lib" + +!ELSEIF "$(CFG)" == "freetype - Win32 Debug Multithreaded" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "freetype___Win32_Debug_Multithreaded" +# PROP BASE Intermediate_Dir "freetype___Win32_Debug_Multithreaded" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "..\..\..\objs\debug_mt" +# PROP Intermediate_Dir "..\..\..\objs\debug_mt" +# PROP Target_Dir "" +# ADD BASE CPP /nologo /Za /W3 /Gm /GX /ZI /Od /I "..\include\\" /D "_DEBUG" /D "WIN32" /D "_MBCS" /D "_LIB" /D "FT_FLAT_COMPILE" /YX /FD /GZ /c +# SUBTRACT BASE CPP /X +# ADD CPP /MTd /Za /W4 /GX /Z7 /Od /I "..\..\..\include" /D "_DEBUG" /D "FT_DEBUG_LEVEL_ERROR" /D "FT_DEBUG_LEVEL_TRACE" /D "WIN32" /D "_MBCS" /D "_LIB" /D "FT2_BUILD_LIBRARY" /FD /GZ /c +# SUBTRACT CPP /nologo /X /YX +# ADD BASE RSC /l 0x409 /d "_DEBUG" +# ADD RSC /l 0x409 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LIB32=link.exe -lib +# ADD BASE LIB32 /nologo /out:"lib\freetype_D.lib" +# ADD LIB32 /nologo /out:"..\..\..\objs\freetypeMT_D.lib" + +!ELSEIF "$(CFG)" == "freetype - Win32 Release Multithreaded" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "freetype___Win32_Release_Multithreaded" +# PROP BASE Intermediate_Dir "freetype___Win32_Release_Multithreaded" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "..\..\..\objs\release_mt" +# PROP Intermediate_Dir "..\..\..\objs\release_mt" +# PROP Target_Dir "" +# ADD BASE CPP /nologo /Za /W3 /GX /O2 /I "..\include\\" /D "NDEBUG" /D "WIN32" /D "_MBCS" /D "_LIB" /D "FT_FLAT_COMPILE" /YX /FD /c +# ADD CPP /MT /Za /W4 /GX /O2 /I "..\..\..\include" /D "NDEBUG" /D "WIN32" /D "_MBCS" /D "_LIB" /D "FT2_BUILD_LIBRARY" /FD /c +# SUBTRACT CPP /nologo /Z /YX +# ADD BASE RSC /l 0x409 /d "NDEBUG" +# ADD RSC /l 0x409 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LIB32=link.exe -lib +# ADD BASE LIB32 /nologo /out:"lib\freetype.lib" +# ADD LIB32 /nologo /out:"..\..\..\objs\freetypeMT.lib" + +!ELSEIF "$(CFG)" == "freetype - Win32 Release Singlethreaded" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "freetype___Win32_Release_Singlethreaded" +# PROP BASE Intermediate_Dir "freetype___Win32_Release_Singlethreaded" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "..\..\..\objs\release_st" +# PROP Intermediate_Dir "..\..\..\objs\release_st" +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MD /Za /W4 /GX /Zi /O2 /I "..\..\..\include" /D "NDEBUG" /D "WIN32" /D "_MBCS" /D "_LIB" /FD /c +# SUBTRACT BASE CPP /YX +# ADD CPP /Za /W4 /GX /O2 /I "..\..\..\include" /D "NDEBUG" /D "WIN32" /D "_MBCS" /D "_LIB" /D "FT2_BUILD_LIBRARY" /FD /c +# SUBTRACT CPP /nologo /Z /YX +# ADD BASE RSC /l 0x409 /d "NDEBUG" +# ADD RSC /l 0x409 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LIB32=link.exe -lib +# ADD BASE LIB32 /nologo /out:"..\..\..\objs\freetype.lib" +# ADD LIB32 /out:"..\..\..\objs\freetypeST.lib" +# SUBTRACT LIB32 /nologo + +!ELSEIF "$(CFG)" == "freetype - Win32 Debug Singlethreaded" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "freetype___Win32_Debug_Singlethreaded" +# PROP BASE Intermediate_Dir "freetype___Win32_Debug_Singlethreaded" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "..\..\..\objs\debug_st" +# PROP Intermediate_Dir "..\..\..\objs\debug_st" +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MDd /Za /W4 /Gm /GX /Zi /Od /I "..\..\..\include" /D "_DEBUG" /D "WIN32" /D "_MBCS" /D "_LIB" /D "FT_DEBUG_LEVEL_ERROR" /D "FT_DEBUG_LEVEL_TRACE" /FD /GZ /c +# SUBTRACT BASE CPP /X /YX +# ADD CPP /Za /W4 /GX /Z7 /Od /I "..\..\..\include" /D "_DEBUG" /D "FT_DEBUG_LEVEL_ERROR" /D "FT_DEBUG_LEVEL_TRACE" /D "WIN32" /D "_MBCS" /D "_LIB" /D "FT2_BUILD_LIBRARY" /FD /GZ /c +# SUBTRACT CPP /nologo /X /YX +# ADD BASE RSC /l 0x409 /d "_DEBUG" +# ADD RSC /l 0x409 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LIB32=link.exe -lib +# ADD BASE LIB32 /nologo /out:"..\..\..\objs\freetype_D.lib" +# ADD LIB32 /nologo /out:"..\..\..\objs\freetypeST_D.lib" + +!ENDIF + +# Begin Target + +# Name "freetype - Win32 Release" +# Name "freetype - Win32 Debug" +# Name "freetype - Win32 Debug Multithreaded" +# Name "freetype - Win32 Release Multithreaded" +# Name "freetype - Win32 Release Singlethreaded" +# Name "freetype - Win32 Debug Singlethreaded" +# Begin Group "Source Files" + +# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat" +# Begin Source File + +SOURCE=..\..\..\src\autofit\autofit.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\bdf\bdf.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\cff\cff.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftbase.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftbbox.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftbdf.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftbitmap.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftcid.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftfstype.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftgasp.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\cache\ftcache.c +# End Source File +# Begin Source File + +SOURCE=..\ftdebug.c +# ADD CPP /Ze +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftglyph.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftgxval.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\gzip\ftgzip.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftinit.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\lzw\ftlzw.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftmm.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftotval.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftpatent.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftpfr.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftstroke.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftsynth.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftsystem.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\fttype1.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\base\ftwinfnt.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\pcf\pcf.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\pfr\pfr.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\psaux\psaux.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\pshinter\pshinter.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\psnames\psmodule.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\raster\raster.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\sfnt\sfnt.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\smooth\smooth.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\truetype\truetype.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\type1\type1.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\cid\type1cid.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\type42\type42.c +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\winfonts\winfnt.c +# End Source File +# End Group +# Begin Group "Header Files" + +# PROP Default_Filter "h;hpp;hxx;hm;inl" +# Begin Source File + +SOURCE=..\..\..\include\ft2build.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\include\freetype\config\ftconfig.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\include\freetype\config\ftheader.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\include\freetype\config\ftmodule.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\include\freetype\config\ftoption.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\include\freetype\config\ftstdlib.h +# End Source File +# End Group +# Begin Group "Resource Files" + +# PROP Default_Filter "rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx" +# Begin Source File + +SOURCE=..\..\..\src\base\ftver.rc +# End Source File +# End Group +# End Target +# End Project diff --git a/3rdparty/freetype-2.13.2/builds/windows/visualce/freetype.dsw b/3rdparty/freetype-2.13.2/builds/windows/visualce/freetype.dsw new file mode 100644 index 000000000..b149e769b --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/visualce/freetype.dsw @@ -0,0 +1,29 @@ +Microsoft Developer Studio Workspace File, Format Version 6.00 +# WARNING: DO NOT EDIT OR DELETE THIS WORKSPACE FILE! + +############################################################################### + +Project: "freetype"=.\freetype.dsp - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ +}}} + +############################################################################### + +Global: + +Package=<5> +{{{ +}}} + +Package=<3> +{{{ +}}} + +############################################################################### + diff --git a/3rdparty/freetype-2.13.2/builds/windows/visualce/freetype.vcproj b/3rdparty/freetype-2.13.2/builds/windows/visualce/freetype.vcproj new file mode 100644 index 000000000..e271462bd --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/visualce/freetype.vcproj @@ -0,0 +1,3706 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/3rdparty/freetype-2.13.2/builds/windows/visualce/index.html b/3rdparty/freetype-2.13.2/builds/windows/visualce/index.html new file mode 100644 index 000000000..d9c8fe475 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/visualce/index.html @@ -0,0 +1,47 @@ + +
+ + FreeType 2 Project Files for Visual C++ and VS.NET 2005 + (Pocket PC) + + + +

+ FreeType 2 Project Files for Visual C++ and VS.NET 2005 + (Pocket PC) +

+ +

This directory contains project files for Visual C++, named +freetype.dsp, and Visual Studio, called freetype.sln for +the following targets: + +

    +
  • PPC/SP 2003 (Pocket PC 2003)
  • +
  • PPC/SP WM5 (Windows Mobile 5)
  • +
  • PPC/SP WM6 (Windows Mobile 6)
  • +
+ +It compiles the following libraries from the FreeType 2.13.2 sources:

+ +
    +
    +    freetype.lib     - release build; single threaded
    +    freetype_D.lib   - debug build;   single threaded
    +    freetypeMT.lib   - release build; multi-threaded
    +    freetypeMT_D.lib - debug build;   multi-threaded
    +
+ +

Be sure to extract the files with the Windows (CR+LF) line endings. ZIP +archives are already stored this way, so no further action is required. If +you use some .tar.*z archives, be sure to configure your extracting +tool to convert the line endings. For example, with WinZip, you should activate the TAR +file smart CR/LF Conversion option. Alternatively, you may consider +using the unix2dos or u2d utilities that are floating +around, which specifically deal with this particular problem. + +

Build directories are placed in the top-level objs +directory.

+ + + diff --git a/3rdparty/freetype-2.13.2/builds/windows/w32-bcc.mk b/3rdparty/freetype-2.13.2/builds/windows/w32-bcc.mk new file mode 100644 index 000000000..e7cf668df --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/w32-bcc.mk @@ -0,0 +1,28 @@ +# +# FreeType 2 Borland C++ on Win32 +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + +# default definitions of the export list +# +EXPORTS_LIST = $(OBJ_DIR)/freetype.def +EXPORTS_OPTIONS = /DEF:$(EXPORTS_LIST) +APINAMES_OPTIONS := -dfreetype.dll -wB + +include $(TOP_DIR)/builds/windows/win32-def.mk +include $(TOP_DIR)/builds/compiler/bcc.mk + +# include linking instructions +include $(TOP_DIR)/builds/link_dos.mk + + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/windows/w32-bccd.mk b/3rdparty/freetype-2.13.2/builds/windows/w32-bccd.mk new file mode 100644 index 000000000..64dafdb94 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/w32-bccd.mk @@ -0,0 +1,26 @@ +# +# FreeType 2 Borland C++ on Win32 + debugging +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + + +DEVEL_DIR := $(TOP_DIR)/devel + +include $(TOP_DIR)/builds/windows/win32-def.mk + +include $(TOP_DIR)/builds/compiler/bcc-dev.mk + +# include linking instructions +include $(TOP_DIR)/builds/link_dos.mk + + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/windows/w32-dev.mk b/3rdparty/freetype-2.13.2/builds/windows/w32-dev.mk new file mode 100644 index 000000000..7c89ad2a2 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/w32-dev.mk @@ -0,0 +1,32 @@ +# +# FreeType 2 configuration rules for Win32 + GCC +# +# Development version without optimizations. +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + + +# NOTE: This version requires that GNU Make is invoked from the Windows +# Shell (_not_ Cygwin BASH)! +# + +DEVEL_DIR := $(TOP_DIR)/devel + +include $(TOP_DIR)/builds/windows/win32-def.mk + +include $(TOP_DIR)/builds/compiler/gcc-dev.mk + +# include linking instructions +include $(TOP_DIR)/builds/link_dos.mk + + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/windows/w32-gcc.mk b/3rdparty/freetype-2.13.2/builds/windows/w32-gcc.mk new file mode 100644 index 000000000..f37c185f5 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/w32-gcc.mk @@ -0,0 +1,31 @@ +# +# FreeType 2 configuration rules for Win32 + GCC +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + +# default definitions of the export list +# +EXPORTS_LIST = $(OBJ_DIR)/freetype.def +EXPORTS_OPTIONS = $(EXPORTS_LIST) +APINAMES_OPTIONS := -dfreetype.dll -w + +# include Win32-specific definitions +include $(TOP_DIR)/builds/windows/win32-def.mk + +# include gcc-specific definitions +include $(TOP_DIR)/builds/compiler/gcc.mk + +# include linking instructions +include $(TOP_DIR)/builds/link_dos.mk + + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/windows/w32-icc.mk b/3rdparty/freetype-2.13.2/builds/windows/w32-icc.mk new file mode 100644 index 000000000..cf51ccead --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/w32-icc.mk @@ -0,0 +1,28 @@ +# +# FreeType 2 configuration rules for Win32 + IBM Visual Age C++ +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + +# default definitions of the export list +# +EXPORTS_LIST = $(OBJ_DIR)/freetype.def +EXPORTS_OPTIONS = /DEF:$(EXPORTS_LIST) +APINAMES_OPTIONS := -dfreetype.dll -w + +include $(TOP_DIR)/builds/windows/win32-def.mk +include $(TOP_DIR)/builds/compiler/visualage.mk + +# include linking instructions +include $(TOP_DIR)/builds/link_dos.mk + + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/windows/w32-intl.mk b/3rdparty/freetype-2.13.2/builds/windows/w32-intl.mk new file mode 100644 index 000000000..0c16b4c84 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/w32-intl.mk @@ -0,0 +1,28 @@ +# +# FreeType 2 configuration rules for Intel C/C++ on Win32 +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + +# default definitions of the export list +# +EXPORTS_LIST = $(OBJ_DIR)/freetype.def +EXPORTS_OPTIONS = /DEF:$(EXPORTS_LIST) +APINAMES_OPTIONS := -dfreetype.dll -w + +include $(TOP_DIR)/builds/windows/win32-def.mk +include $(TOP_DIR)/builds/compiler/intelc.mk + +# include linking instructions +include $(TOP_DIR)/builds/link_dos.mk + + +# EOF diff --git a/src/font/freetype-2.10.2/src/winfonts/Jamfile b/3rdparty/freetype-2.13.2/builds/windows/w32-lcc.mk similarity index 57% rename from src/font/freetype-2.10.2/src/winfonts/Jamfile rename to 3rdparty/freetype-2.13.2/builds/windows/w32-lcc.mk index 4b7ce0715..0dd740e25 100644 --- a/src/font/freetype-2.10.2/src/winfonts/Jamfile +++ b/3rdparty/freetype-2.13.2/builds/windows/w32-lcc.mk @@ -1,6 +1,9 @@ -# FreeType 2 src/winfonts Jamfile # -# Copyright (C) 2001-2020 by +# FreeType 2 configuration rules for Win32 + LCC +# + + +# Copyright (C) 1996-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, @@ -9,8 +12,13 @@ # indicate that you have read the license and understand and accept it # fully. -SubDir FT2_TOP $(FT2_SRC_DIR) winfonts ; -Library $(FT2_LIB) : winfnt.c ; +SEP := / +include $(TOP_DIR)/builds/windows/win32-def.mk +include $(TOP_DIR)/builds/compiler/win-lcc.mk + +# include linking instructions +include $(TOP_DIR)/builds/link_dos.mk + +# EOF -# end of src/winfonts Jamfile diff --git a/3rdparty/freetype-2.13.2/builds/windows/w32-mingw32.mk b/3rdparty/freetype-2.13.2/builds/windows/w32-mingw32.mk new file mode 100644 index 000000000..dc323bd34 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/w32-mingw32.mk @@ -0,0 +1,33 @@ +# +# FreeType 2 configuration rules for mingw32 +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + +# default definitions of the export list +# +EXPORTS_LIST = $(OBJ_DIR)/freetype.def +EXPORTS_OPTIONS = $(EXPORTS_LIST) +APINAMES_OPTIONS := -dfreetype.dll -w + +# include Win32-specific definitions +include $(TOP_DIR)/builds/windows/win32-def.mk + +LIBRARY := lib$(PROJECT) + +# include gcc-specific definitions +include $(TOP_DIR)/builds/compiler/gcc.mk + +# include linking instructions +include $(TOP_DIR)/builds/link_dos.mk + + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/windows/w32-vcc.mk b/3rdparty/freetype-2.13.2/builds/windows/w32-vcc.mk new file mode 100644 index 000000000..eea7db8b5 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/w32-vcc.mk @@ -0,0 +1,28 @@ +# +# FreeType 2 Visual C++ on Win32 +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + +# definitions of the export list +# +EXPORTS_LIST = $(OBJ_DIR)/freetype.def +EXPORTS_OPTIONS = /DEF:$(EXPORTS_LIST) +APINAMES_OPTIONS := -dfreetype.dll -w + +include $(TOP_DIR)/builds/windows/win32-def.mk +include $(TOP_DIR)/builds/compiler/visualc.mk + +# include linking instructions +include $(TOP_DIR)/builds/link_dos.mk + + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/windows/w32-wat.mk b/3rdparty/freetype-2.13.2/builds/windows/w32-wat.mk new file mode 100644 index 000000000..5392d2a4b --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/w32-wat.mk @@ -0,0 +1,28 @@ +# +# FreeType 2 configuration rules for Watcom C/C++ +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + +# redefine export symbol definitions +# +EXPORTS_LIST = $(OBJ_DIR)/watcom-ftexports.lbc +EXPORTS_OPTIONS = -\"export @$(EXPORTS_LIST)\"- +APINAMES_OPTIONS := -wW + +include $(TOP_DIR)/builds/windows/win32-def.mk +include $(TOP_DIR)/builds/compiler/watcom.mk + +# include linking instructions +include $(TOP_DIR)/builds/link_dos.mk + + +# EOF diff --git a/3rdparty/freetype-2.13.2/builds/windows/win32-def.mk b/3rdparty/freetype-2.13.2/builds/windows/win32-def.mk new file mode 100644 index 000000000..324265132 --- /dev/null +++ b/3rdparty/freetype-2.13.2/builds/windows/win32-def.mk @@ -0,0 +1,51 @@ +# +# FreeType 2 Win32 specific definitions +# + + +# Copyright (C) 1996-2023 by +# David Turner, Robert Wilhelm, and Werner Lemberg. +# +# This file is part of the FreeType project, and may only be used, modified, +# and distributed under the terms of the FreeType project license, +# LICENSE.TXT. By continuing to use, modify, or distribute this file you +# indicate that you have read the license and understand and accept it +# fully. + + +DELETE := del +CAT := type +SEP := $(strip \ ) +PLATFORM_DIR := $(TOP_DIR)/builds/windows +PLATFORM := windows + +# This is used for `make refdoc' and `make refdoc-venv' +# +BIN := Scripts + +# The executable file extension (for tools). NOTE: WE INCLUDE THE DOT HERE !! +# +E := .exe +E_BUILD := .exe + + +# The directory where all library files are placed. +# +# By default, this is the same as $(OBJ_DIR); however, this can be changed +# to suit particular needs. +# +LIB_DIR := $(OBJ_DIR) + + +# The name of the final library file. Note that the DOS-specific Makefile +# uses a shorter (8.3) name. +# +LIBRARY := $(PROJECT) + + +# The NO_OUTPUT macro is used to ignore the output of commands. +# +NO_OUTPUT = 2> nul + + +# EOF diff --git a/3rdparty/freetype-2.13.2/devel/ft2build.h b/3rdparty/freetype-2.13.2/devel/ft2build.h new file mode 100644 index 000000000..82fdb30f6 --- /dev/null +++ b/3rdparty/freetype-2.13.2/devel/ft2build.h @@ -0,0 +1,41 @@ +/**************************************************************************** + * + * ft2build.h + * + * FreeType 2 build and setup macros (development version). + * + * Copyright (C) 1996-2023 by + * David Turner, Robert Wilhelm, and Werner Lemberg. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + + /* + * This is a development version of to build the library in + * debug mode. Its only difference to the default version is that it + * includes a local `ftoption.h' header file with different settings for + * many configuration macros. + * + * To use it, simply ensure that the directory containing this file is + * scanned by the compiler before the default FreeType header directory. + * + */ + +#ifndef FT2BUILD_H_ +#define FT2BUILD_H_ + +#define FT_CONFIG_MODULES_H +#define FT_CONFIG_OPTIONS_H + +#include + +#endif /* FT2BUILD_H_ */ + + +/* END */ diff --git a/3rdparty/freetype-2.13.2/devel/ftoption.h b/3rdparty/freetype-2.13.2/devel/ftoption.h new file mode 100644 index 000000000..da56abc5a --- /dev/null +++ b/3rdparty/freetype-2.13.2/devel/ftoption.h @@ -0,0 +1,1014 @@ +/**************************************************************************** + * + * ftoption.h (for development) + * + * User-selectable configuration macros (specification only). + * + * Copyright (C) 1996-2023 by + * David Turner, Robert Wilhelm, and Werner Lemberg. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + +#ifndef FTOPTION_H_ +#define FTOPTION_H_ + + +#include + + +FT_BEGIN_HEADER + + /************************************************************************** + * + * USER-SELECTABLE CONFIGURATION MACROS + * + * This file contains the default configuration macro definitions for a + * standard build of the FreeType library. There are three ways to use + * this file to build project-specific versions of the library: + * + * - You can modify this file by hand, but this is not recommended in + * cases where you would like to build several versions of the library + * from a single source directory. + * + * - You can put a copy of this file in your build directory, more + * precisely in `$BUILD/freetype/config/ftoption.h`, where `$BUILD` is + * the name of a directory that is included _before_ the FreeType include + * path during compilation. + * + * The default FreeType Makefiles use the build directory + * `builds/` by default, but you can easily change that for your + * own projects. + * + * - Copy the file to `$BUILD/ft2build.h` and modify it + * slightly to pre-define the macro `FT_CONFIG_OPTIONS_H` used to locate + * this file during the build. For example, + * + * ``` + * #define FT_CONFIG_OPTIONS_H + * #include + * ``` + * + * will use `$BUILD/myftoptions.h` instead of this file for macro + * definitions. + * + * Note also that you can similarly pre-define the macro + * `FT_CONFIG_MODULES_H` used to locate the file listing of the modules + * that are statically linked to the library at compile time. By + * default, this file is ``. + * + * We highly recommend using the third method whenever possible. + * + */ + + + /*************************************************************************/ + /*************************************************************************/ + /**** ****/ + /**** G E N E R A L F R E E T Y P E 2 C O N F I G U R A T I O N ****/ + /**** ****/ + /*************************************************************************/ + /*************************************************************************/ + + + /*#************************************************************************ + * + * If you enable this configuration option, FreeType recognizes an + * environment variable called `FREETYPE_PROPERTIES`, which can be used to + * control the various font drivers and modules. The controllable + * properties are listed in the section @properties. + * + * You have to undefine this configuration option on platforms that lack + * the concept of environment variables (and thus don't have the `getenv` + * function), for example Windows CE. + * + * `FREETYPE_PROPERTIES` has the following syntax form (broken here into + * multiple lines for better readability). + * + * ``` + * + * ':' + * '=' + * + * ':' + * '=' + * ... + * ``` + * + * Example: + * + * ``` + * FREETYPE_PROPERTIES=truetype:interpreter-version=35 \ + * cff:no-stem-darkening=1 + * ``` + * + */ +#define FT_CONFIG_OPTION_ENVIRONMENT_PROPERTIES + + + /************************************************************************** + * + * Uncomment the line below if you want to activate LCD rendering + * technology similar to ClearType in this build of the library. This + * technology triples the resolution in the direction color subpixels. To + * mitigate color fringes inherent to this technology, you also need to + * explicitly set up LCD filtering. + * + * When this macro is not defined, FreeType offers alternative LCD + * rendering technology that produces excellent output. + */ +/* #define FT_CONFIG_OPTION_SUBPIXEL_RENDERING */ + + + /************************************************************************** + * + * Many compilers provide a non-ANSI 64-bit data type that can be used by + * FreeType to speed up some computations. However, this will create some + * problems when compiling the library in strict ANSI mode. + * + * For this reason, the use of 64-bit integers is normally disabled when + * the `__STDC__` macro is defined. You can however disable this by + * defining the macro `FT_CONFIG_OPTION_FORCE_INT64` here. + * + * For most compilers, this will only create compilation warnings when + * building the library. + * + * ObNote: The compiler-specific 64-bit integers are detected in the + * file `ftconfig.h` either statically or through the `configure` + * script on supported platforms. + */ +#undef FT_CONFIG_OPTION_FORCE_INT64 + + + /************************************************************************** + * + * If this macro is defined, do not try to use an assembler version of + * performance-critical functions (e.g., @FT_MulFix). You should only do + * that to verify that the assembler function works properly, or to execute + * benchmark tests of the various implementations. + */ +/* #define FT_CONFIG_OPTION_NO_ASSEMBLER */ + + + /************************************************************************** + * + * If this macro is defined, try to use an inlined assembler version of the + * @FT_MulFix function, which is a 'hotspot' when loading and hinting + * glyphs, and which should be executed as fast as possible. + * + * Note that if your compiler or CPU is not supported, this will default to + * the standard and portable implementation found in `ftcalc.c`. + */ +#define FT_CONFIG_OPTION_INLINE_MULFIX + + + /************************************************************************** + * + * LZW-compressed file support. + * + * FreeType now handles font files that have been compressed with the + * `compress` program. This is mostly used to parse many of the PCF + * files that come with various X11 distributions. The implementation + * uses NetBSD's `zopen` to partially uncompress the file on the fly (see + * `src/lzw/ftgzip.c`). + * + * Define this macro if you want to enable this 'feature'. + */ +#define FT_CONFIG_OPTION_USE_LZW + + + /************************************************************************** + * + * Gzip-compressed file support. + * + * FreeType now handles font files that have been compressed with the + * `gzip` program. This is mostly used to parse many of the PCF files + * that come with XFree86. The implementation uses 'zlib' to partially + * uncompress the file on the fly (see `src/gzip/ftgzip.c`). + * + * Define this macro if you want to enable this 'feature'. See also the + * macro `FT_CONFIG_OPTION_SYSTEM_ZLIB` below. + */ +#define FT_CONFIG_OPTION_USE_ZLIB + + + /************************************************************************** + * + * ZLib library selection + * + * This macro is only used when `FT_CONFIG_OPTION_USE_ZLIB` is defined. + * It allows FreeType's 'ftgzip' component to link to the system's + * installation of the ZLib library. This is useful on systems like + * Unix or VMS where it generally is already available. + * + * If you let it undefined, the component will use its own copy of the + * zlib sources instead. These have been modified to be included + * directly within the component and **not** export external function + * names. This allows you to link any program with FreeType _and_ ZLib + * without linking conflicts. + * + * Do not `#undef` this macro here since the build system might define + * it for certain configurations only. + * + * If you use a build system like cmake or the `configure` script, + * options set by those programs have precedence, overwriting the value + * here with the configured one. + * + * If you use the GNU make build system directly (that is, without the + * `configure` script) and you define this macro, you also have to pass + * `SYSTEM_ZLIB=yes` as an argument to make. + */ +/* #define FT_CONFIG_OPTION_SYSTEM_ZLIB */ + + + /************************************************************************** + * + * Bzip2-compressed file support. + * + * FreeType now handles font files that have been compressed with the + * `bzip2` program. This is mostly used to parse many of the PCF files + * that come with XFree86. The implementation uses `libbz2` to partially + * uncompress the file on the fly (see `src/bzip2/ftbzip2.c`). Contrary + * to gzip, bzip2 currently is not included and need to use the system + * available bzip2 implementation. + * + * Define this macro if you want to enable this 'feature'. + * + * If you use a build system like cmake or the `configure` script, + * options set by those programs have precedence, overwriting the value + * here with the configured one. + */ +#define FT_CONFIG_OPTION_USE_BZIP2 + + + /************************************************************************** + * + * Define to disable the use of file stream functions and types, `FILE`, + * `fopen`, etc. Enables the use of smaller system libraries on embedded + * systems that have multiple system libraries, some with or without file + * stream support, in the cases where file stream support is not necessary + * such as memory loading of font files. + */ +/* #define FT_CONFIG_OPTION_DISABLE_STREAM_SUPPORT */ + + + /************************************************************************** + * + * PNG bitmap support. + * + * FreeType now handles loading color bitmap glyphs in the PNG format. + * This requires help from the external libpng library. Uncompressed + * color bitmaps do not need any external libraries and will be supported + * regardless of this configuration. + * + * Define this macro if you want to enable this 'feature'. + * + * If you use a build system like cmake or the `configure` script, + * options set by those programs have precedence, overwriting the value + * here with the configured one. + */ +#define FT_CONFIG_OPTION_USE_PNG + + + /************************************************************************** + * + * HarfBuzz support. + * + * FreeType uses the HarfBuzz library to improve auto-hinting of OpenType + * fonts. If available, many glyphs not directly addressable by a font's + * character map will be hinted also. + * + * Define this macro if you want to enable this 'feature'. + * + * If you use a build system like cmake or the `configure` script, + * options set by those programs have precedence, overwriting the value + * here with the configured one. + */ +#define FT_CONFIG_OPTION_USE_HARFBUZZ + + + /************************************************************************** + * + * Brotli support. + * + * FreeType uses the Brotli library to provide support for decompressing + * WOFF2 streams. + * + * Define this macro if you want to enable this 'feature'. + * + * If you use a build system like cmake or the `configure` script, + * options set by those programs have precedence, overwriting the value + * here with the configured one. + */ +#define FT_CONFIG_OPTION_USE_BROTLI + + + /************************************************************************** + * + * Glyph Postscript Names handling + * + * By default, FreeType 2 is compiled with the 'psnames' module. This + * module is in charge of converting a glyph name string into a Unicode + * value, or return a Macintosh standard glyph name for the use with the + * TrueType 'post' table. + * + * Undefine this macro if you do not want 'psnames' compiled in your + * build of FreeType. This has the following effects: + * + * - The TrueType driver will provide its own set of glyph names, if you + * build it to support postscript names in the TrueType 'post' table, + * but will not synthesize a missing Unicode charmap. + * + * - The Type~1 driver will not be able to synthesize a Unicode charmap + * out of the glyphs found in the fonts. + * + * You would normally undefine this configuration macro when building a + * version of FreeType that doesn't contain a Type~1 or CFF driver. + */ +#define FT_CONFIG_OPTION_POSTSCRIPT_NAMES + + + /************************************************************************** + * + * Postscript Names to Unicode Values support + * + * By default, FreeType~2 is built with the 'psnames' module compiled in. + * Among other things, the module is used to convert a glyph name into a + * Unicode value. This is especially useful in order to synthesize on + * the fly a Unicode charmap from the CFF/Type~1 driver through a big + * table named the 'Adobe Glyph List' (AGL). + * + * Undefine this macro if you do not want the Adobe Glyph List compiled + * in your 'psnames' module. The Type~1 driver will not be able to + * synthesize a Unicode charmap out of the glyphs found in the fonts. + */ +#define FT_CONFIG_OPTION_ADOBE_GLYPH_LIST + + + /************************************************************************** + * + * Support for Mac fonts + * + * Define this macro if you want support for outline fonts in Mac format + * (mac dfont, mac resource, macbinary containing a mac resource) on + * non-Mac platforms. + * + * Note that the 'FOND' resource isn't checked. + */ +#define FT_CONFIG_OPTION_MAC_FONTS + + + /************************************************************************** + * + * Guessing methods to access embedded resource forks + * + * Enable extra Mac fonts support on non-Mac platforms (e.g., GNU/Linux). + * + * Resource forks which include fonts data are stored sometimes in + * locations which users or developers don't expected. In some cases, + * resource forks start with some offset from the head of a file. In + * other cases, the actual resource fork is stored in file different from + * what the user specifies. If this option is activated, FreeType tries + * to guess whether such offsets or different file names must be used. + * + * Note that normal, direct access of resource forks is controlled via + * the `FT_CONFIG_OPTION_MAC_FONTS` option. + */ +#ifdef FT_CONFIG_OPTION_MAC_FONTS +#define FT_CONFIG_OPTION_GUESSING_EMBEDDED_RFORK +#endif + + + /************************************************************************** + * + * Allow the use of `FT_Incremental_Interface` to load typefaces that + * contain no glyph data, but supply it via a callback function. This is + * required by clients supporting document formats which supply font data + * incrementally as the document is parsed, such as the Ghostscript + * interpreter for the PostScript language. + */ +#define FT_CONFIG_OPTION_INCREMENTAL + + + /************************************************************************** + * + * The size in bytes of the render pool used by the scan-line converter to + * do all of its work. + */ +#define FT_RENDER_POOL_SIZE 16384L + + + /************************************************************************** + * + * FT_MAX_MODULES + * + * The maximum number of modules that can be registered in a single + * FreeType library object. 32~is the default. + */ +#define FT_MAX_MODULES 32 + + + /************************************************************************** + * + * Debug level + * + * FreeType can be compiled in debug or trace mode. In debug mode, + * errors are reported through the 'ftdebug' component. In trace mode, + * additional messages are sent to the standard output during execution. + * + * Define `FT_DEBUG_LEVEL_ERROR` to build the library in debug mode. + * Define `FT_DEBUG_LEVEL_TRACE` to build it in trace mode. + * + * Don't define any of these macros to compile in 'release' mode! + * + * Do not `#undef` these macros here since the build system might define + * them for certain configurations only. + */ +#define FT_DEBUG_LEVEL_ERROR +#define FT_DEBUG_LEVEL_TRACE + + + /************************************************************************** + * + * Logging + * + * Compiling FreeType in debug or trace mode makes FreeType write error + * and trace log messages to `stderr`. Enabling this macro + * automatically forces the `FT_DEBUG_LEVEL_ERROR` and + * `FT_DEBUG_LEVEL_TRACE` macros and allows FreeType to write error and + * trace log messages to a file instead of `stderr`. For writing logs + * to a file, FreeType uses an the external `dlg` library (the source + * code is in `src/dlg`). + * + * This option needs a C99 compiler. + */ +#define FT_DEBUG_LOGGING + + + /************************************************************************** + * + * Autofitter debugging + * + * If `FT_DEBUG_AUTOFIT` is defined, FreeType provides some means to + * control the autofitter behaviour for debugging purposes with global + * boolean variables (consequently, you should **never** enable this + * while compiling in 'release' mode): + * + * ``` + * af_debug_disable_horz_hints_ + * af_debug_disable_vert_hints_ + * af_debug_disable_blue_hints_ + * ``` + * + * Additionally, the following functions provide dumps of various + * internal autofit structures to stdout (using `printf`): + * + * ``` + * af_glyph_hints_dump_points + * af_glyph_hints_dump_segments + * af_glyph_hints_dump_edges + * af_glyph_hints_get_num_segments + * af_glyph_hints_get_segment_offset + * ``` + * + * As an argument, they use another global variable: + * + * ``` + * af_debug_hints_ + * ``` + * + * Please have a look at the `ftgrid` demo program to see how those + * variables and macros should be used. + * + * Do not `#undef` these macros here since the build system might define + * them for certain configurations only. + */ +#define FT_DEBUG_AUTOFIT + + + /************************************************************************** + * + * Memory Debugging + * + * FreeType now comes with an integrated memory debugger that is capable + * of detecting simple errors like memory leaks or double deletes. To + * compile it within your build of the library, you should define + * `FT_DEBUG_MEMORY` here. + * + * Note that the memory debugger is only activated at runtime when when + * the _environment_ variable `FT2_DEBUG_MEMORY` is defined also! + * + * Do not `#undef` this macro here since the build system might define it + * for certain configurations only. + */ +#define FT_DEBUG_MEMORY + + + /************************************************************************** + * + * Module errors + * + * If this macro is set (which is _not_ the default), the higher byte of + * an error code gives the module in which the error has occurred, while + * the lower byte is the real error code. + * + * Setting this macro makes sense for debugging purposes only, since it + * would break source compatibility of certain programs that use + * FreeType~2. + * + * More details can be found in the files `ftmoderr.h` and `fterrors.h`. + */ +#undef FT_CONFIG_OPTION_USE_MODULE_ERRORS + + + /************************************************************************** + * + * OpenType SVG Glyph Support + * + * Setting this macro enables support for OpenType SVG glyphs. By + * default, FreeType can only fetch SVG documents. However, it can also + * render them if external rendering hook functions are plugged in at + * runtime. + * + * More details on the hooks can be found in file `otsvg.h`. + */ +#define FT_CONFIG_OPTION_SVG + + + /************************************************************************** + * + * Error Strings + * + * If this macro is set, `FT_Error_String` will return meaningful + * descriptions. This is not enabled by default to reduce the overall + * size of FreeType. + * + * More details can be found in the file `fterrors.h`. + */ +/* #define FT_CONFIG_OPTION_ERROR_STRINGS */ + + + /*************************************************************************/ + /*************************************************************************/ + /**** ****/ + /**** S F N T D R I V E R C O N F I G U R A T I O N ****/ + /**** ****/ + /*************************************************************************/ + /*************************************************************************/ + + + /************************************************************************** + * + * Define `TT_CONFIG_OPTION_EMBEDDED_BITMAPS` if you want to support + * embedded bitmaps in all formats using the 'sfnt' module (namely + * TrueType~& OpenType). + */ +#define TT_CONFIG_OPTION_EMBEDDED_BITMAPS + + + /************************************************************************** + * + * Define `TT_CONFIG_OPTION_COLOR_LAYERS` if you want to support colored + * outlines (from the 'COLR'/'CPAL' tables) in all formats using the 'sfnt' + * module (namely TrueType~& OpenType). + */ +#define TT_CONFIG_OPTION_COLOR_LAYERS + + + /************************************************************************** + * + * Define `TT_CONFIG_OPTION_POSTSCRIPT_NAMES` if you want to be able to + * load and enumerate Postscript names of glyphs in a TrueType or OpenType + * file. + * + * Note that if you do not compile the 'psnames' module by undefining the + * above `FT_CONFIG_OPTION_POSTSCRIPT_NAMES` macro, the 'sfnt' module will + * contain additional code to read the PostScript name table from a font. + * + * (By default, the module uses 'psnames' to extract glyph names.) + */ +#define TT_CONFIG_OPTION_POSTSCRIPT_NAMES + + + /************************************************************************** + * + * Define `TT_CONFIG_OPTION_SFNT_NAMES` if your applications need to access + * the internal name table in a SFNT-based format like TrueType or + * OpenType. The name table contains various strings used to describe the + * font, like family name, copyright, version, etc. It does not contain + * any glyph name though. + * + * Accessing SFNT names is done through the functions declared in + * `ftsnames.h`. + */ +#define TT_CONFIG_OPTION_SFNT_NAMES + + + /************************************************************************** + * + * TrueType CMap support + * + * Here you can fine-tune which TrueType CMap table format shall be + * supported. + */ +#define TT_CONFIG_CMAP_FORMAT_0 +#define TT_CONFIG_CMAP_FORMAT_2 +#define TT_CONFIG_CMAP_FORMAT_4 +#define TT_CONFIG_CMAP_FORMAT_6 +#define TT_CONFIG_CMAP_FORMAT_8 +#define TT_CONFIG_CMAP_FORMAT_10 +#define TT_CONFIG_CMAP_FORMAT_12 +#define TT_CONFIG_CMAP_FORMAT_13 +#define TT_CONFIG_CMAP_FORMAT_14 + + + /*************************************************************************/ + /*************************************************************************/ + /**** ****/ + /**** T R U E T Y P E D R I V E R C O N F I G U R A T I O N ****/ + /**** ****/ + /*************************************************************************/ + /*************************************************************************/ + + /************************************************************************** + * + * Define `TT_CONFIG_OPTION_BYTECODE_INTERPRETER` if you want to compile a + * bytecode interpreter in the TrueType driver. + * + * By undefining this, you will only compile the code necessary to load + * TrueType glyphs without hinting. + * + * Do not `#undef` this macro here, since the build system might define it + * for certain configurations only. + */ +#define TT_CONFIG_OPTION_BYTECODE_INTERPRETER + + + /************************************************************************** + * + * Define `TT_CONFIG_OPTION_SUBPIXEL_HINTING` if you want to compile + * subpixel hinting support into the TrueType driver. This modifies the + * TrueType hinting mechanism when anything but `FT_RENDER_MODE_MONO` is + * requested. + * + * In particular, it modifies the bytecode interpreter to interpret (or + * not) instructions in a certain way so that all TrueType fonts look like + * they do in a Windows ClearType (DirectWrite) environment. See [1] for a + * technical overview on what this means. See `ttinterp.h` for more + * details on this option. + * + * The new default mode focuses on applying a minimal set of rules to all + * fonts indiscriminately so that modern and web fonts render well while + * legacy fonts render okay. The corresponding interpreter version is v40. + * The so-called Infinality mode (v38) is no longer available in FreeType. + * + * By undefining these, you get rendering behavior like on Windows without + * ClearType, i.e., Windows XP without ClearType enabled and Win9x + * (interpreter version v35). Or not, depending on how much hinting blood + * and testing tears the font designer put into a given font. If you + * define one or both subpixel hinting options, you can switch between + * between v35 and the ones you define (using `FT_Property_Set`). + * + * This option requires `TT_CONFIG_OPTION_BYTECODE_INTERPRETER` to be + * defined. + * + * [1] + * https://www.microsoft.com/typography/cleartype/truetypecleartype.aspx + */ +#define TT_CONFIG_OPTION_SUBPIXEL_HINTING + + + /************************************************************************** + * + * Define `TT_CONFIG_OPTION_COMPONENT_OFFSET_SCALED` to compile the + * TrueType glyph loader to use Apple's definition of how to handle + * component offsets in composite glyphs. + * + * Apple and MS disagree on the default behavior of component offsets in + * composites. Apple says that they should be scaled by the scaling + * factors in the transformation matrix (roughly, it's more complex) while + * MS says they should not. OpenType defines two bits in the composite + * flags array which can be used to disambiguate, but old fonts will not + * have them. + * + * https://www.microsoft.com/typography/otspec/glyf.htm + * https://developer.apple.com/fonts/TrueType-Reference-Manual/RM06/Chap6glyf.html + */ +#undef TT_CONFIG_OPTION_COMPONENT_OFFSET_SCALED + + + /************************************************************************** + * + * Define `TT_CONFIG_OPTION_GX_VAR_SUPPORT` if you want to include support + * for Apple's distortable font technology ('fvar', 'gvar', 'cvar', and + * 'avar' tables). Tagged 'Font Variations', this is now part of OpenType + * also. This has many similarities to Type~1 Multiple Masters support. + */ +#define TT_CONFIG_OPTION_GX_VAR_SUPPORT + + + /************************************************************************** + * + * Define `TT_CONFIG_OPTION_NO_BORING_EXPANSION` if you want to exclude + * support for 'boring' OpenType specification expansions. + * + * https://github.com/harfbuzz/boring-expansion-spec + * + * Right now, the following features are covered: + * + * - 'avar' version 2.0 + * + * Most likely, this is a temporary configuration option to be removed in + * the near future, since it is assumed that eventually those features are + * added to the OpenType standard. + */ +/* #define TT_CONFIG_OPTION_NO_BORING_EXPANSION */ + + + /************************************************************************** + * + * Define `TT_CONFIG_OPTION_BDF` if you want to include support for an + * embedded 'BDF~' table within SFNT-based bitmap formats. + */ +#define TT_CONFIG_OPTION_BDF + + + /************************************************************************** + * + * Option `TT_CONFIG_OPTION_MAX_RUNNABLE_OPCODES` controls the maximum + * number of bytecode instructions executed for a single run of the + * bytecode interpreter, needed to prevent infinite loops. You don't want + * to change this except for very special situations (e.g., making a + * library fuzzer spend less time to handle broken fonts). + * + * It is not expected that this value is ever modified by a configuring + * script; instead, it gets surrounded with `#ifndef ... #endif` so that + * the value can be set as a preprocessor option on the compiler's command + * line. + */ +#ifndef TT_CONFIG_OPTION_MAX_RUNNABLE_OPCODES +#define TT_CONFIG_OPTION_MAX_RUNNABLE_OPCODES 1000000L +#endif + + + /*************************************************************************/ + /*************************************************************************/ + /**** ****/ + /**** T Y P E 1 D R I V E R C O N F I G U R A T I O N ****/ + /**** ****/ + /*************************************************************************/ + /*************************************************************************/ + + + /************************************************************************** + * + * `T1_MAX_DICT_DEPTH` is the maximum depth of nest dictionaries and arrays + * in the Type~1 stream (see `t1load.c`). A minimum of~4 is required. + */ +#define T1_MAX_DICT_DEPTH 5 + + + /************************************************************************** + * + * `T1_MAX_SUBRS_CALLS` details the maximum number of nested sub-routine + * calls during glyph loading. + */ +#define T1_MAX_SUBRS_CALLS 16 + + + /************************************************************************** + * + * `T1_MAX_CHARSTRING_OPERANDS` is the charstring stack's capacity. A + * minimum of~16 is required. + * + * The Chinese font 'MingTiEG-Medium' (covering the CNS 11643 character + * set) needs 256. + */ +#define T1_MAX_CHARSTRINGS_OPERANDS 256 + + + /************************************************************************** + * + * Define this configuration macro if you want to prevent the compilation + * of the 't1afm' module, which is in charge of reading Type~1 AFM files + * into an existing face. Note that if set, the Type~1 driver will be + * unable to produce kerning distances. + */ +#undef T1_CONFIG_OPTION_NO_AFM + + + /************************************************************************** + * + * Define this configuration macro if you want to prevent the compilation + * of the Multiple Masters font support in the Type~1 driver. + */ +#undef T1_CONFIG_OPTION_NO_MM_SUPPORT + + + /************************************************************************** + * + * `T1_CONFIG_OPTION_OLD_ENGINE` controls whether the pre-Adobe Type~1 + * engine gets compiled into FreeType. If defined, it is possible to + * switch between the two engines using the `hinting-engine` property of + * the 'type1' driver module. + */ +#define T1_CONFIG_OPTION_OLD_ENGINE + + + /*************************************************************************/ + /*************************************************************************/ + /**** ****/ + /**** C F F D R I V E R C O N F I G U R A T I O N ****/ + /**** ****/ + /*************************************************************************/ + /*************************************************************************/ + + + /************************************************************************** + * + * Using `CFF_CONFIG_OPTION_DARKENING_PARAMETER_{X,Y}{1,2,3,4}` it is + * possible to set up the default values of the four control points that + * define the stem darkening behaviour of the (new) CFF engine. For more + * details please read the documentation of the `darkening-parameters` + * property (file `ftdriver.h`), which allows the control at run-time. + * + * Do **not** undefine these macros! + */ +#define CFF_CONFIG_OPTION_DARKENING_PARAMETER_X1 500 +#define CFF_CONFIG_OPTION_DARKENING_PARAMETER_Y1 400 + +#define CFF_CONFIG_OPTION_DARKENING_PARAMETER_X2 1000 +#define CFF_CONFIG_OPTION_DARKENING_PARAMETER_Y2 275 + +#define CFF_CONFIG_OPTION_DARKENING_PARAMETER_X3 1667 +#define CFF_CONFIG_OPTION_DARKENING_PARAMETER_Y3 275 + +#define CFF_CONFIG_OPTION_DARKENING_PARAMETER_X4 2333 +#define CFF_CONFIG_OPTION_DARKENING_PARAMETER_Y4 0 + + + /************************************************************************** + * + * `CFF_CONFIG_OPTION_OLD_ENGINE` controls whether the pre-Adobe CFF engine + * gets compiled into FreeType. If defined, it is possible to switch + * between the two engines using the `hinting-engine` property of the 'cff' + * driver module. + */ +#define CFF_CONFIG_OPTION_OLD_ENGINE + + + /*************************************************************************/ + /*************************************************************************/ + /**** ****/ + /**** P C F D R I V E R C O N F I G U R A T I O N ****/ + /**** ****/ + /*************************************************************************/ + /*************************************************************************/ + + + /************************************************************************** + * + * There are many PCF fonts just called 'Fixed' which look completely + * different, and which have nothing to do with each other. When selecting + * 'Fixed' in KDE or Gnome one gets results that appear rather random, the + * style changes often if one changes the size and one cannot select some + * fonts at all. This option makes the 'pcf' module prepend the foundry + * name (plus a space) to the family name. + * + * We also check whether we have 'wide' characters; all put together, we + * get family names like 'Sony Fixed' or 'Misc Fixed Wide'. + * + * If this option is activated, it can be controlled with the + * `no-long-family-names` property of the 'pcf' driver module. + */ +#define PCF_CONFIG_OPTION_LONG_FAMILY_NAMES + + + /*************************************************************************/ + /*************************************************************************/ + /**** ****/ + /**** A U T O F I T M O D U L E C O N F I G U R A T I O N ****/ + /**** ****/ + /*************************************************************************/ + /*************************************************************************/ + + + /************************************************************************** + * + * Compile 'autofit' module with CJK (Chinese, Japanese, Korean) script + * support. + */ +#define AF_CONFIG_OPTION_CJK + + + /************************************************************************** + * + * Compile 'autofit' module with fallback Indic script support, covering + * some scripts that the 'latin' submodule of the 'autofit' module doesn't + * (yet) handle. Currently, this needs option `AF_CONFIG_OPTION_CJK`. + */ +#ifdef AF_CONFIG_OPTION_CJK +#define AF_CONFIG_OPTION_INDIC +#endif + + + /************************************************************************** + * + * Use TrueType-like size metrics for 'light' auto-hinting. + * + * It is strongly recommended to avoid this option, which exists only to + * help some legacy applications retain its appearance and behaviour with + * respect to auto-hinted TrueType fonts. + * + * The very reason this option exists at all are GNU/Linux distributions + * like Fedora that did not un-patch the following change (which was + * present in FreeType between versions 2.4.6 and 2.7.1, inclusive). + * + * ``` + * 2011-07-16 Steven Chu + * + * [truetype] Fix metrics on size request for scalable fonts. + * ``` + * + * This problematic commit is now reverted (more or less). + */ +/* #define AF_CONFIG_OPTION_TT_SIZE_METRICS */ + + /* */ + + + /* + * This macro is obsolete. Support has been removed in FreeType version + * 2.5. + */ +/* #define FT_CONFIG_OPTION_OLD_INTERNALS */ + + + /* + * The next two macros are defined if native TrueType hinting is + * requested by the definitions above. Don't change this. + */ +#ifdef TT_CONFIG_OPTION_BYTECODE_INTERPRETER +#define TT_USE_BYTECODE_INTERPRETER +#ifdef TT_CONFIG_OPTION_SUBPIXEL_HINTING +#define TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL +#endif +#endif + + + /* + * The TT_SUPPORT_COLRV1 macro is defined to indicate to clients that this + * version of FreeType has support for 'COLR' v1 API. This definition is + * useful to FreeType clients that want to build in support for 'COLR' v1 + * depending on a tip-of-tree checkout before it is officially released in + * FreeType, and while the feature cannot yet be tested against using + * version macros. Don't change this macro. This may be removed once the + * feature is in a FreeType release version and version macros can be used + * to test for availability. + */ +#ifdef TT_CONFIG_OPTION_COLOR_LAYERS +#define TT_SUPPORT_COLRV1 +#endif + + + /* + * Check CFF darkening parameters. The checks are the same as in function + * `cff_property_set` in file `cffdrivr.c`. + */ +#if CFF_CONFIG_OPTION_DARKENING_PARAMETER_X1 < 0 || \ + CFF_CONFIG_OPTION_DARKENING_PARAMETER_X2 < 0 || \ + CFF_CONFIG_OPTION_DARKENING_PARAMETER_X3 < 0 || \ + CFF_CONFIG_OPTION_DARKENING_PARAMETER_X4 < 0 || \ + \ + CFF_CONFIG_OPTION_DARKENING_PARAMETER_Y1 < 0 || \ + CFF_CONFIG_OPTION_DARKENING_PARAMETER_Y2 < 0 || \ + CFF_CONFIG_OPTION_DARKENING_PARAMETER_Y3 < 0 || \ + CFF_CONFIG_OPTION_DARKENING_PARAMETER_Y4 < 0 || \ + \ + CFF_CONFIG_OPTION_DARKENING_PARAMETER_X1 > \ + CFF_CONFIG_OPTION_DARKENING_PARAMETER_X2 || \ + CFF_CONFIG_OPTION_DARKENING_PARAMETER_X2 > \ + CFF_CONFIG_OPTION_DARKENING_PARAMETER_X3 || \ + CFF_CONFIG_OPTION_DARKENING_PARAMETER_X3 > \ + CFF_CONFIG_OPTION_DARKENING_PARAMETER_X4 || \ + \ + CFF_CONFIG_OPTION_DARKENING_PARAMETER_Y1 > 500 || \ + CFF_CONFIG_OPTION_DARKENING_PARAMETER_Y2 > 500 || \ + CFF_CONFIG_OPTION_DARKENING_PARAMETER_Y3 > 500 || \ + CFF_CONFIG_OPTION_DARKENING_PARAMETER_Y4 > 500 +#error "Invalid CFF darkening parameters!" +#endif + + +FT_END_HEADER + +#endif /* FTOPTION_H_ */ + + +/* END */ diff --git a/3rdparty/freetype-2.13.2/include/dlg/dlg.h b/3rdparty/freetype-2.13.2/include/dlg/dlg.h new file mode 100644 index 000000000..fa10730e8 --- /dev/null +++ b/3rdparty/freetype-2.13.2/include/dlg/dlg.h @@ -0,0 +1,290 @@ +// Copyright (c) 2019 nyorain +// Distributed under the Boost Software License, Version 1.0. +// See accompanying file LICENSE or copy at http://www.boost.org/LICENSE_1_0.txt + +#ifndef INC_DLG_DLG_H_ +#define INC_DLG_DLG_H_ + +#include +#include +#include +#include +#include + +// Hosted at https://github.com/nyorain/dlg. +// There are examples and documentation. +// Issue reports and contributions appreciated. + +// - CONFIG - +// Define this macro to make all dlg macros have no effect at all +// #define DLG_DISABLE + +// the log/assertion levels below which logs/assertions are ignored +// defaulted depending on the NDEBUG macro +#ifndef DLG_LOG_LEVEL + #ifdef NDEBUG + #define DLG_LOG_LEVEL dlg_level_warn + #else + #define DLG_LOG_LEVEL dlg_level_trace + #endif +#endif + +#ifndef DLG_ASSERT_LEVEL + #ifdef NDEBUG + #define DLG_ASSERT_LEVEL dlg_level_warn + #else + #define DLG_ASSERT_LEVEL dlg_level_trace + #endif +#endif + +// the assert level of dlg_assert +#ifndef DLG_DEFAULT_ASSERT + #define DLG_DEFAULT_ASSERT dlg_level_error +#endif + +// evaluated to the 'file' member in dlg_origin +#ifndef DLG_FILE + #define DLG_FILE dlg__strip_root_path(__FILE__, DLG_BASE_PATH) + + // the base path stripped from __FILE__. If you don't override DLG_FILE set this to + // the project root to make 'main.c' from '/some/bullshit/main.c' + #ifndef DLG_BASE_PATH + #define DLG_BASE_PATH "" + #endif +#endif + +// Default tags applied to all logs/assertions (in the defining file). +// Must be in format ```#define DLG_DEFAULT_TAGS "tag1", "tag2"``` +// or just nothing (as defaulted here) +#ifndef DLG_DEFAULT_TAGS + #define DLG_DEFAULT_TAGS_TERM NULL +#else + #define DLG_DEFAULT_TAGS_TERM DLG_DEFAULT_TAGS, NULL +#endif + +// The function used for formatting. Can have any signature, but must be callable with +// the arguments the log/assertions macros are called with. Must return a const char* +// that will not be freed by dlg, the formatting function must keep track of it. +// The formatting function might use dlg_thread_buffer or a custom owned buffer. +// The returned const char* has to be valid until the dlg log/assertion ends. +// Usually a c function with ... (i.e. using va_list) or a variadic c++ template do +// allow formatting. +#ifndef DLG_FMT_FUNC + #define DLG_FMT_FUNC dlg__printf_format +#endif + +// Only overwrite (i.e. predefine) this if you know what you are doing. +// On windows this is used to add the dllimport specified. +// If you are using the static version of dlg (on windows) define +// DLG_STATIC before including dlg.h +#ifndef DLG_API + #if (defined(_WIN32) || defined(__CYGWIN__)) && !defined(DLG_STATIC) + #define DLG_API __declspec(dllimport) + #else + #define DLG_API + #endif +#endif + +// This macro is used when an assertion fails. It gets the source expression +// and can return an alternative (that must stay alive). +// Mainly useful to execute something on failed assertion. +#ifndef DLG_FAILED_ASSERTION_TEXT + #define DLG_FAILED_ASSERTION_TEXT(x) x +#endif + +// - utility - +// two methods needed since cplusplus does not support compound literals +// and c does not support uniform initialization/initializer lists +#ifdef __cplusplus + #include + #define DLG_CREATE_TAGS(...) std::initializer_list \ + {DLG_DEFAULT_TAGS_TERM, __VA_ARGS__, NULL}.begin() +#else + #define DLG_CREATE_TAGS(...) (const char* const[]) {DLG_DEFAULT_TAGS_TERM, __VA_ARGS__, NULL} +#endif + +#ifdef __GNUC__ + #define DLG_PRINTF_ATTRIB(a, b) __attribute__ ((format (printf, a, b))) +#else + #define DLG_PRINTF_ATTRIB(a, b) +#endif + +#ifdef __cplusplus +extern "C" { +#endif + + +// Represents the importance of a log/assertion call. +enum dlg_level { + dlg_level_trace = 0, // temporary used debug, e.g. to check if control reaches function + dlg_level_debug, // general debugging, prints e.g. all major events + dlg_level_info, // general useful information + dlg_level_warn, // warning, something went wrong but might have no (really bad) side effect + dlg_level_error, // something really went wrong; expect serious issues + dlg_level_fatal // critical error; application is likely to crash/exit +}; + +// Holds various information associated with a log/assertion call. +// Forwarded to the output handler. +struct dlg_origin { + const char* file; + unsigned int line; + const char* func; + enum dlg_level level; + const char** tags; // null-terminated + const char* expr; // assertion expression, otherwise null +}; + +// Type of the output handler, see dlg_set_handler. +typedef void(*dlg_handler)(const struct dlg_origin* origin, const char* string, void* data); + +#ifndef DLG_DISABLE + // Tagged/Untagged logging with variable level + // Tags must always be in the format `("tag1", "tag2")` (including brackets) + // Example usages: + // dlg_log(dlg_level_warning, "test 1") + // dlg_logt(("tag1, "tag2"), dlg_level_debug, "test %d", 2) + #define dlg_log(level, ...) if(level >= DLG_LOG_LEVEL) \ + dlg__do_log(level, DLG_CREATE_TAGS(NULL), DLG_FILE, __LINE__, __func__, \ + DLG_FMT_FUNC(__VA_ARGS__), NULL) + #define dlg_logt(level, tags, ...) if(level >= DLG_LOG_LEVEL) \ + dlg__do_log(level, DLG_CREATE_TAGS tags, DLG_FILE, __LINE__, __func__, \ + DLG_FMT_FUNC(__VA_ARGS__), NULL) + + // Dynamic level assert macros in various versions for additional arguments + // Example usages: + // dlg_assertl(dlg_level_warning, data != nullptr); + // dlg_assertlt(("tag1, "tag2"), dlg_level_trace, data != nullptr); + // dlg_asserttlm(("tag1), dlg_level_warning, data != nullptr, "Data must not be null"); + // dlg_assertlm(dlg_level_error, data != nullptr, "Data must not be null"); + #define dlg_assertl(level, expr) if(level >= DLG_ASSERT_LEVEL && !(expr)) \ + dlg__do_log(level, DLG_CREATE_TAGS(NULL), DLG_FILE, __LINE__, __func__, NULL, \ + DLG_FAILED_ASSERTION_TEXT(#expr)) + #define dlg_assertlt(level, tags, expr) if(level >= DLG_ASSERT_LEVEL && !(expr)) \ + dlg__do_log(level, DLG_CREATE_TAGS tags, DLG_FILE, __LINE__, __func__, NULL, \ + DLG_FAILED_ASSERTION_TEXT(#expr)) + #define dlg_assertlm(level, expr, ...) if(level >= DLG_ASSERT_LEVEL && !(expr)) \ + dlg__do_log(level, DLG_CREATE_TAGS(NULL), DLG_FILE, __LINE__, __func__, \ + DLG_FMT_FUNC(__VA_ARGS__), DLG_FAILED_ASSERTION_TEXT(#expr)) + #define dlg_assertltm(level, tags, expr, ...) if(level >= DLG_ASSERT_LEVEL && !(expr)) \ + dlg__do_log(level, DLG_CREATE_TAGS tags, DLG_FILE, __LINE__, \ + __func__, DLG_FMT_FUNC(__VA_ARGS__), DLG_FAILED_ASSERTION_TEXT(#expr)) + + #define dlg__assert_or(level, tags, expr, code, msg) if(!(expr)) {\ + if(level >= DLG_ASSERT_LEVEL) \ + dlg__do_log(level, tags, DLG_FILE, __LINE__, __func__, msg, \ + DLG_FAILED_ASSERTION_TEXT(#expr)); \ + code; \ + } (void) NULL + + // - Private interface: not part of the abi/api but needed in macros - + // Formats the given format string and arguments as printf would, uses the thread buffer. + DLG_API const char* dlg__printf_format(const char* format, ...) DLG_PRINTF_ATTRIB(1, 2); + DLG_API void dlg__do_log(enum dlg_level lvl, const char* const*, const char*, int, + const char*, const char*, const char*); + DLG_API const char* dlg__strip_root_path(const char* file, const char* base); + +#else // DLG_DISABLE + + #define dlg_log(level, ...) + #define dlg_logt(level, tags, ...) + + #define dlg_assertl(level, expr) // assert without tags/message + #define dlg_assertlt(level, tags, expr) // assert with tags + #define dlg_assertlm(level, expr, ...) // assert with message + #define dlg_assertltm(level, tags, expr, ...) // assert with tags & message + + #define dlg__assert_or(level, tags, expr, code, msg) if(!(expr)) { code; } (void) NULL +#endif // DLG_DISABLE + +// The API below is independent from DLG_DISABLE + +// Sets the handler that is responsible for formatting and outputting log calls. +// This function is not thread safe and the handler is set globally. +// The handler itself must not change dlg tags or call a dlg macro (if it +// does so, the provided string or tags array in 'origin' might get invalid). +// The handler can also be used for various other things such as dealing +// with failed assertions or filtering calls based on the passed tags. +// The default handler is dlg_default_output (see its doc for more info). +// If using c++ make sure the registered handler cannot throw e.g. by +// wrapping everything into a try-catch blog. +DLG_API void dlg_set_handler(dlg_handler handler, void* data); + +// The default output handler. +// Only use this to reset the output handler, prefer to use +// dlg_generic_output (from output.h) which this function simply calls. +// It also flushes the stream used and correctly outputs even from multiple threads. +DLG_API void dlg_default_output(const struct dlg_origin*, const char* string, void*); + +// Returns the currently active dlg handler and sets `data` to +// its user data pointer. `data` must not be NULL. +// Useful to create handler chains. +// This function is not threadsafe, i.e. retrieving the handler while +// changing it from another thread is unsafe. +// See `dlg_set_handler`. +DLG_API dlg_handler dlg_get_handler(void** data); + +// Adds the given tag associated with the given function to the thread specific list. +// If func is not NULL the tag will only applied to calls from the same function. +// Remove the tag again calling dlg_remove_tag (with exactly the same pointers!). +// Does not check if the tag is already present. +DLG_API void dlg_add_tag(const char* tag, const char* func); + +// Removes a tag added with dlg_add_tag (has no effect for tags no present). +// The pointers must be exactly the same pointers that were supplied to dlg_add_tag, +// this function will not check using strcmp. When the same tag/func combination +// is added multiple times, this function remove exactly one candidate, it is +// undefined which. Returns whether a tag was found (and removed). +DLG_API bool dlg_remove_tag(const char* tag, const char* func); + +// Returns the thread-specific buffer and its size for dlg. +// The buffer should only be used by formatting functions. +// The buffer can be reallocated and the size changed, just make sure +// to update both values correctly. +DLG_API char** dlg_thread_buffer(size_t** size); + +// Untagged leveled logging +#define dlg_trace(...) dlg_log(dlg_level_trace, __VA_ARGS__) +#define dlg_debug(...) dlg_log(dlg_level_debug, __VA_ARGS__) +#define dlg_info(...) dlg_log(dlg_level_info, __VA_ARGS__) +#define dlg_warn(...) dlg_log(dlg_level_warn, __VA_ARGS__) +#define dlg_error(...) dlg_log(dlg_level_error, __VA_ARGS__) +#define dlg_fatal(...) dlg_log(dlg_level_fatal, __VA_ARGS__) + +// Tagged leveled logging +#define dlg_tracet(tags, ...) dlg_logt(dlg_level_trace, tags, __VA_ARGS__) +#define dlg_debugt(tags, ...) dlg_logt(dlg_level_debug, tags, __VA_ARGS__) +#define dlg_infot(tags, ...) dlg_logt(dlg_level_info, tags, __VA_ARGS__) +#define dlg_warnt(tags, ...) dlg_logt(dlg_level_warn, tags, __VA_ARGS__) +#define dlg_errort(tags, ...) dlg_logt(dlg_level_error, tags, __VA_ARGS__) +#define dlg_fatalt(tags, ...) dlg_logt(dlg_level_fatal, tags, __VA_ARGS__) + +// Assert macros useing DLG_DEFAULT_ASSERT as level +#define dlg_assert(expr) dlg_assertl(DLG_DEFAULT_ASSERT, expr) +#define dlg_assertt(tags, expr) dlg_assertlt(DLG_DEFAULT_ASSERT, tags, expr) +#define dlg_assertm(expr, ...) dlg_assertlm(DLG_DEFAULT_ASSERT, expr, __VA_ARGS__) +#define dlg_asserttm(tags, expr, ...) dlg_assertltm(DLG_DEFAULT_ASSERT, tags, expr, __VA_ARGS__) + +// If (expr) does not evaluate to true, always executes 'code' (no matter what +// DLG_ASSERT_LEVEL is or if dlg is disabled or not). +// When dlg is enabled and the level is greater or equal to DLG_ASSERT_LEVEL, +// logs the failed assertion. +// Example usages: +// dlg_assertl_or(dlg_level_warn, data != nullptr, return); +// dlg_assertlm_or(dlg_level_fatal, data != nullptr, return, "Data must not be null"); +// dlg_assert_or(data != nullptr, logError(); return false); +#define dlg_assertltm_or(level, tags, expr, code, ...) dlg__assert_or(level, \ + DLG_CREATE_TAGS tags, expr, code, DLG_FMT_FUNC(__VA_ARGS__)) +#define dlg_assertlm_or(level, expr, code, ...) dlg__assert_or(level, \ + DLG_CREATE_TAGS(NULL), expr, code, DLG_FMT_FUNC(__VA_ARGS__)) +#define dlg_assertl_or(level, expr, code) dlg__assert_or(level, \ + DLG_CREATE_TAGS(NULL), expr, code, NULL) + +#define dlg_assert_or(expr, code) dlg_assertl_or(DLG_DEFAULT_ASSERT, expr, code) +#define dlg_assertm_or(expr, code, ...) dlg_assertlm_or(DLG_DEFAULT_ASSERT, expr, code, __VA_ARGS__) + +#ifdef __cplusplus +} +#endif + +#endif // header guard diff --git a/3rdparty/freetype-2.13.2/include/dlg/output.h b/3rdparty/freetype-2.13.2/include/dlg/output.h new file mode 100644 index 000000000..453e4a561 --- /dev/null +++ b/3rdparty/freetype-2.13.2/include/dlg/output.h @@ -0,0 +1,172 @@ +// Copyright (c) 2019 nyorain +// Distributed under the Boost Software License, Version 1.0. +// See accompanying file LICENSE or copy at http://www.boost.org/LICENSE_1_0.txt + +#ifndef INC_DLG_OUTPUT_H_ +#define INC_DLG_OUTPUT_H_ + +#include +#include + +#ifdef __cplusplus +extern "C" { +#endif + +// Text style +enum dlg_text_style { + dlg_text_style_reset = 0, + dlg_text_style_bold = 1, + dlg_text_style_dim = 2, + dlg_text_style_italic = 3, + dlg_text_style_underline = 4, + dlg_text_style_blink = 5, + dlg_text_style_rblink = 6, + dlg_text_style_reversed = 7, + dlg_text_style_conceal = 8, + dlg_text_style_crossed = 9, + dlg_text_style_none, +}; + +// Text color +enum dlg_color { + dlg_color_black = 0, + dlg_color_red, + dlg_color_green, + dlg_color_yellow, + dlg_color_blue, + dlg_color_magenta, + dlg_color_cyan, + dlg_color_gray, + dlg_color_reset = 9, + + dlg_color_black2 = 60, + dlg_color_red2, + dlg_color_green2, + dlg_color_yellow2, + dlg_color_blue2, + dlg_color_magenta2, + dlg_color_cyan2, + dlg_color_gray2, + + dlg_color_none = 69, +}; + +struct dlg_style { + enum dlg_text_style style; + enum dlg_color fg; + enum dlg_color bg; +}; + +// Like fprintf but fixes utf-8 output to console on windows. +// On non-windows sytems just uses the corresponding standard library +// functions. On windows, if dlg was compiled with the win_console option, +// will first try to output it in a way that allows the default console +// to display utf-8. If that fails, will fall back to the standard +// library functions. +DLG_API int dlg_fprintf(FILE* stream, const char* format, ...) DLG_PRINTF_ATTRIB(2, 3); +DLG_API int dlg_vfprintf(FILE* stream, const char* format, va_list list); + +// Like dlg_printf, but also applies the given style to this output. +// The style will always be applied (using escape sequences), independent of the given stream. +// On windows escape sequences don't work out of the box, see dlg_win_init_ansi(). +DLG_API int dlg_styled_fprintf(FILE* stream, struct dlg_style style, + const char* format, ...) DLG_PRINTF_ATTRIB(3, 4); + +// Features to output from the generic output handler. +// Some features might have only an effect in the specializations. +enum dlg_output_feature { + dlg_output_tags = 1, // output tags list + dlg_output_time = 2, // output time of log call (hour:minute:second) + dlg_output_style = 4, // whether to use the supplied styles + dlg_output_func = 8, // output function + dlg_output_file_line = 16, // output file:line, + dlg_output_newline = 32, // output a newline at the end + dlg_output_threadsafe = 64, // locks stream before printing + dlg_output_time_msecs = 128 // output micro seconds (ms on windows) +}; + +// The default level-dependent output styles. The array values represent the styles +// to be used for the associated level (i.e. [0] for trace level). +DLG_API extern const struct dlg_style dlg_default_output_styles[6]; + +// Generic output function. Used by the default output handler and might be useful +// for custom output handlers (that don't want to manually format the output). +// Will call the given output func with the given data (and format + args to print) +// for everything it has to print in printf format. +// See also the *_stream and *_buf specializations for common usage. +// The given output function must not be NULL. +typedef void(*dlg_generic_output_handler)(void* data, const char* format, ...); +DLG_API void dlg_generic_output(dlg_generic_output_handler output, void* data, + unsigned int features, const struct dlg_origin* origin, const char* string, + const struct dlg_style styles[6]); + +// Generic output function, using a format string instead of feature flags. +// Use following conversion characters: +// %h - output the time in H:M:S format +// %m - output the time in milliseconds +// %t - output the full list of tags, comma separated +// %f - output the function name noted in the origin +// %o - output the file:line of the origin +// %s - print the appropriate style escape sequence. +// %r - print the escape sequence to reset the style. +// %c - The content of the log/assert +// %% - print the '%' character +// Only the above specified conversion characters are valid, the rest are +// written as it is. +DLG_API void dlg_generic_outputf(dlg_generic_output_handler output, void* data, + const char* format_string, const struct dlg_origin* origin, + const char* string, const struct dlg_style styles[6]); + +// Generic output function. Used by the default output handler and might be useful +// for custom output handlers (that don't want to manually format the output). +// If stream is NULL uses stdout. +// Automatically uses dlg_fprintf to assure correct utf-8 even on windows consoles. +// Locks the stream (i.e. assures threadsafe access) when the associated feature +// is passed (note that stdout/stderr might still mix from multiple threads). +DLG_API void dlg_generic_output_stream(FILE* stream, unsigned int features, + const struct dlg_origin* origin, const char* string, + const struct dlg_style styles[6]); +DLG_API void dlg_generic_outputf_stream(FILE* stream, const char* format_string, + const struct dlg_origin* origin, const char* string, + const struct dlg_style styles[6], bool lock_stream); + +// Generic output function (see dlg_generic_output) that uses a buffer instead of +// a stream. buf must at least point to *size bytes. Will set *size to the number +// of bytes written (capped to the given size), if buf == NULL will set *size +// to the needed size. The size parameter must not be NULL. +DLG_API void dlg_generic_output_buf(char* buf, size_t* size, unsigned int features, + const struct dlg_origin* origin, const char* string, + const struct dlg_style styles[6]); +DLG_API void dlg_generic_outputf_buf(char* buf, size_t* size, const char* format_string, + const struct dlg_origin* origin, const char* string, + const struct dlg_style styles[6]); + +// Returns if the given stream is a tty. Useful for custom output handlers +// e.g. to determine whether to use color. +// NOTE: Due to windows limitations currently returns false for wsl ttys. +DLG_API bool dlg_is_tty(FILE* stream); + +// Returns the null-terminated escape sequence for the given style into buf. +// Undefined behvaiour if any member of style has a value outside its enum range (will +// probably result in a buffer overflow or garbage being printed). +// If all member of style are 'none' will simply nullterminate the first buf char. +DLG_API void dlg_escape_sequence(struct dlg_style style, char buf[12]); + +// The reset style escape sequence. +DLG_API extern const char* const dlg_reset_sequence; + +// Just returns true without other effect on non-windows systems or if dlg +// was compiled without the win_console option. +// On windows tries to set the console mode to ansi to make escape sequences work. +// This works only on newer windows 10 versions. Returns false on error. +// Only the first call to it will have an effect, following calls just return the result. +// The function is threadsafe. Automatically called by the default output handler. +// This will only be able to set the mode for the stdout and stderr consoles, so +// other streams to consoles will still not work. +DLG_API bool dlg_win_init_ansi(void); + +#ifdef __cplusplus +} // extern "C" +#endif + +#endif // header guard diff --git a/3rdparty/freetype-2.13.2/include/freetype/config/ftconfig.h b/3rdparty/freetype-2.13.2/include/freetype/config/ftconfig.h new file mode 100644 index 000000000..a85151699 --- /dev/null +++ b/3rdparty/freetype-2.13.2/include/freetype/config/ftconfig.h @@ -0,0 +1,51 @@ +/**************************************************************************** + * + * ftconfig.h + * + * ANSI-specific configuration file (specification only). + * + * Copyright (C) 1996-2023 by + * David Turner, Robert Wilhelm, and Werner Lemberg. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + + /************************************************************************** + * + * This header file contains a number of macro definitions that are used by + * the rest of the engine. Most of the macros here are automatically + * determined at compile time, and you should not need to change it to port + * FreeType, except to compile the library with a non-ANSI compiler. + * + * Note however that if some specific modifications are needed, we advise + * you to place a modified copy in your build directory. + * + * The build directory is usually `builds/`, and contains + * system-specific files that are always included first when building the + * library. + * + * This ANSI version should stay in `include/config/`. + * + */ + +#ifndef FTCONFIG_H_ +#define FTCONFIG_H_ + +#include +#include FT_CONFIG_OPTIONS_H +#include FT_CONFIG_STANDARD_LIBRARY_H + +#include +#include +#include + +#endif /* FTCONFIG_H_ */ + + +/* END */ diff --git a/src/font/freetype-2.10.2/include/freetype/config/ftheader.h b/3rdparty/freetype-2.13.2/include/freetype/config/ftheader.h similarity index 92% rename from src/font/freetype-2.10.2/include/freetype/config/ftheader.h rename to 3rdparty/freetype-2.13.2/include/freetype/config/ftheader.h index e91598e20..e607bce15 100644 --- a/src/font/freetype-2.10.2/include/freetype/config/ftheader.h +++ b/3rdparty/freetype-2.13.2/include/freetype/config/ftheader.h @@ -4,7 +4,7 @@ * * Build macros of the FreeType 2 library. * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -30,10 +30,12 @@ /* encapsulated in an `extern "C" { .. }` block when included from a */ /* C++ compiler. */ /* */ -#ifdef __cplusplus -#define FT_BEGIN_HEADER extern "C" { -#else -#define FT_BEGIN_HEADER /* nothing */ +#ifndef FT_BEGIN_HEADER +# ifdef __cplusplus +# define FT_BEGIN_HEADER extern "C" { +# else +# define FT_BEGIN_HEADER /* nothing */ +# endif #endif @@ -48,10 +50,12 @@ /* encapsulated in an `extern "C" { .. }` block when included from a */ /* C++ compiler. */ /* */ -#ifdef __cplusplus -#define FT_END_HEADER } -#else -#define FT_END_HEADER /* nothing */ +#ifndef FT_END_HEADER +# ifdef __cplusplus +# define FT_END_HEADER } +# else +# define FT_END_HEADER /* nothing */ +# endif #endif @@ -73,9 +77,16 @@ * Macro definitions used to `#include` specific header files. * * @description: - * The following macros are defined to the name of specific FreeType~2 - * header files. They can be used directly in `#include` statements as - * in: + * In addition to the normal scheme of including header files like + * + * ``` + * #include + * #include + * #include + * ``` + * + * it is possible to used named macros instead. They can be used + * directly in `#include` statements as in * * ``` * #include FT_FREETYPE_H @@ -83,13 +94,9 @@ * #include FT_GLYPH_H * ``` * - * There are several reasons why we are now using macros to name public - * header files. The first one is that such macros are not limited to - * the infamous 8.3~naming rule required by DOS (and - * `FT_MULTIPLE_MASTERS_H` is a lot more meaningful than `ftmm.h`). - * - * The second reason is that it allows for more flexibility in the way - * FreeType~2 is installed on a given system. + * These macros were introduced to overcome the infamous 8.3~naming rule + * required by DOS (and `FT_MULTIPLE_MASTERS_H` is a lot more meaningful + * than `ftmm.h`). * */ @@ -770,6 +777,18 @@ #define FT_COLOR_H + /************************************************************************** + * + * @macro: + * FT_OTSVG_H + * + * @description: + * A macro used in `#include` statements to name the file containing the + * FreeType~2 API which handles the OpenType 'SVG~' glyphs. + */ +#define FT_OTSVG_H + + /* */ /* These header files don't need to be included by the user. */ @@ -797,16 +816,19 @@ #define FT_CACHE_INTERNAL_IMAGE_H FT_CACHE_H #define FT_CACHE_INTERNAL_SBITS_H FT_CACHE_H - - /* - * Include internal headers definitions from `` only when - * building the library. - */ +/* TODO(david): Move this section below to a different header */ #ifdef FT2_BUILD_LIBRARY -#define FT_INTERNAL_INTERNAL_H -#include FT_INTERNAL_INTERNAL_H -#endif /* FT2_BUILD_LIBRARY */ +#if defined( _MSC_VER ) /* Visual C++ (and Intel C++) */ + /* We disable the warning `conditional expression is constant' here */ + /* in order to compile cleanly with the maximum level of warnings. */ + /* In particular, the warning complains about stuff like `while(0)' */ + /* which is very useful in macro definitions. There is no benefit */ + /* in having it enabled. */ +#pragma warning( disable : 4127 ) + +#endif /* _MSC_VER */ +#endif /* FT2_BUILD_LIBRARY */ #endif /* FTHEADER_H_ */ diff --git a/src/font/freetype-2.10.2/include/freetype/config/ftmodule.h b/3rdparty/freetype-2.13.2/include/freetype/config/ftmodule.h similarity index 87% rename from src/font/freetype-2.10.2/include/freetype/config/ftmodule.h rename to 3rdparty/freetype-2.13.2/include/freetype/config/ftmodule.h index 3c4d19b03..51ddfd087 100644 --- a/src/font/freetype-2.10.2/include/freetype/config/ftmodule.h +++ b/3rdparty/freetype-2.13.2/include/freetype/config/ftmodule.h @@ -19,14 +19,15 @@ FT_USE_MODULE( FT_Driver_ClassRec, cff_driver_class ) //FT_USE_MODULE( FT_Driver_ClassRec, t42_driver_class ) //FT_USE_MODULE( FT_Driver_ClassRec, winfnt_driver_class ) //FT_USE_MODULE( FT_Driver_ClassRec, pcf_driver_class ) +//FT_USE_MODULE( FT_Driver_ClassRec, bdf_driver_class ) //FT_USE_MODULE( FT_Module_Class, psaux_module_class ) FT_USE_MODULE( FT_Module_Class, psnames_module_class ) FT_USE_MODULE( FT_Module_Class, pshinter_module_class ) -FT_USE_MODULE( FT_Renderer_Class, ft_raster1_renderer_class ) FT_USE_MODULE( FT_Module_Class, sfnt_module_class ) FT_USE_MODULE( FT_Renderer_Class, ft_smooth_renderer_class ) -//FT_USE_MODULE( FT_Renderer_Class, ft_smooth_lcd_renderer_class ) -//FT_USE_MODULE( FT_Renderer_Class, ft_smooth_lcdv_renderer_class ) -//FT_USE_MODULE( FT_Driver_ClassRec, bdf_driver_class ) +FT_USE_MODULE( FT_Renderer_Class, ft_raster1_renderer_class ) +//FT_USE_MODULE( FT_Renderer_Class, ft_sdf_renderer_class ) +//FT_USE_MODULE( FT_Renderer_Class, ft_bitmap_sdf_renderer_class ) +//FT_USE_MODULE( FT_Renderer_Class, ft_svg_renderer_class ) /* EOF */ diff --git a/src/font/freetype-2.10.2/include/freetype/config/ftoption.h b/3rdparty/freetype-2.13.2/include/freetype/config/ftoption.h similarity index 90% rename from src/font/freetype-2.10.2/include/freetype/config/ftoption.h rename to 3rdparty/freetype-2.13.2/include/freetype/config/ftoption.h index 1eba9531c..3349a7eef 100644 --- a/src/font/freetype-2.10.2/include/freetype/config/ftoption.h +++ b/3rdparty/freetype-2.13.2/include/freetype/config/ftoption.h @@ -4,7 +4,7 @@ * * User-selectable configuration macros (specification only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -42,7 +42,7 @@ FT_BEGIN_HEADER * the name of a directory that is included _before_ the FreeType include * path during compilation. * - * The default FreeType Makefiles and Jamfiles use the build directory + * The default FreeType Makefiles use the build directory * `builds/` by default, but you can easily change that for your * own projects. * @@ -105,8 +105,7 @@ FT_BEGIN_HEADER * * ``` * FREETYPE_PROPERTIES=truetype:interpreter-version=35 \ - * cff:no-stem-darkening=1 \ - * autofitter:warping=1 + * cff:no-stem-darkening=1 * ``` * */ @@ -121,10 +120,8 @@ FT_BEGIN_HEADER * mitigate color fringes inherent to this technology, you also need to * explicitly set up LCD filtering. * - * Note that this feature is covered by several Microsoft patents and - * should not be activated in any default build of the library. When this - * macro is not defined, FreeType offers alternative LCD rendering - * technology that produces excellent output without LCD filtering. + * When this macro is not defined, FreeType offers alternative LCD + * rendering technology that produces excellent output. */ /* #define FT_CONFIG_OPTION_SUBPIXEL_RENDERING */ @@ -183,7 +180,7 @@ FT_BEGIN_HEADER * * Define this macro if you want to enable this 'feature'. */ -//#define FT_CONFIG_OPTION_USE_LZW +/*#define FT_CONFIG_OPTION_USE_LZW*/ /************************************************************************** @@ -198,7 +195,7 @@ FT_BEGIN_HEADER * Define this macro if you want to enable this 'feature'. See also the * macro `FT_CONFIG_OPTION_SYSTEM_ZLIB` below. */ -//#define FT_CONFIG_OPTION_USE_ZLIB +/*#define FT_CONFIG_OPTION_USE_ZLIB*/ /************************************************************************** @@ -222,6 +219,10 @@ FT_BEGIN_HEADER * If you use a build system like cmake or the `configure` script, * options set by those programs have precedence, overwriting the value * here with the configured one. + * + * If you use the GNU make build system directly (that is, without the + * `configure` script) and you define this macro, you also have to pass + * `SYSTEM_ZLIB=yes` as an argument to make. */ /* #define FT_CONFIG_OPTION_SYSTEM_ZLIB */ @@ -360,7 +361,7 @@ FT_BEGIN_HEADER * * Note that the 'FOND' resource isn't checked. */ -//#define FT_CONFIG_OPTION_MAC_FONTS +#define FT_CONFIG_OPTION_MAC_FONTS /************************************************************************** @@ -392,7 +393,7 @@ FT_BEGIN_HEADER * incrementally as the document is parsed, such as the Ghostscript * interpreter for the PostScript language. */ -//#define FT_CONFIG_OPTION_INCREMENTAL +#define FT_CONFIG_OPTION_INCREMENTAL /************************************************************************** @@ -433,6 +434,23 @@ FT_BEGIN_HEADER /* #define FT_DEBUG_LEVEL_TRACE */ + /************************************************************************** + * + * Logging + * + * Compiling FreeType in debug or trace mode makes FreeType write error + * and trace log messages to `stderr`. Enabling this macro + * automatically forces the `FT_DEBUG_LEVEL_ERROR` and + * `FT_DEBUG_LEVEL_TRACE` macros and allows FreeType to write error and + * trace log messages to a file instead of `stderr`. For writing logs + * to a file, FreeType uses an the external `dlg` library (the source + * code is in `src/dlg`). + * + * This option needs a C99 compiler. + */ +/* #define FT_DEBUG_LOGGING */ + + /************************************************************************** * * Autofitter debugging @@ -443,9 +461,9 @@ FT_BEGIN_HEADER * while compiling in 'release' mode): * * ``` - * _af_debug_disable_horz_hints - * _af_debug_disable_vert_hints - * _af_debug_disable_blue_hints + * af_debug_disable_horz_hints_ + * af_debug_disable_vert_hints_ + * af_debug_disable_blue_hints_ * ``` * * Additionally, the following functions provide dumps of various @@ -462,7 +480,7 @@ FT_BEGIN_HEADER * As an argument, they use another global variable: * * ``` - * _af_debug_hints + * af_debug_hints_ * ``` * * Please have a look at the `ftgrid` demo program to see how those @@ -509,6 +527,20 @@ FT_BEGIN_HEADER #undef FT_CONFIG_OPTION_USE_MODULE_ERRORS + /************************************************************************** + * + * OpenType SVG Glyph Support + * + * Setting this macro enables support for OpenType SVG glyphs. By + * default, FreeType can only fetch SVG documents. However, it can also + * render them if external rendering hook functions are plugged in at + * runtime. + * + * More details on the hooks can be found in file `otsvg.h`. + */ +/*#define FT_CONFIG_OPTION_SVG*/ + + /************************************************************************** * * Error Strings @@ -542,7 +574,7 @@ FT_BEGIN_HEADER /************************************************************************** * - * Define `TT_CONFIG_OPTION_COLOR_LAYERS` if you want to support coloured + * Define `TT_CONFIG_OPTION_COLOR_LAYERS` if you want to support colored * outlines (from the 'COLR'/'CPAL' tables) in all formats using the 'sfnt' * module (namely TrueType~& OpenType). */ @@ -552,12 +584,12 @@ FT_BEGIN_HEADER /************************************************************************** * * Define `TT_CONFIG_OPTION_POSTSCRIPT_NAMES` if you want to be able to - * load and enumerate the glyph Postscript names in a TrueType or OpenType + * load and enumerate Postscript names of glyphs in a TrueType or OpenType * file. * - * Note that when you do not compile the 'psnames' module by undefining the - * above `FT_CONFIG_OPTION_POSTSCRIPT_NAMES`, the 'sfnt' module will - * contain additional code used to read the PS Names table from a font. + * Note that if you do not compile the 'psnames' module by undefining the + * above `FT_CONFIG_OPTION_POSTSCRIPT_NAMES` macro, the 'sfnt' module will + * contain additional code to read the PostScript name table from a font. * * (By default, the module uses 'psnames' to extract glyph names.) */ @@ -629,36 +661,12 @@ FT_BEGIN_HEADER * not) instructions in a certain way so that all TrueType fonts look like * they do in a Windows ClearType (DirectWrite) environment. See [1] for a * technical overview on what this means. See `ttinterp.h` for more - * details on the LEAN option. - * - * There are three possible values. - * - * Value 1: - * This value is associated with the 'Infinality' moniker, contributed by - * an individual nicknamed Infinality with the goal of making TrueType - * fonts render better than on Windows. A high amount of configurability - * and flexibility, down to rules for single glyphs in fonts, but also - * very slow. Its experimental and slow nature and the original - * developer losing interest meant that this option was never enabled in - * default builds. + * details on this option. * - * The corresponding interpreter version is v38. - * - * Value 2: - * The new default mode for the TrueType driver. The Infinality code - * base was stripped to the bare minimum and all configurability removed - * in the name of speed and simplicity. The configurability was mainly - * aimed at legacy fonts like 'Arial', 'Times New Roman', or 'Courier'. - * Legacy fonts are fonts that modify vertical stems to achieve clean - * black-and-white bitmaps. The new mode focuses on applying a minimal - * set of rules to all fonts indiscriminately so that modern and web - * fonts render well while legacy fonts render okay. - * - * The corresponding interpreter version is v40. - * - * Value 3: - * Compile both, making both v38 and v40 available (the latter is the - * default). + * The new default mode focuses on applying a minimal set of rules to all + * fonts indiscriminately so that modern and web fonts render well while + * legacy fonts render okay. The corresponding interpreter version is v40. + * The so-called Infinality mode (v38) is no longer available in FreeType. * * By undefining these, you get rendering behavior like on Windows without * ClearType, i.e., Windows XP without ClearType enabled and Win9x @@ -673,9 +681,7 @@ FT_BEGIN_HEADER * [1] * https://www.microsoft.com/typography/cleartype/truetypecleartype.aspx */ -/* #define TT_CONFIG_OPTION_SUBPIXEL_HINTING 1 */ -#define TT_CONFIG_OPTION_SUBPIXEL_HINTING 2 -/* #define TT_CONFIG_OPTION_SUBPIXEL_HINTING ( 1 | 2 ) */ +#define TT_CONFIG_OPTION_SUBPIXEL_HINTING /************************************************************************** @@ -704,7 +710,25 @@ FT_BEGIN_HEADER * 'avar' tables). Tagged 'Font Variations', this is now part of OpenType * also. This has many similarities to Type~1 Multiple Masters support. */ -//#define TT_CONFIG_OPTION_GX_VAR_SUPPORT +#define TT_CONFIG_OPTION_GX_VAR_SUPPORT + + + /************************************************************************** + * + * Define `TT_CONFIG_OPTION_NO_BORING_EXPANSION` if you want to exclude + * support for 'boring' OpenType specification expansions. + * + * https://github.com/harfbuzz/boring-expansion-spec + * + * Right now, the following features are covered: + * + * - 'avar' version 2.0 + * + * Most likely, this is a temporary configuration option to be removed in + * the near future, since it is assumed that eventually those features are + * added to the OpenType standard. + */ +/* #define TT_CONFIG_OPTION_NO_BORING_EXPANSION */ /************************************************************************** @@ -894,24 +918,6 @@ FT_BEGIN_HEADER #endif - /************************************************************************** - * - * Compile 'autofit' module with warp hinting. The idea of the warping - * code is to slightly scale and shift a glyph within a single dimension so - * that as much of its segments are aligned (more or less) on the grid. To - * find out the optimal scaling and shifting value, various parameter - * combinations are tried and scored. - * - * You can switch warping on and off with the `warping` property of the - * auto-hinter (see file `ftdriver.h` for more information; by default it - * is switched off). - * - * This experimental option is not active if the rendering mode is - * `FT_RENDER_MODE_LIGHT`. - */ -#define AF_CONFIG_OPTION_USE_WARPER - - /************************************************************************** * * Use TrueType-like size metrics for 'light' auto-hinting. @@ -945,21 +951,29 @@ FT_BEGIN_HEADER /* - * The next three macros are defined if native TrueType hinting is + * The next two macros are defined if native TrueType hinting is * requested by the definitions above. Don't change this. */ #ifdef TT_CONFIG_OPTION_BYTECODE_INTERPRETER #define TT_USE_BYTECODE_INTERPRETER - #ifdef TT_CONFIG_OPTION_SUBPIXEL_HINTING -#if TT_CONFIG_OPTION_SUBPIXEL_HINTING & 1 -#define TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY -#endif - -#if TT_CONFIG_OPTION_SUBPIXEL_HINTING & 2 #define TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL #endif #endif + + + /* + * The TT_SUPPORT_COLRV1 macro is defined to indicate to clients that this + * version of FreeType has support for 'COLR' v1 API. This definition is + * useful to FreeType clients that want to build in support for 'COLR' v1 + * depending on a tip-of-tree checkout before it is officially released in + * FreeType, and while the feature cannot yet be tested against using + * version macros. Don't change this macro. This may be removed once the + * feature is in a FreeType release version and version macros can be used + * to test for availability. + */ +#ifdef TT_CONFIG_OPTION_COLOR_LAYERS +#define TT_SUPPORT_COLRV1 #endif @@ -991,8 +1005,8 @@ FT_BEGIN_HEADER #error "Invalid CFF darkening parameters!" #endif -FT_END_HEADER +FT_END_HEADER #endif /* FTOPTION_H_ */ diff --git a/src/font/freetype-2.10.2/include/freetype/config/ftstdlib.h b/3rdparty/freetype-2.13.2/include/freetype/config/ftstdlib.h similarity index 88% rename from src/font/freetype-2.10.2/include/freetype/config/ftstdlib.h rename to 3rdparty/freetype-2.13.2/include/freetype/config/ftstdlib.h index d6091f8b3..f65148a90 100644 --- a/src/font/freetype-2.10.2/include/freetype/config/ftstdlib.h +++ b/3rdparty/freetype-2.13.2/include/freetype/config/ftstdlib.h @@ -5,7 +5,7 @@ * ANSI-specific library and header configuration file (specification * only). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -43,7 +43,8 @@ * * `UINT_MAX` and `ULONG_MAX` are used to automatically compute the size of * `int` and `long` in bytes at compile-time. So far, this works for all - * platforms the library has been tested on. + * platforms the library has been tested on. We also check `ULLONG_MAX` + * to see whether we can use 64-bit `long long` later on. * * Note that on the extremely rare platforms that do not provide integer * types that are _exactly_ 16 and 32~bits wide (e.g., some old Crays where @@ -66,6 +67,15 @@ #define FT_LONG_MIN LONG_MIN #define FT_LONG_MAX LONG_MAX #define FT_ULONG_MAX ULONG_MAX +#ifdef LLONG_MAX +#define FT_LLONG_MAX LLONG_MAX +#endif +#ifdef LLONG_MIN +#define FT_LLONG_MIN LLONG_MIN +#endif +#ifdef ULLONG_MAX +#define FT_ULLONG_MAX ULLONG_MAX +#endif /************************************************************************** @@ -101,13 +111,13 @@ #include -#define FT_FILE FILE -#define ft_fclose fclose -#define ft_fopen fopen -#define ft_fread fread -#define ft_fseek fseek -#define ft_ftell ftell -#define ft_sprintf sprintf +#define FT_FILE FILE +#define ft_fclose fclose +#define ft_fopen fopen +#define ft_fread fread +#define ft_fseek fseek +#define ft_ftell ftell +#define ft_snprintf snprintf /************************************************************************** diff --git a/3rdparty/freetype-2.13.2/include/freetype/config/integer-types.h b/3rdparty/freetype-2.13.2/include/freetype/config/integer-types.h new file mode 100644 index 000000000..7258b5085 --- /dev/null +++ b/3rdparty/freetype-2.13.2/include/freetype/config/integer-types.h @@ -0,0 +1,250 @@ +/**************************************************************************** + * + * config/integer-types.h + * + * FreeType integer types definitions. + * + * Copyright (C) 1996-2023 by + * David Turner, Robert Wilhelm, and Werner Lemberg. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ +#ifndef FREETYPE_CONFIG_INTEGER_TYPES_H_ +#define FREETYPE_CONFIG_INTEGER_TYPES_H_ + + /* There are systems (like the Texas Instruments 'C54x) where a `char` */ + /* has 16~bits. ANSI~C says that `sizeof(char)` is always~1. Since an */ + /* `int` has 16~bits also for this system, `sizeof(int)` gives~1 which */ + /* is probably unexpected. */ + /* */ + /* `CHAR_BIT` (defined in `limits.h`) gives the number of bits in a */ + /* `char` type. */ + +#ifndef FT_CHAR_BIT +#define FT_CHAR_BIT CHAR_BIT +#endif + +#ifndef FT_SIZEOF_INT + + /* The size of an `int` type. */ +#if FT_UINT_MAX == 0xFFFFUL +#define FT_SIZEOF_INT ( 16 / FT_CHAR_BIT ) +#elif FT_UINT_MAX == 0xFFFFFFFFUL +#define FT_SIZEOF_INT ( 32 / FT_CHAR_BIT ) +#elif FT_UINT_MAX > 0xFFFFFFFFUL && FT_UINT_MAX == 0xFFFFFFFFFFFFFFFFUL +#define FT_SIZEOF_INT ( 64 / FT_CHAR_BIT ) +#else +#error "Unsupported size of `int' type!" +#endif + +#endif /* !defined(FT_SIZEOF_INT) */ + +#ifndef FT_SIZEOF_LONG + + /* The size of a `long` type. A five-byte `long` (as used e.g. on the */ + /* DM642) is recognized but avoided. */ +#if FT_ULONG_MAX == 0xFFFFFFFFUL +#define FT_SIZEOF_LONG ( 32 / FT_CHAR_BIT ) +#elif FT_ULONG_MAX > 0xFFFFFFFFUL && FT_ULONG_MAX == 0xFFFFFFFFFFUL +#define FT_SIZEOF_LONG ( 32 / FT_CHAR_BIT ) +#elif FT_ULONG_MAX > 0xFFFFFFFFUL && FT_ULONG_MAX == 0xFFFFFFFFFFFFFFFFUL +#define FT_SIZEOF_LONG ( 64 / FT_CHAR_BIT ) +#else +#error "Unsupported size of `long' type!" +#endif + +#endif /* !defined(FT_SIZEOF_LONG) */ + +#ifndef FT_SIZEOF_LONG_LONG + + /* The size of a `long long` type if available */ +#if defined( FT_ULLONG_MAX ) && FT_ULLONG_MAX >= 0xFFFFFFFFFFFFFFFFULL +#define FT_SIZEOF_LONG_LONG ( 64 / FT_CHAR_BIT ) +#else +#define FT_SIZEOF_LONG_LONG 0 +#endif + +#endif /* !defined(FT_SIZEOF_LONG_LONG) */ + + + /************************************************************************** + * + * @section: + * basic_types + * + */ + + + /************************************************************************** + * + * @type: + * FT_Int16 + * + * @description: + * A typedef for a 16bit signed integer type. + */ + typedef signed short FT_Int16; + + + /************************************************************************** + * + * @type: + * FT_UInt16 + * + * @description: + * A typedef for a 16bit unsigned integer type. + */ + typedef unsigned short FT_UInt16; + + /* */ + + + /* this #if 0 ... #endif clause is for documentation purposes */ +#if 0 + + /************************************************************************** + * + * @type: + * FT_Int32 + * + * @description: + * A typedef for a 32bit signed integer type. The size depends on the + * configuration. + */ + typedef signed XXX FT_Int32; + + + /************************************************************************** + * + * @type: + * FT_UInt32 + * + * A typedef for a 32bit unsigned integer type. The size depends on the + * configuration. + */ + typedef unsigned XXX FT_UInt32; + + + /************************************************************************** + * + * @type: + * FT_Int64 + * + * A typedef for a 64bit signed integer type. The size depends on the + * configuration. Only defined if there is real 64bit support; + * otherwise, it gets emulated with a structure (if necessary). + */ + typedef signed XXX FT_Int64; + + + /************************************************************************** + * + * @type: + * FT_UInt64 + * + * A typedef for a 64bit unsigned integer type. The size depends on the + * configuration. Only defined if there is real 64bit support; + * otherwise, it gets emulated with a structure (if necessary). + */ + typedef unsigned XXX FT_UInt64; + + /* */ + +#endif + +#if FT_SIZEOF_INT == ( 32 / FT_CHAR_BIT ) + + typedef signed int FT_Int32; + typedef unsigned int FT_UInt32; + +#elif FT_SIZEOF_LONG == ( 32 / FT_CHAR_BIT ) + + typedef signed long FT_Int32; + typedef unsigned long FT_UInt32; + +#else +#error "no 32bit type found -- please check your configuration files" +#endif + + + /* look up an integer type that is at least 32~bits */ +#if FT_SIZEOF_INT >= ( 32 / FT_CHAR_BIT ) + + typedef int FT_Fast; + typedef unsigned int FT_UFast; + +#elif FT_SIZEOF_LONG >= ( 32 / FT_CHAR_BIT ) + + typedef long FT_Fast; + typedef unsigned long FT_UFast; + +#endif + + + /* determine whether we have a 64-bit integer type */ +#if FT_SIZEOF_LONG == ( 64 / FT_CHAR_BIT ) + +#define FT_INT64 long +#define FT_UINT64 unsigned long + +#elif FT_SIZEOF_LONG_LONG >= ( 64 / FT_CHAR_BIT ) + +#define FT_INT64 long long int +#define FT_UINT64 unsigned long long int + + /************************************************************************** + * + * A 64-bit data type may create compilation problems if you compile in + * strict ANSI mode. To avoid them, we disable other 64-bit data types if + * `__STDC__` is defined. You can however ignore this rule by defining the + * `FT_CONFIG_OPTION_FORCE_INT64` configuration macro. + */ +#elif !defined( __STDC__ ) || defined( FT_CONFIG_OPTION_FORCE_INT64 ) + +#if defined( _MSC_VER ) && _MSC_VER >= 900 /* Visual C++ (and Intel C++) */ + + /* this compiler provides the `__int64` type */ +#define FT_INT64 __int64 +#define FT_UINT64 unsigned __int64 + +#elif defined( __BORLANDC__ ) /* Borland C++ */ + + /* XXXX: We should probably check the value of `__BORLANDC__` in order */ + /* to test the compiler version. */ + + /* this compiler provides the `__int64` type */ +#define FT_INT64 __int64 +#define FT_UINT64 unsigned __int64 + +#elif defined( __WATCOMC__ ) && __WATCOMC__ >= 1100 /* Watcom C++ */ + +#define FT_INT64 long long int +#define FT_UINT64 unsigned long long int + +#elif defined( __MWERKS__ ) /* Metrowerks CodeWarrior */ + +#define FT_INT64 long long int +#define FT_UINT64 unsigned long long int + +#elif defined( __GNUC__ ) + + /* GCC provides the `long long` type */ +#define FT_INT64 long long int +#define FT_UINT64 unsigned long long int + +#endif /* !__STDC__ */ + +#endif /* FT_SIZEOF_LONG == (64 / FT_CHAR_BIT) */ + +#ifdef FT_INT64 + typedef FT_INT64 FT_Int64; + typedef FT_UINT64 FT_UInt64; +#endif + + +#endif /* FREETYPE_CONFIG_INTEGER_TYPES_H_ */ diff --git a/3rdparty/freetype-2.13.2/include/freetype/config/mac-support.h b/3rdparty/freetype-2.13.2/include/freetype/config/mac-support.h new file mode 100644 index 000000000..b77b96d5d --- /dev/null +++ b/3rdparty/freetype-2.13.2/include/freetype/config/mac-support.h @@ -0,0 +1,49 @@ +/**************************************************************************** + * + * config/mac-support.h + * + * Mac/OS X support configuration header. + * + * Copyright (C) 1996-2023 by + * David Turner, Robert Wilhelm, and Werner Lemberg. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ +#ifndef FREETYPE_CONFIG_MAC_SUPPORT_H_ +#define FREETYPE_CONFIG_MAC_SUPPORT_H_ + + /************************************************************************** + * + * Mac support + * + * This is the only necessary change, so it is defined here instead + * providing a new configuration file. + */ +#if defined( __APPLE__ ) || ( defined( __MWERKS__ ) && defined( macintosh ) ) + /* No Carbon frameworks for 64bit 10.4.x. */ + /* `AvailabilityMacros.h` is available since Mac OS X 10.2, */ + /* so guess the system version by maximum errno before inclusion. */ +#include +#ifdef ECANCELED /* defined since 10.2 */ +#include "AvailabilityMacros.h" +#endif +#if defined( __LP64__ ) && \ + ( MAC_OS_X_VERSION_MIN_REQUIRED <= MAC_OS_X_VERSION_10_4 ) +#undef FT_MACINTOSH +#endif + +#elif defined( __SC__ ) || defined( __MRC__ ) + /* Classic MacOS compilers */ +#include "ConditionalMacros.h" +#if TARGET_OS_MAC +#define FT_MACINTOSH 1 +#endif + +#endif /* Mac support */ + +#endif /* FREETYPE_CONFIG_MAC_SUPPORT_H_ */ diff --git a/3rdparty/freetype-2.13.2/include/freetype/config/public-macros.h b/3rdparty/freetype-2.13.2/include/freetype/config/public-macros.h new file mode 100644 index 000000000..23d0fa6a3 --- /dev/null +++ b/3rdparty/freetype-2.13.2/include/freetype/config/public-macros.h @@ -0,0 +1,138 @@ +/**************************************************************************** + * + * config/public-macros.h + * + * Define a set of compiler macros used in public FreeType headers. + * + * Copyright (C) 2020-2023 by + * David Turner, Robert Wilhelm, and Werner Lemberg. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + /* + * The definitions in this file are used by the public FreeType headers + * and thus should be considered part of the public API. + * + * Other compiler-specific macro definitions that are not exposed by the + * FreeType API should go into + * `include/freetype/internal/compiler-macros.h` instead. + */ +#ifndef FREETYPE_CONFIG_PUBLIC_MACROS_H_ +#define FREETYPE_CONFIG_PUBLIC_MACROS_H_ + + /* + * `FT_BEGIN_HEADER` and `FT_END_HEADER` might have already been defined + * by `freetype/config/ftheader.h`, but we don't want to include this + * header here, so redefine the macros here only when needed. Their + * definition is very stable, so keeping them in sync with the ones in the + * header should not be a maintenance issue. + */ +#ifndef FT_BEGIN_HEADER +#ifdef __cplusplus +#define FT_BEGIN_HEADER extern "C" { +#else +#define FT_BEGIN_HEADER /* empty */ +#endif +#endif /* FT_BEGIN_HEADER */ + +#ifndef FT_END_HEADER +#ifdef __cplusplus +#define FT_END_HEADER } +#else +#define FT_END_HEADER /* empty */ +#endif +#endif /* FT_END_HEADER */ + + +FT_BEGIN_HEADER + + /* + * Mark a function declaration as public. This ensures it will be + * properly exported to client code. Place this before a function + * declaration. + * + * NOTE: This macro should be considered an internal implementation + * detail, and not part of the FreeType API. It is only defined here + * because it is needed by `FT_EXPORT`. + */ + + /* Visual C, mingw */ +#if defined( _WIN32 ) + +#if defined( FT2_BUILD_LIBRARY ) && defined( DLL_EXPORT ) +#define FT_PUBLIC_FUNCTION_ATTRIBUTE __declspec( dllexport ) +#elif defined( DLL_IMPORT ) +#define FT_PUBLIC_FUNCTION_ATTRIBUTE __declspec( dllimport ) +#endif + + /* gcc, clang */ +#elif ( defined( __GNUC__ ) && __GNUC__ >= 4 ) || defined( __clang__ ) +#define FT_PUBLIC_FUNCTION_ATTRIBUTE \ + __attribute__(( visibility( "default" ) )) + + /* Sun */ +#elif defined( __SUNPRO_C ) && __SUNPRO_C >= 0x550 +#define FT_PUBLIC_FUNCTION_ATTRIBUTE __global +#endif + + +#ifndef FT_PUBLIC_FUNCTION_ATTRIBUTE +#define FT_PUBLIC_FUNCTION_ATTRIBUTE /* empty */ +#endif + + + /* + * Define a public FreeType API function. This ensures it is properly + * exported or imported at build time. The macro parameter is the + * function's return type as in: + * + * FT_EXPORT( FT_Bool ) + * FT_Object_Method( FT_Object obj, + * ... ); + * + * NOTE: This requires that all `FT_EXPORT` uses are inside + * `FT_BEGIN_HEADER ... FT_END_HEADER` blocks. This guarantees that the + * functions are exported with C linkage, even when the header is included + * by a C++ source file. + */ +#define FT_EXPORT( x ) FT_PUBLIC_FUNCTION_ATTRIBUTE extern x + + + /* + * `FT_UNUSED` indicates that a given parameter is not used -- this is + * only used to get rid of unpleasant compiler warnings. + * + * Technically, this was not meant to be part of the public API, but some + * third-party code depends on it. + */ +#ifndef FT_UNUSED +#define FT_UNUSED( arg ) ( (arg) = (arg) ) +#endif + + + /* + * Support for casts in both C and C++. + */ +#ifdef __cplusplus +#define FT_STATIC_CAST( type, var ) static_cast(var) +#define FT_REINTERPRET_CAST( type, var ) reinterpret_cast(var) + +#define FT_STATIC_BYTE_CAST( type, var ) \ + static_cast( static_cast( var ) ) +#else +#define FT_STATIC_CAST( type, var ) (type)(var) +#define FT_REINTERPRET_CAST( type, var ) (type)(var) + +#define FT_STATIC_BYTE_CAST( type, var ) (type)(unsigned char)(var) +#endif + + +FT_END_HEADER + +#endif /* FREETYPE_CONFIG_PUBLIC_MACROS_H_ */ diff --git a/src/font/freetype-2.10.2/include/freetype/freetype.h b/3rdparty/freetype-2.13.2/include/freetype/freetype.h similarity index 85% rename from src/font/freetype-2.10.2/include/freetype/freetype.h rename to 3rdparty/freetype-2.13.2/include/freetype/freetype.h index 973264b12..92acf3794 100644 --- a/src/font/freetype-2.10.2/include/freetype/freetype.h +++ b/3rdparty/freetype-2.13.2/include/freetype/freetype.h @@ -4,7 +4,7 @@ * * FreeType high-level API and common types (specification only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,25 +20,44 @@ #define FREETYPE_H_ -#ifndef FT_FREETYPE_H -#error "`ft2build.h' hasn't been included yet!" -#error "Please always use macros to include FreeType header files." -#error "Example:" -#error " #include " -#error " #include FT_FREETYPE_H" -#endif - - #include #include FT_CONFIG_CONFIG_H -#include FT_TYPES_H -#include FT_ERRORS_H +#include +#include FT_BEGIN_HEADER + /************************************************************************** + * + * @section: + * preamble + * + * @title: + * Preamble + * + * @abstract: + * What FreeType is and isn't + * + * @description: + * FreeType is a library that provides access to glyphs in font files. It + * scales the glyph images and their metrics to a requested size, and it + * rasterizes the glyph images to produce pixel or subpixel alpha coverage + * bitmaps. + * + * Note that FreeType is _not_ a text layout engine. You have to use + * higher-level libraries like HarfBuzz, Pango, or ICU for that. + * + * Note also that FreeType does _not_ perform alpha blending or + * compositing the resulting bitmaps or pixmaps by itself. Use your + * favourite graphics library (for example, Cairo or Skia) to further + * process FreeType's output. + * + */ + + /************************************************************************** * * @section: @@ -51,22 +70,15 @@ FT_BEGIN_HEADER * How client applications should include FreeType header files. * * @description: - * To be as flexible as possible (and for historical reasons), FreeType - * uses a very special inclusion scheme to load header files, for example + * To be as flexible as possible (and for historical reasons), you must + * load file `ft2build.h` first before other header files, for example * * ``` * #include * - * #include FT_FREETYPE_H - * #include FT_OUTLINE_H + * #include + * #include * ``` - * - * A compiler and its preprocessor only needs an include path to find the - * file `ft2build.h`; the exact locations and names of the other FreeType - * header files are hidden by @header_file_macros, loaded by - * `ft2build.h`. The API documentation always gives the header macro - * name needed for a particular function. - * */ @@ -90,58 +102,25 @@ FT_BEGIN_HEADER */ - - /*************************************************************************/ - /*************************************************************************/ - /* */ - /* B A S I C T Y P E S */ - /* */ - /*************************************************************************/ - /*************************************************************************/ - - /************************************************************************** * * @section: - * base_interface + * font_testing_macros * * @title: - * Base Interface + * Font Testing Macros * * @abstract: - * The FreeType~2 base font interface. + * Macros to test various properties of fonts. * * @description: - * This section describes the most important public high-level API - * functions of FreeType~2. - * - * @order: - * FT_Library - * FT_Face - * FT_Size - * FT_GlyphSlot - * FT_CharMap - * FT_Encoding - * FT_ENC_TAG - * - * FT_FaceRec + * Macros to test the most important font properties. * - * FT_FACE_FLAG_SCALABLE - * FT_FACE_FLAG_FIXED_SIZES - * FT_FACE_FLAG_FIXED_WIDTH - * FT_FACE_FLAG_HORIZONTAL - * FT_FACE_FLAG_VERTICAL - * FT_FACE_FLAG_COLOR - * FT_FACE_FLAG_SFNT - * FT_FACE_FLAG_CID_KEYED - * FT_FACE_FLAG_TRICKY - * FT_FACE_FLAG_KERNING - * FT_FACE_FLAG_MULTIPLE_MASTERS - * FT_FACE_FLAG_VARIATION - * FT_FACE_FLAG_GLYPH_NAMES - * FT_FACE_FLAG_EXTERNAL_STREAM - * FT_FACE_FLAG_HINTER + * It is recommended to use these high-level macros instead of directly + * testing the corresponding flags, which are scattered over various + * structures. * + * @order: * FT_HAS_HORIZONTAL * FT_HAS_VERTICAL * FT_HAS_KERNING @@ -149,6 +128,9 @@ FT_BEGIN_HEADER * FT_HAS_GLYPH_NAMES * FT_HAS_COLOR * FT_HAS_MULTIPLE_MASTERS + * FT_HAS_SVG + * FT_HAS_SBIX + * FT_HAS_SBIX_OVERLAY * * FT_IS_SFNT * FT_IS_SCALABLE @@ -158,21 +140,59 @@ FT_BEGIN_HEADER * FT_IS_NAMED_INSTANCE * FT_IS_VARIATION * - * FT_STYLE_FLAG_BOLD - * FT_STYLE_FLAG_ITALIC + */ + + + /************************************************************************** * - * FT_SizeRec - * FT_Size_Metrics + * @section: + * library_setup * - * FT_GlyphSlotRec - * FT_Glyph_Metrics - * FT_SubGlyph + * @title: + * Library Setup * - * FT_Bitmap_Size + * @abstract: + * Functions to start and end the usage of the FreeType library. + * + * @description: + * Functions to start and end the usage of the FreeType library. * + * Note that @FT_Library_Version and @FREETYPE_XXX are of limited use + * because even a new release of FreeType with only documentation + * changes increases the version number. + * + * @order: + * FT_Library * FT_Init_FreeType * FT_Done_FreeType * + * FT_Library_Version + * FREETYPE_XXX + * + */ + + + /************************************************************************** + * + * @section: + * face_creation + * + * @title: + * Face Creation + * + * @abstract: + * Functions to manage fonts. + * + * @description: + * The functions and structures collected in this section operate on + * fonts globally. + * + * @order: + * FT_Face + * FT_FaceRec + * FT_FACE_FLAG_XXX + * FT_STYLE_FLAG_XXX + * * FT_New_Face * FT_Done_Face * FT_Reference_Face @@ -180,10 +200,36 @@ FT_BEGIN_HEADER * FT_Face_Properties * FT_Open_Face * FT_Open_Args + * FT_OPEN_XXX * FT_Parameter * FT_Attach_File * FT_Attach_Stream * + */ + + + /************************************************************************** + * + * @section: + * sizing_and_scaling + * + * @title: + * Sizing and Scaling + * + * @abstract: + * Functions to manage font sizes. + * + * @description: + * The functions and structures collected in this section are related to + * selecting and manipulating the size of a font globally. + * + * @order: + * FT_Size + * FT_SizeRec + * FT_Size_Metrics + * + * FT_Bitmap_Size + * * FT_Set_Char_Size * FT_Set_Pixel_Sizes * FT_Request_Size @@ -191,77 +237,159 @@ FT_BEGIN_HEADER * FT_Size_Request_Type * FT_Size_RequestRec * FT_Size_Request + * * FT_Set_Transform - * FT_Load_Glyph - * FT_Get_Char_Index - * FT_Get_First_Char - * FT_Get_Next_Char - * FT_Get_Name_Index - * FT_Load_Char + * FT_Get_Transform * - * FT_OPEN_MEMORY - * FT_OPEN_STREAM - * FT_OPEN_PATHNAME - * FT_OPEN_DRIVER - * FT_OPEN_PARAMS - * - * FT_LOAD_DEFAULT - * FT_LOAD_RENDER - * FT_LOAD_MONOCHROME - * FT_LOAD_LINEAR_DESIGN - * FT_LOAD_NO_SCALE - * FT_LOAD_NO_HINTING - * FT_LOAD_NO_BITMAP - * FT_LOAD_NO_AUTOHINT - * FT_LOAD_COLOR - * - * FT_LOAD_VERTICAL_LAYOUT - * FT_LOAD_IGNORE_TRANSFORM - * FT_LOAD_FORCE_AUTOHINT - * FT_LOAD_NO_RECURSE - * FT_LOAD_PEDANTIC - * - * FT_LOAD_TARGET_NORMAL - * FT_LOAD_TARGET_LIGHT - * FT_LOAD_TARGET_MONO - * FT_LOAD_TARGET_LCD - * FT_LOAD_TARGET_LCD_V + */ + + + /************************************************************************** + * + * @section: + * glyph_retrieval + * + * @title: + * Glyph Retrieval + * + * @abstract: + * Functions to manage glyphs. + * + * @description: + * The functions and structures collected in this section operate on + * single glyphs, of which @FT_Load_Glyph is most important. + * + * @order: + * FT_GlyphSlot + * FT_GlyphSlotRec + * FT_Glyph_Metrics * + * FT_Load_Glyph + * FT_LOAD_XXX * FT_LOAD_TARGET_MODE + * FT_LOAD_TARGET_XXX * * FT_Render_Glyph * FT_Render_Mode * FT_Get_Kerning * FT_Kerning_Mode * FT_Get_Track_Kerning - * FT_Get_Glyph_Name - * FT_Get_Postscript_Name * + */ + + + /************************************************************************** + * + * @section: + * character_mapping + * + * @title: + * Character Mapping + * + * @abstract: + * Functions to manage character-to-glyph maps. + * + * @description: + * This section holds functions and structures that are related to + * mapping character input codes to glyph indices. + * + * Note that for many scripts the simplistic approach used by FreeType + * of mapping a single character to a single glyph is not valid or + * possible! In general, a higher-level library like HarfBuzz or ICU + * should be used for handling text strings. + * + * @order: + * FT_CharMap * FT_CharMapRec + * FT_Encoding + * FT_ENC_TAG + * * FT_Select_Charmap * FT_Set_Charmap * FT_Get_Charmap_Index * + * FT_Get_Char_Index + * FT_Get_First_Char + * FT_Get_Next_Char + * FT_Load_Char + * + */ + + + /************************************************************************** + * + * @section: + * information_retrieval + * + * @title: + * Information Retrieval + * + * @abstract: + * Functions to retrieve font and glyph information. + * + * @description: + * Functions to retrieve font and glyph information. Only some very + * basic data is covered; see also the chapter on the format-specific + * API for more. + * + * + * @order: + * FT_Get_Name_Index + * FT_Get_Glyph_Name + * FT_Get_Postscript_Name * FT_Get_FSType_Flags + * FT_FSTYPE_XXX * FT_Get_SubGlyph_Info + * FT_SUBGLYPH_FLAG_XXX + * + */ + + + /************************************************************************** + * + * @section: + * other_api_data + * + * @title: + * Other API Data * + * @abstract: + * Other structures, enumerations, and macros. + * + * @description: + * Other structures, enumerations, and macros. Deprecated functions are + * also listed here. + * + * @order: * FT_Face_Internal * FT_Size_Internal * FT_Slot_Internal * - * FT_FACE_FLAG_XXX - * FT_STYLE_FLAG_XXX - * FT_OPEN_XXX - * FT_LOAD_XXX - * FT_LOAD_TARGET_XXX - * FT_SUBGLYPH_FLAG_XXX - * FT_FSTYPE_XXX + * FT_SubGlyph * * FT_HAS_FAST_GLYPHS + * FT_Face_CheckTrueTypePatents + * FT_Face_SetUnpatentedHinting * */ + /*************************************************************************/ + /*************************************************************************/ + /* */ + /* B A S I C T Y P E S */ + /* */ + /*************************************************************************/ + /*************************************************************************/ + + + /************************************************************************** + * + * @section: + * glyph_retrieval + * + */ + /************************************************************************** * * @struct: @@ -329,6 +457,13 @@ FT_BEGIN_HEADER } FT_Glyph_Metrics; + /************************************************************************** + * + * @section: + * sizing_and_scaling + * + */ + /************************************************************************** * * @struct: @@ -389,6 +524,13 @@ FT_BEGIN_HEADER /*************************************************************************/ /*************************************************************************/ + /************************************************************************** + * + * @section: + * library_setup + * + */ + /************************************************************************** * * @type: @@ -463,7 +605,7 @@ FT_BEGIN_HEADER /************************************************************************** * * @section: - * base_interface + * face_creation * */ @@ -499,6 +641,13 @@ FT_BEGIN_HEADER typedef struct FT_FaceRec_* FT_Face; + /************************************************************************** + * + * @section: + * sizing_and_scaling + * + */ + /************************************************************************** * * @type: @@ -509,13 +658,15 @@ FT_BEGIN_HEADER * size. * * @note: - * An @FT_Face has one _active_ @FT_Size object that is used by functions - * like @FT_Load_Glyph to determine the scaling transformation that in - * turn is used to load and hint glyphs and metrics. + * An @FT_Face has one _active_ `FT_Size` object that is used by + * functions like @FT_Load_Glyph to determine the scaling transformation + * that in turn is used to load and hint glyphs and metrics. * - * You can use @FT_Set_Char_Size, @FT_Set_Pixel_Sizes, @FT_Request_Size + * A newly created `FT_Size` object contains only meaningless zero values. + * You must use @FT_Set_Char_Size, @FT_Set_Pixel_Sizes, @FT_Request_Size * or even @FT_Select_Size to change the content (i.e., the scaling - * values) of the active @FT_Size. + * values) of the active `FT_Size`. Otherwise, the scaling and hinting + * will not be performed. * * You can use @FT_New_Size to create additional size objects for a given * @FT_Face, but they won't be used by other functions until you activate @@ -529,6 +680,13 @@ FT_BEGIN_HEADER typedef struct FT_SizeRec_* FT_Size; + /************************************************************************** + * + * @section: + * glyph_retrieval + * + */ + /************************************************************************** * * @type: @@ -548,6 +706,13 @@ FT_BEGIN_HEADER typedef struct FT_GlyphSlotRec_* FT_GlyphSlot; + /************************************************************************** + * + * @section: + * character_mapping + * + */ + /************************************************************************** * * @type: @@ -603,11 +768,12 @@ FT_BEGIN_HEADER */ #ifndef FT_ENC_TAG -#define FT_ENC_TAG( value, a, b, c, d ) \ - value = ( ( (FT_UInt32)(a) << 24 ) | \ - ( (FT_UInt32)(b) << 16 ) | \ - ( (FT_UInt32)(c) << 8 ) | \ - (FT_UInt32)(d) ) + +#define FT_ENC_TAG( value, a, b, c, d ) \ + value = ( ( FT_STATIC_BYTE_CAST( FT_UInt32, a ) << 24 ) | \ + ( FT_STATIC_BYTE_CAST( FT_UInt32, b ) << 16 ) | \ + ( FT_STATIC_BYTE_CAST( FT_UInt32, c ) << 8 ) | \ + FT_STATIC_BYTE_CAST( FT_UInt32, d ) ) #endif /* FT_ENC_TAG */ @@ -623,7 +789,7 @@ FT_BEGIN_HEADER * * @note: * Despite the name, this enumeration lists specific character - * repertories (i.e., charsets), and not text encoding methods (e.g., + * repertoires (i.e., charsets), and not text encoding methods (e.g., * UTF-8, UTF-16, etc.). * * Other encodings might be defined in the future. @@ -717,11 +883,16 @@ FT_BEGIN_HEADER * Same as FT_ENCODING_JOHAB. Deprecated. * * @note: - * By default, FreeType enables a Unicode charmap and tags it with - * `FT_ENCODING_UNICODE` when it is either provided or can be generated - * from PostScript glyph name dictionaries in the font file. All other - * encodings are considered legacy and tagged only if explicitly defined - * in the font file. Otherwise, `FT_ENCODING_NONE` is used. + * When loading a font, FreeType makes a Unicode charmap active if + * possible (either if the font provides such a charmap, or if FreeType + * can synthesize one from PostScript glyph name dictionaries; in either + * case, the charmap is tagged with `FT_ENCODING_UNICODE`). If such a + * charmap is synthesized, it is placed at the first position of the + * charmap array. + * + * All other encodings are considered legacy and tagged only if + * explicitly defined in the font file. Otherwise, `FT_ENCODING_NONE` is + * used. * * `FT_ENCODING_NONE` is set by the BDF and PCF drivers if the charmap is * neither Unicode nor ISO-8859-1 (otherwise it is set to @@ -751,7 +922,7 @@ FT_BEGIN_HEADER * `encoding_id`. If, for example, `encoding_id` is `TT_MAC_ID_ROMAN` * and the language ID (minus~1) is `TT_MAC_LANGID_GREEK`, it is the * Greek encoding, not Roman. `TT_MAC_ID_ARABIC` with - * `TT_MAC_LANGID_FARSI` means the Farsi variant the Arabic encoding. + * `TT_MAC_LANGID_FARSI` means the Farsi variant of the Arabic encoding. */ typedef enum FT_Encoding_ { @@ -849,6 +1020,13 @@ FT_BEGIN_HEADER /*************************************************************************/ + /************************************************************************** + * + * @section: + * other_api_data + * + */ + /************************************************************************** * * @type: @@ -864,6 +1042,13 @@ FT_BEGIN_HEADER typedef struct FT_Face_InternalRec_* FT_Face_Internal; + /************************************************************************** + * + * @section: + * face_creation + * + */ + /************************************************************************** * * @struct: @@ -890,7 +1075,7 @@ FT_BEGIN_HEADER * If we have the third named instance of face~4, say, `face_index` is * set to 0x00030004. * - * Bit 31 is always zero (this is, `face_index` is always a positive + * Bit 31 is always zero (that is, `face_index` is always a positive * value). * * [Since 2.9] Changing the design coordinates with @@ -908,7 +1093,7 @@ FT_BEGIN_HEADER * * [Since 2.6.1] Bits 16-30 hold the number of named instances * available for the current face if we have a GX or OpenType variation - * (sub)font. Bit 31 is always zero (this is, `style_flags` is always + * (sub)font. Bit 31 is always zero (that is, `style_flags` is always * a positive value). Note that a variation font has always at least * one named instance, namely the default instance. * @@ -974,6 +1159,9 @@ FT_BEGIN_HEADER * Note that the bounding box might be off by (at least) one pixel for * hinted fonts. See @FT_Size_Metrics for further discussion. * + * Note that the bounding box does not vary in OpenType variation fonts + * and should only be used in relation to the default instance. + * * units_per_EM :: * The number of font units per EM square for this face. This is * typically 2048 for TrueType fonts, and 1000 for Type~1 fonts. Only @@ -1059,9 +1247,9 @@ FT_BEGIN_HEADER FT_Generic generic; - /*# The following member variables (down to `underline_thickness`) */ - /*# are only relevant to scalable outlines; cf. @FT_Bitmap_Size */ - /*# for bitmap fonts. */ + /* The following member variables (down to `underline_thickness`) */ + /* are only relevant to scalable outlines; cf. @FT_Bitmap_Size */ + /* for bitmap fonts. */ FT_BBox bbox; FT_UShort units_per_EM; @@ -1079,7 +1267,7 @@ FT_BEGIN_HEADER FT_Size size; FT_CharMap charmap; - /*@private begin */ + /* private fields, internal to FreeType */ FT_Driver driver; FT_Memory memory; @@ -1092,8 +1280,6 @@ FT_BEGIN_HEADER FT_Face_Internal internal; - /*@private end */ - } FT_FaceRec; @@ -1136,9 +1322,9 @@ FT_BEGIN_HEADER * FT_FACE_FLAG_KERNING :: * The face contains kerning information. If set, the kerning distance * can be retrieved using the function @FT_Get_Kerning. Otherwise the - * function always return the vector (0,0). Note that FreeType doesn't - * handle kerning data from the SFNT 'GPOS' table (as present in many - * OpenType fonts). + * function always returns the vector (0,0). Note that FreeType + * doesn't handle kerning data from the SFNT 'GPOS' table (as present + * in many OpenType fonts). * * FT_FACE_FLAG_FAST_GLYPHS :: * THIS FLAG IS DEPRECATED. DO NOT USE OR TEST IT. @@ -1176,13 +1362,13 @@ FT_BEGIN_HEADER * successfully; in all other cases you get an * `FT_Err_Invalid_Argument` error. * - * Note that CID-keyed fonts that are in an SFNT wrapper (this is, all + * Note that CID-keyed fonts that are in an SFNT wrapper (that is, all * OpenType/CFF fonts) don't have this flag set since the glyphs are * accessed in the normal way (using contiguous indices); the * 'CID-ness' isn't visible to the application. * * FT_FACE_FLAG_TRICKY :: - * The face is 'tricky', this is, it always needs the font format's + * The face is 'tricky', that is, it always needs the font format's * native hinting engine to get a reasonable result. A typical example * is the old Chinese font `mingli.ttf` (but not `mingliu.ttc`) that * uses TrueType bytecode instructions to move and scale all of its @@ -1204,8 +1390,21 @@ FT_BEGIN_HEADER * FT_FACE_FLAG_VARIATION :: * [Since 2.9] Set if the current face (or named instance) has been * altered with @FT_Set_MM_Design_Coordinates, - * @FT_Set_Var_Design_Coordinates, or @FT_Set_Var_Blend_Coordinates. - * This flag is unset by a call to @FT_Set_Named_Instance. + * @FT_Set_Var_Design_Coordinates, @FT_Set_Var_Blend_Coordinates, or + * @FT_Set_MM_WeightVector to select a non-default instance. + * + * FT_FACE_FLAG_SVG :: + * [Since 2.12] The face has an 'SVG~' OpenType table. + * + * FT_FACE_FLAG_SBIX :: + * [Since 2.12] The face has an 'sbix' OpenType table *and* outlines. + * For such fonts, @FT_FACE_FLAG_SCALABLE is not set by default to + * retain backward compatibility. + * + * FT_FACE_FLAG_SBIX_OVERLAY :: + * [Since 2.12] The face has an 'sbix' OpenType table where outlines + * should be drawn on top of bitmap strikes. + * */ #define FT_FACE_FLAG_SCALABLE ( 1L << 0 ) #define FT_FACE_FLAG_FIXED_SIZES ( 1L << 1 ) @@ -1223,7 +1422,17 @@ FT_BEGIN_HEADER #define FT_FACE_FLAG_TRICKY ( 1L << 13 ) #define FT_FACE_FLAG_COLOR ( 1L << 14 ) #define FT_FACE_FLAG_VARIATION ( 1L << 15 ) +#define FT_FACE_FLAG_SVG ( 1L << 16 ) +#define FT_FACE_FLAG_SBIX ( 1L << 17 ) +#define FT_FACE_FLAG_SBIX_OVERLAY ( 1L << 18 ) + + /************************************************************************** + * + * @section: + * font_testing_macros + * + */ /************************************************************************** * @@ -1334,6 +1543,13 @@ FT_BEGIN_HEADER ( !!( (face)->face_flags & FT_FACE_FLAG_FIXED_SIZES ) ) + /************************************************************************** + * + * @section: + * other_api_data + * + */ + /************************************************************************** * * @macro: @@ -1346,6 +1562,13 @@ FT_BEGIN_HEADER #define FT_HAS_FAST_GLYPHS( face ) 0 + /************************************************************************** + * + * @section: + * font_testing_macros + * + */ + /************************************************************************** * * @macro: @@ -1404,8 +1627,8 @@ FT_BEGIN_HEADER * * @description: * A macro that returns true whenever a face object has been altered by - * @FT_Set_MM_Design_Coordinates, @FT_Set_Var_Design_Coordinates, or - * @FT_Set_Var_Blend_Coordinates. + * @FT_Set_MM_Design_Coordinates, @FT_Set_Var_Design_Coordinates, + * @FT_Set_Var_Blend_Coordinates, or @FT_Set_MM_WeightVector. * * @since: * 2.9 @@ -1417,51 +1640,176 @@ FT_BEGIN_HEADER /************************************************************************** * - * @macro: - * FT_IS_CID_KEYED + * @macro: + * FT_IS_CID_KEYED + * + * @description: + * A macro that returns true whenever a face object contains a CID-keyed + * font. See the discussion of @FT_FACE_FLAG_CID_KEYED for more details. + * + * If this macro is true, all functions defined in @FT_CID_H are + * available. + * + */ +#define FT_IS_CID_KEYED( face ) \ + ( !!( (face)->face_flags & FT_FACE_FLAG_CID_KEYED ) ) + + + /************************************************************************** + * + * @macro: + * FT_IS_TRICKY + * + * @description: + * A macro that returns true whenever a face represents a 'tricky' font. + * See the discussion of @FT_FACE_FLAG_TRICKY for more details. + * + */ +#define FT_IS_TRICKY( face ) \ + ( !!( (face)->face_flags & FT_FACE_FLAG_TRICKY ) ) + + + /************************************************************************** + * + * @macro: + * FT_HAS_COLOR + * + * @description: + * A macro that returns true whenever a face object contains tables for + * color glyphs. + * + * @since: + * 2.5.1 + * + */ +#define FT_HAS_COLOR( face ) \ + ( !!( (face)->face_flags & FT_FACE_FLAG_COLOR ) ) + + + /************************************************************************** + * + * @macro: + * FT_HAS_SVG + * + * @description: + * A macro that returns true whenever a face object contains an 'SVG~' + * OpenType table. + * + * @since: + * 2.12 + */ +#define FT_HAS_SVG( face ) \ + ( !!( (face)->face_flags & FT_FACE_FLAG_SVG ) ) + + + /************************************************************************** + * + * @macro: + * FT_HAS_SBIX + * + * @description: + * A macro that returns true whenever a face object contains an 'sbix' + * OpenType table *and* outline glyphs. + * + * Currently, FreeType only supports bitmap glyphs in PNG format for this + * table (i.e., JPEG and TIFF formats are unsupported, as are + * Apple-specific formats not part of the OpenType specification). + * + * @note: + * For backward compatibility, a font with an 'sbix' table is treated as + * a bitmap-only face. Using @FT_Open_Face with + * @FT_PARAM_TAG_IGNORE_SBIX, an application can switch off 'sbix' + * handling so that the face is treated as an ordinary outline font with + * scalable outlines. + * + * Here is some pseudo code that roughly illustrates how to implement + * 'sbix' handling according to the OpenType specification. + * + * ``` + * if ( FT_HAS_SBIX( face ) ) + * { + * // open font as a scalable one without sbix handling + * FT_Face face2; + * FT_Parameter param = { FT_PARAM_TAG_IGNORE_SBIX, NULL }; + * FT_Open_Args args = { FT_OPEN_PARAMS | ..., + * ..., + * 1, ¶m }; + * + * + * FT_Open_Face( library, &args, 0, &face2 ); + * + * available_size` as necessary into + * `preferred_sizes`[*]> + * + * for ( i = 0; i < face->num_fixed_sizes; i++ ) + * { + * size = preferred_sizes[i].size; + * + * error = FT_Set_Pixel_Sizes( face, size, size ); + * + * + * // check whether we have a glyph in a bitmap strike + * error = FT_Load_Glyph( face, + * glyph_index, + * FT_LOAD_SBITS_ONLY | + * FT_LOAD_BITMAP_METRICS_ONLY ); + * if ( error == FT_Err_Invalid_Argument ) + * continue; + * else if ( error ) + * + * else + * break; + * } + * + * if ( i != face->num_fixed_sizes ) + * * - * @description: - * A macro that returns true whenever a face object contains a CID-keyed - * font. See the discussion of @FT_FACE_FLAG_CID_KEYED for more details. + * if ( i == face->num_fixed_sizes || + * FT_HAS_SBIX_OVERLAY( face ) ) + * + * } + * ``` * - * If this macro is true, all functions defined in @FT_CID_H are - * available. + * [*] Assuming a target value of 400dpi and available strike sizes 100, + * 200, 300, and 400dpi, a possible order might be [400, 200, 300, 100]: + * scaling 200dpi to 400dpi usually gives better results than scaling + * 300dpi to 400dpi; it is also much faster. However, scaling 100dpi to + * 400dpi can yield a too pixelated result, thus the preference might be + * 300dpi over 100dpi. * + * @since: + * 2.12 */ -#define FT_IS_CID_KEYED( face ) \ - ( !!( (face)->face_flags & FT_FACE_FLAG_CID_KEYED ) ) +#define FT_HAS_SBIX( face ) \ + ( !!( (face)->face_flags & FT_FACE_FLAG_SBIX ) ) /************************************************************************** * * @macro: - * FT_IS_TRICKY + * FT_HAS_SBIX_OVERLAY * * @description: - * A macro that returns true whenever a face represents a 'tricky' font. - * See the discussion of @FT_FACE_FLAG_TRICKY for more details. + * A macro that returns true whenever a face object contains an 'sbix' + * OpenType table with bit~1 in its `flags` field set, instructing the + * application to overlay the bitmap strike with the corresponding + * outline glyph. See @FT_HAS_SBIX for pseudo code how to use it. * + * @since: + * 2.12 */ -#define FT_IS_TRICKY( face ) \ - ( !!( (face)->face_flags & FT_FACE_FLAG_TRICKY ) ) +#define FT_HAS_SBIX_OVERLAY( face ) \ + ( !!( (face)->face_flags & FT_FACE_FLAG_SBIX_OVERLAY ) ) /************************************************************************** * - * @macro: - * FT_HAS_COLOR - * - * @description: - * A macro that returns true whenever a face object contains tables for - * color glyphs. - * - * @since: - * 2.5.1 + * @section: + * face_creation * */ -#define FT_HAS_COLOR( face ) \ - ( !!( (face)->face_flags & FT_FACE_FLAG_COLOR ) ) - /************************************************************************** * @@ -1489,6 +1837,13 @@ FT_BEGIN_HEADER #define FT_STYLE_FLAG_BOLD ( 1 << 1 ) + /************************************************************************** + * + * @section: + * other_api_data + * + */ + /************************************************************************** * * @type: @@ -1501,6 +1856,13 @@ FT_BEGIN_HEADER typedef struct FT_Size_InternalRec_* FT_Size_Internal; + /************************************************************************** + * + * @section: + * sizing_and_scaling + * + */ + /************************************************************************** * * @struct: @@ -1652,6 +2014,13 @@ FT_BEGIN_HEADER } FT_SizeRec; + /************************************************************************** + * + * @section: + * other_api_data + * + */ + /************************************************************************** * * @struct: @@ -1683,6 +2052,13 @@ FT_BEGIN_HEADER typedef struct FT_Slot_InternalRec_* FT_Slot_Internal; + /************************************************************************** + * + * @section: + * glyph_retrieval + * + */ + /************************************************************************** * * @struct: @@ -1727,13 +2103,13 @@ FT_BEGIN_HEADER * The advance width of the unhinted glyph. Its value is expressed in * 16.16 fractional pixels, unless @FT_LOAD_LINEAR_DESIGN is set when * loading the glyph. This field can be important to perform correct - * WYSIWYG layout. Only relevant for outline glyphs. + * WYSIWYG layout. Only relevant for scalable glyphs. * * linearVertAdvance :: * The advance height of the unhinted glyph. Its value is expressed in * 16.16 fractional pixels, unless @FT_LOAD_LINEAR_DESIGN is set when * loading the glyph. This field can be important to perform correct - * WYSIWYG layout. Only relevant for outline glyphs. + * WYSIWYG layout. Only relevant for scalable glyphs. * * advance :: * This shorthand is, depending on @FT_LOAD_IGNORE_TRANSFORM, the @@ -1927,6 +2303,13 @@ FT_BEGIN_HEADER /*************************************************************************/ + /************************************************************************** + * + * @section: + * library_setup + * + */ + /************************************************************************** * * @function: @@ -1984,6 +2367,13 @@ FT_BEGIN_HEADER FT_Done_FreeType( FT_Library library ); + /************************************************************************** + * + * @section: + * face_creation + * + */ + /************************************************************************** * * @enum: @@ -2078,7 +2468,8 @@ FT_BEGIN_HEADER * The size in bytes of the file in memory. * * pathname :: - * A pointer to an 8-bit file pathname. The pointer is not owned by + * A pointer to an 8-bit file pathname, which must be a C~string (i.e., + * no null bytes except at the very end). The pointer is not owned by * FreeType. * * stream :: @@ -2097,8 +2488,7 @@ FT_BEGIN_HEADER * Extra parameters passed to the font driver when opening a new face. * * @note: - * The stream type is determined by the contents of `flags` that are - * tested in the following order by @FT_Open_Face: + * The stream type is determined by the contents of `flags`: * * If the @FT_OPEN_MEMORY bit is set, assume that this is a memory file * of `memory_size` bytes, located at `memory_address`. The data are not @@ -2111,6 +2501,9 @@ FT_BEGIN_HEADER * Otherwise, if the @FT_OPEN_PATHNAME bit is set, assume that this is a * normal file and use `pathname` to open it. * + * If none of the above bits are set or if multiple are set at the same + * time, the flags are invalid and @FT_Open_Face fails. + * * If the @FT_OPEN_DRIVER bit is set, @FT_Open_Face only tries to open * the file with the driver whose handler is in `driver`. * @@ -2163,6 +2556,13 @@ FT_BEGIN_HEADER * FreeType error code. 0~means success. * * @note: + * The `pathname` string should be recognizable as such by a standard + * `fopen` call on your system; in particular, this means that `pathname` + * must not contain null bytes. If that is not sufficient to address all + * file name possibilities (for example, to handle wide character file + * names on Windows in UTF-16 encoding) you might use @FT_Open_Face to + * pass a memory array or a stream object instead. + * * Use @FT_Done_Face to destroy the created @FT_Face object (along with * its slot and sizes). */ @@ -2276,13 +2676,17 @@ FT_BEGIN_HEADER * Each new face object created with this function also owns a default * @FT_Size object, accessible as `face->size`. * - * One @FT_Library instance can have multiple face objects, this is, + * One @FT_Library instance can have multiple face objects, that is, * @FT_Open_Face and its siblings can be called multiple times using the * same `library` argument. * * See the discussion of reference counters in the description of * @FT_Reference_Face. * + * If `FT_OPEN_STREAM` is set in `args->flags`, the stream in + * `args->stream` is automatically closed before this function returns + * any error (including `FT_Err_Invalid_Argument`). + * * @example: * To loop over all faces, use code similar to the following snippet * (omitting the error handling). @@ -2414,8 +2818,8 @@ FT_BEGIN_HEADER * stream attachments. */ FT_EXPORT( FT_Error ) - FT_Attach_Stream( FT_Face face, - FT_Open_Args* parameters ); + FT_Attach_Stream( FT_Face face, + const FT_Open_Args* parameters ); /************************************************************************** @@ -2441,6 +2845,7 @@ FT_BEGIN_HEADER * * @since: * 2.4.2 + * */ FT_EXPORT( FT_Error ) FT_Reference_Face( FT_Face face ); @@ -2470,6 +2875,13 @@ FT_BEGIN_HEADER FT_Done_Face( FT_Face face ); + /************************************************************************** + * + * @section: + * sizing_and_scaling + * + */ + /************************************************************************** * * @function: @@ -2499,7 +2911,7 @@ FT_BEGIN_HEADER * silently uses outlines if there is no bitmap for a given glyph index. * * For GX and OpenType variation fonts, a bitmap strike makes sense only - * if the default instance is active (this is, no glyph variation takes + * if the default instance is active (that is, no glyph variation takes * place); otherwise, FreeType simply ignores bitmap strikes. The same * is true for all named instances that are different from the default * instance. @@ -2665,8 +3077,8 @@ FT_BEGIN_HEADER * 'https://www.freetype.org/freetype2/docs/glyphs/glyphs-2.html'. * * Contrary to @FT_Set_Char_Size, this function doesn't have special code - * to normalize zero-valued widths, heights, or resolutions (which lead - * to errors in most cases). + * to normalize zero-valued widths, heights, or resolutions, which are + * treated as @FT_LOAD_NO_SCALE. * * Don't use this function if you are using the FreeType cache API. */ @@ -2762,6 +3174,13 @@ FT_BEGIN_HEADER FT_UInt pixel_height ); + /************************************************************************** + * + * @section: + * glyph_retrieval + * + */ + /************************************************************************** * * @function: @@ -2782,7 +3201,7 @@ FT_BEGIN_HEADER * * load_flags :: * A flag indicating what to load for this glyph. The @FT_LOAD_XXX - * constants can be used to control the glyph loading process (e.g., + * flags can be used to control the glyph loading process (e.g., * whether the outline should be scaled, whether to load bitmaps or * not, whether to hint the outline, etc). * @@ -2790,11 +3209,13 @@ FT_BEGIN_HEADER * FreeType error code. 0~means success. * * @note: - * The loaded glyph may be transformed. See @FT_Set_Transform for the - * details. + * For proper scaling and hinting, the active @FT_Size object owned by + * the face has to be meaningfully initialized by calling + * @FT_Set_Char_Size before this function, for example. The loaded + * glyph may be transformed. See @FT_Set_Transform for the details. * * For subsetted CID-keyed fonts, `FT_Err_Invalid_Argument` is returned - * for invalid CID values (this is, for CID values that don't have a + * for invalid CID values (that is, for CID values that don't have a * corresponding glyph in the font). See the discussion of the * @FT_FACE_FLAG_CID_KEYED flag for more details. * @@ -2808,6 +3229,13 @@ FT_BEGIN_HEADER FT_Int32 load_flags ); + /************************************************************************** + * + * @section: + * character_mapping + * + */ + /************************************************************************** * * @function: @@ -2851,6 +3279,13 @@ FT_BEGIN_HEADER FT_Int32 load_flags ); + /************************************************************************** + * + * @section: + * glyph_retrieval + * + */ + /************************************************************************** * * @enum: @@ -2881,19 +3316,21 @@ FT_BEGIN_HEADER * * FT_LOAD_NO_SCALE :: * Don't scale the loaded outline glyph but keep it in font units. + * This flag is also assumed if @FT_Size owned by the face was not + * properly initialized. * * This flag implies @FT_LOAD_NO_HINTING and @FT_LOAD_NO_BITMAP, and * unsets @FT_LOAD_RENDER. * * If the font is 'tricky' (see @FT_FACE_FLAG_TRICKY for more), using * `FT_LOAD_NO_SCALE` usually yields meaningless outlines because the - * subglyphs must be scaled and positioned with hinting instructions. + * subglyphs must be scaled and positioned with hinting instructions. * This can be solved by loading the font without `FT_LOAD_NO_SCALE` * and setting the character size to `font->units_per_EM`. * * FT_LOAD_NO_HINTING :: * Disable hinting. This generally generates 'blurrier' bitmap glyphs - * when the glyph are rendered in any of the anti-aliased modes. See + * when the glyphs are rendered in any of the anti-aliased modes. See * also the note below. * * This flag is implied by @FT_LOAD_NO_SCALE. @@ -2911,6 +3348,15 @@ FT_BEGIN_HEADER * * @FT_LOAD_NO_SCALE always sets this flag. * + * FT_LOAD_SBITS_ONLY :: + * [Since 2.12] This is the opposite of @FT_LOAD_NO_BITMAP, more or + * less: @FT_Load_Glyph returns `FT_Err_Invalid_Argument` if the face + * contains a bitmap strike for the given size (or the strike selected + * by @FT_Select_Size) but there is no glyph in the strike. + * + * Note that this load flag was part of FreeType since version 2.0.6 + * but previously tagged as internal. + * * FT_LOAD_VERTICAL_LAYOUT :: * Load the glyph for vertical text layout. In particular, the * `advance` value in the @FT_GlyphSlotRec structure is set to the @@ -2967,25 +3413,39 @@ FT_BEGIN_HEADER * Disable the auto-hinter. See also the note below. * * FT_LOAD_COLOR :: - * Load colored glyphs. There are slight differences depending on the - * font format. - * - * [Since 2.5] Load embedded color bitmap images. The resulting color - * bitmaps, if available, will have the @FT_PIXEL_MODE_BGRA format, - * with pre-multiplied color channels. If the flag is not set and - * color bitmaps are found, they are converted to 256-level gray - * bitmaps, using the @FT_PIXEL_MODE_GRAY format. - * - * [Since 2.10, experimental] If the glyph index contains an entry in + * Load colored glyphs. FreeType searches in the following order; + * there are slight differences depending on the font format. + * + * [Since 2.5] Load embedded color bitmap images (provided + * @FT_LOAD_NO_BITMAP is not set). The resulting color bitmaps, if + * available, have the @FT_PIXEL_MODE_BGRA format, with pre-multiplied + * color channels. If the flag is not set and color bitmaps are found, + * they are converted to 256-level gray bitmaps, using the + * @FT_PIXEL_MODE_GRAY format. + * + * [Since 2.12] If the glyph index maps to an entry in the face's + * 'SVG~' table, load the associated SVG document from this table and + * set the `format` field of @FT_GlyphSlotRec to @FT_GLYPH_FORMAT_SVG + * ([since 2.13.1] provided @FT_LOAD_NO_SVG is not set). Note that + * FreeType itself can't render SVG documents; however, the library + * provides hooks to seamlessly integrate an external renderer. See + * sections @ot_svg_driver and @svg_fonts for more. + * + * [Since 2.10, experimental] If the glyph index maps to an entry in * the face's 'COLR' table with a 'CPAL' palette table (as defined in * the OpenType specification), make @FT_Render_Glyph provide a default * blending of the color glyph layers associated with the glyph index, * using the same bitmap format as embedded color bitmap images. This - * is mainly for convenience; for full control of color layers use + * is mainly for convenience and works only for glyphs in 'COLR' v0 + * tables (or glyphs in 'COLR' v1 tables that exclusively use v0 + * features). For full control of color layers use * @FT_Get_Color_Glyph_Layer and FreeType's color functions like * @FT_Palette_Select instead of setting @FT_LOAD_COLOR for rendering * so that the client application can handle blending by itself. * + * FT_LOAD_NO_SVG :: + * [Since 2.13.1] Ignore SVG glyph data when loading. + * * FT_LOAD_COMPUTE_METRICS :: * [Since 2.6.1] Compute glyph metrics from the glyph data, without the * use of bundled metrics tables (for example, the 'hdmx' table in @@ -3032,30 +3492,32 @@ FT_BEGIN_HEADER * */ #define FT_LOAD_DEFAULT 0x0 -#define FT_LOAD_NO_SCALE ( 1L << 0 ) -#define FT_LOAD_NO_HINTING ( 1L << 1 ) -#define FT_LOAD_RENDER ( 1L << 2 ) -#define FT_LOAD_NO_BITMAP ( 1L << 3 ) -#define FT_LOAD_VERTICAL_LAYOUT ( 1L << 4 ) -#define FT_LOAD_FORCE_AUTOHINT ( 1L << 5 ) -#define FT_LOAD_CROP_BITMAP ( 1L << 6 ) -#define FT_LOAD_PEDANTIC ( 1L << 7 ) -#define FT_LOAD_IGNORE_GLOBAL_ADVANCE_WIDTH ( 1L << 9 ) +#define FT_LOAD_NO_SCALE ( 1L << 0 ) +#define FT_LOAD_NO_HINTING ( 1L << 1 ) +#define FT_LOAD_RENDER ( 1L << 2 ) +#define FT_LOAD_NO_BITMAP ( 1L << 3 ) +#define FT_LOAD_VERTICAL_LAYOUT ( 1L << 4 ) +#define FT_LOAD_FORCE_AUTOHINT ( 1L << 5 ) +#define FT_LOAD_CROP_BITMAP ( 1L << 6 ) +#define FT_LOAD_PEDANTIC ( 1L << 7 ) +#define FT_LOAD_IGNORE_GLOBAL_ADVANCE_WIDTH ( 1L << 9 ) #define FT_LOAD_NO_RECURSE ( 1L << 10 ) #define FT_LOAD_IGNORE_TRANSFORM ( 1L << 11 ) #define FT_LOAD_MONOCHROME ( 1L << 12 ) #define FT_LOAD_LINEAR_DESIGN ( 1L << 13 ) +#define FT_LOAD_SBITS_ONLY ( 1L << 14 ) #define FT_LOAD_NO_AUTOHINT ( 1L << 15 ) /* Bits 16-19 are used by `FT_LOAD_TARGET_` */ #define FT_LOAD_COLOR ( 1L << 20 ) #define FT_LOAD_COMPUTE_METRICS ( 1L << 21 ) #define FT_LOAD_BITMAP_METRICS_ONLY ( 1L << 22 ) +#define FT_LOAD_NO_SVG ( 1L << 24 ) /* */ /* used internally only by certain font drivers */ -#define FT_LOAD_ADVANCE_ONLY ( 1L << 8 ) -#define FT_LOAD_SBITS_ONLY ( 1L << 14 ) +#define FT_LOAD_ADVANCE_ONLY ( 1L << 8 ) +#define FT_LOAD_SVG_ONLY ( 1L << 23 ) /************************************************************************** @@ -3145,7 +3607,7 @@ FT_BEGIN_HEADER * necessary to empty the cache after a mode switch to avoid false hits. * */ -#define FT_LOAD_TARGET_( x ) ( (FT_Int32)( (x) & 15 ) << 16 ) +#define FT_LOAD_TARGET_( x ) ( FT_STATIC_CAST( FT_Int32, (x) & 15 ) << 16 ) #define FT_LOAD_TARGET_NORMAL FT_LOAD_TARGET_( FT_RENDER_MODE_NORMAL ) #define FT_LOAD_TARGET_LIGHT FT_LOAD_TARGET_( FT_RENDER_MODE_LIGHT ) @@ -3164,8 +3626,16 @@ FT_BEGIN_HEADER * @FT_LOAD_TARGET_XXX value. * */ -#define FT_LOAD_TARGET_MODE( x ) ( (FT_Render_Mode)( ( (x) >> 16 ) & 15 ) ) +#define FT_LOAD_TARGET_MODE( x ) \ + FT_STATIC_CAST( FT_Render_Mode, ( (x) >> 16 ) & 15 ) + + /************************************************************************** + * + * @section: + * sizing_and_scaling + * + */ /************************************************************************** * @@ -3185,9 +3655,16 @@ FT_BEGIN_HEADER * A pointer to the transformation's 2x2 matrix. Use `NULL` for the * identity matrix. * delta :: - * A pointer to the translation vector. Use `NULL` for the null vector. + * A pointer to the translation vector. Use `NULL` for the null + * vector. * * @note: + * This function is provided as a convenience, but keep in mind that + * @FT_Matrix coefficients are only 16.16 fixed-point values, which can + * limit the accuracy of the results. Using floating-point computations + * to perform the transform directly in client code instead will always + * yield better numbers. + * * The transformation is only applied to scalable image formats after the * glyph has been loaded. It means that hinting is unaltered by the * transformation and is performed on the character size given in the @@ -3202,6 +3679,46 @@ FT_BEGIN_HEADER FT_Vector* delta ); + /************************************************************************** + * + * @function: + * FT_Get_Transform + * + * @description: + * Return the transformation that is applied to glyph images when they + * are loaded into a glyph slot through @FT_Load_Glyph. See + * @FT_Set_Transform for more details. + * + * @input: + * face :: + * A handle to the source face object. + * + * @output: + * matrix :: + * A pointer to a transformation's 2x2 matrix. Set this to NULL if you + * are not interested in the value. + * + * delta :: + * A pointer to a translation vector. Set this to NULL if you are not + * interested in the value. + * + * @since: + * 2.11 + * + */ + FT_EXPORT( void ) + FT_Get_Transform( FT_Face face, + FT_Matrix* matrix, + FT_Vector* delta ); + + + /************************************************************************** + * + * @section: + * glyph_retrieval + * + */ + /************************************************************************** * * @enum: @@ -3220,6 +3737,10 @@ FT_BEGIN_HEADER * correction to correctly render non-monochrome glyph bitmaps onto a * surface; see @FT_Render_Glyph. * + * The @FT_RENDER_MODE_SDF is a special render mode that uses up to 256 + * distance values, indicating the signed distance from the grid position + * to the nearest outline. + * * @values: * FT_RENDER_MODE_NORMAL :: * Default render mode; it corresponds to 8-bit anti-aliased bitmaps. @@ -3245,19 +3766,88 @@ FT_BEGIN_HEADER * bitmaps that are 3~times the height of the original glyph outline in * pixels and use the @FT_PIXEL_MODE_LCD_V mode. * - * @note: - * Should you define `FT_CONFIG_OPTION_SUBPIXEL_RENDERING` in your - * `ftoption.h`, which enables patented ClearType-style rendering, the - * LCD-optimized glyph bitmaps should be filtered to reduce color fringes - * inherent to this technology. You can either set up LCD filtering with - * @FT_Library_SetLcdFilter or @FT_Face_Properties, or do the filtering - * yourself. The default FreeType LCD rendering technology does not - * require filtering. + * FT_RENDER_MODE_SDF :: + * This mode corresponds to 8-bit, single-channel signed distance field + * (SDF) bitmaps. Each pixel in the SDF grid is the value from the + * pixel's position to the nearest glyph's outline. The distances are + * calculated from the center of the pixel and are positive if they are + * filled by the outline (i.e., inside the outline) and negative + * otherwise. Check the note below on how to convert the output values + * to usable data. * + * @note: * The selected render mode only affects vector glyphs of a font. * Embedded bitmaps often have a different pixel mode like * @FT_PIXEL_MODE_MONO. You can use @FT_Bitmap_Convert to transform them * into 8-bit pixmaps. + * + * For @FT_RENDER_MODE_SDF the output bitmap buffer contains normalized + * distances that are packed into unsigned 8-bit values. To get pixel + * values in floating point representation use the following pseudo-C + * code for the conversion. + * + * ``` + * // Load glyph and render using FT_RENDER_MODE_SDF, + * // then use the output buffer as follows. + * + * ... + * FT_Byte buffer = glyph->bitmap->buffer; + * + * + * for pixel in buffer + * { + * // `sd` is the signed distance and `spread` is the current spread; + * // the default spread is 2 and can be changed. + * + * float sd = (float)pixel - 128.0f; + * + * + * // Convert to pixel values. + * sd = ( sd / 128.0f ) * spread; + * + * // Store `sd` in a buffer or use as required. + * } + * + * ``` + * + * FreeType has two rasterizers for generating SDF, namely: + * + * 1. `sdf` for generating SDF directly from glyph's outline, and + * + * 2. `bsdf` for generating SDF from rasterized bitmaps. + * + * Depending on the glyph type (i.e., outline or bitmap), one of the two + * rasterizers is chosen at runtime and used for generating SDFs. To + * force the use of `bsdf` you should render the glyph with any of the + * FreeType's other rendering modes (e.g., `FT_RENDER_MODE_NORMAL`) and + * then re-render with `FT_RENDER_MODE_SDF`. + * + * There are some issues with stability and possible failures of the SDF + * renderers (specifically `sdf`). + * + * 1. The `sdf` rasterizer is sensitive to really small features (e.g., + * sharp turns that are less than 1~pixel) and imperfections in the + * glyph's outline, causing artifacts in the final output. + * + * 2. The `sdf` rasterizer has limited support for handling intersecting + * contours and *cannot* handle self-intersecting contours whatsoever. + * Self-intersection happens when a single connected contour + * intersects itself at some point; having these in your font + * definitely poses a problem to the rasterizer and cause artifacts, + * too. + * + * 3. Generating SDF for really small glyphs may result in undesirable + * output; the pixel grid (which stores distance information) becomes + * too coarse. + * + * 4. Since the output buffer is normalized, precision at smaller spreads + * is greater than precision at larger spread values because the + * output range of [0..255] gets mapped to a smaller SDF range. A + * spread of~2 should be sufficient in most cases. + * + * Points (1) and (2) can be avoided by using the `bsdf` rasterizer, + * which is more stable than the `sdf` rasterizer in general. + * */ typedef enum FT_Render_Mode_ { @@ -3266,6 +3856,7 @@ FT_BEGIN_HEADER FT_RENDER_MODE_MONO, FT_RENDER_MODE_LCD, FT_RENDER_MODE_LCD_V, + FT_RENDER_MODE_SDF, FT_RENDER_MODE_MAX @@ -3297,7 +3888,7 @@ FT_BEGIN_HEADER * @FT_Render_Mode for a list of possible values. * * If @FT_RENDER_MODE_NORMAL is used, a previous call of @FT_Load_Glyph - * with flag @FT_LOAD_COLOR makes FT_Render_Glyph provide a default + * with flag @FT_LOAD_COLOR makes `FT_Render_Glyph` provide a default * blending of colored glyph layers associated with the current glyph * slot (provided the font contains such layers) instead of rendering * the glyph slot's outline. This is an experimental feature; see @@ -3307,9 +3898,6 @@ FT_BEGIN_HEADER * FreeType error code. 0~means success. * * @note: - * To get meaningful results, font scaling values must be set with - * functions like @FT_Set_Char_Size before calling `FT_Render_Glyph`. - * * When FreeType outputs a bitmap of a glyph, it really outputs an alpha * coverage map. If a pixel is completely covered by a filled-in * outline, the bitmap contains 0xFF at that pixel, meaning that @@ -3353,7 +3941,8 @@ FT_BEGIN_HEADER * * which is known as the OVER operator. * - * To correctly composite an antialiased pixel of a glyph onto a surface, + * To correctly composite an anti-aliased pixel of a glyph onto a + * surface, * * 1. take the foreground and background colors (e.g., in sRGB space) * and apply gamma to get them in a linear space, @@ -3467,145 +4056,69 @@ FT_BEGIN_HEADER * Only horizontal layouts (left-to-right & right-to-left) are supported * by this method. Other layouts, or more sophisticated kernings, are * out of the scope of this API function -- they can be implemented - * through format-specific interfaces. - * - * Kerning for OpenType fonts implemented in a 'GPOS' table is not - * supported; use @FT_HAS_KERNING to find out whether a font has data - * that can be extracted with `FT_Get_Kerning`. - */ - FT_EXPORT( FT_Error ) - FT_Get_Kerning( FT_Face face, - FT_UInt left_glyph, - FT_UInt right_glyph, - FT_UInt kern_mode, - FT_Vector *akerning ); - - - /************************************************************************** - * - * @function: - * FT_Get_Track_Kerning - * - * @description: - * Return the track kerning for a given face object at a given size. - * - * @input: - * face :: - * A handle to a source face object. - * - * point_size :: - * The point size in 16.16 fractional points. - * - * degree :: - * The degree of tightness. Increasingly negative values represent - * tighter track kerning, while increasingly positive values represent - * looser track kerning. Value zero means no track kerning. - * - * @output: - * akerning :: - * The kerning in 16.16 fractional points, to be uniformly applied - * between all glyphs. - * - * @return: - * FreeType error code. 0~means success. - * - * @note: - * Currently, only the Type~1 font driver supports track kerning, using - * data from AFM files (if attached with @FT_Attach_File or - * @FT_Attach_Stream). - * - * Only very few AFM files come with track kerning data; please refer to - * Adobe's AFM specification for more details. - */ - FT_EXPORT( FT_Error ) - FT_Get_Track_Kerning( FT_Face face, - FT_Fixed point_size, - FT_Int degree, - FT_Fixed* akerning ); - - - /************************************************************************** - * - * @function: - * FT_Get_Glyph_Name - * - * @description: - * Retrieve the ASCII name of a given glyph in a face. This only works - * for those faces where @FT_HAS_GLYPH_NAMES(face) returns~1. - * - * @input: - * face :: - * A handle to a source face object. - * - * glyph_index :: - * The glyph index. - * - * buffer_max :: - * The maximum number of bytes available in the buffer. - * - * @output: - * buffer :: - * A pointer to a target buffer where the name is copied to. - * - * @return: - * FreeType error code. 0~means success. - * - * @note: - * An error is returned if the face doesn't provide glyph names or if the - * glyph index is invalid. In all cases of failure, the first byte of - * `buffer` is set to~0 to indicate an empty name. - * - * The glyph name is truncated to fit within the buffer if it is too - * long. The returned string is always zero-terminated. - * - * Be aware that FreeType reorders glyph indices internally so that glyph - * index~0 always corresponds to the 'missing glyph' (called '.notdef'). + * through format-specific interfaces. * - * This function always returns an error if the config macro - * `FT_CONFIG_OPTION_NO_GLYPH_NAMES` is not defined in `ftoption.h`. + * Kerning for OpenType fonts implemented in a 'GPOS' table is not + * supported; use @FT_HAS_KERNING to find out whether a font has data + * that can be extracted with `FT_Get_Kerning`. */ FT_EXPORT( FT_Error ) - FT_Get_Glyph_Name( FT_Face face, - FT_UInt glyph_index, - FT_Pointer buffer, - FT_UInt buffer_max ); + FT_Get_Kerning( FT_Face face, + FT_UInt left_glyph, + FT_UInt right_glyph, + FT_UInt kern_mode, + FT_Vector *akerning ); /************************************************************************** * * @function: - * FT_Get_Postscript_Name + * FT_Get_Track_Kerning * * @description: - * Retrieve the ASCII PostScript name of a given face, if available. - * This only works with PostScript, TrueType, and OpenType fonts. + * Return the track kerning for a given face object at a given size. * * @input: * face :: - * A handle to the source face object. + * A handle to a source face object. + * + * point_size :: + * The point size in 16.16 fractional points. + * + * degree :: + * The degree of tightness. Increasingly negative values represent + * tighter track kerning, while increasingly positive values represent + * looser track kerning. Value zero means no track kerning. + * + * @output: + * akerning :: + * The kerning in 16.16 fractional points, to be uniformly applied + * between all glyphs. * * @return: - * A pointer to the face's PostScript name. `NULL` if unavailable. + * FreeType error code. 0~means success. * * @note: - * The returned pointer is owned by the face and is destroyed with it. + * Currently, only the Type~1 font driver supports track kerning, using + * data from AFM files (if attached with @FT_Attach_File or + * @FT_Attach_Stream). * - * For variation fonts, this string changes if you select a different - * instance, and you have to call `FT_Get_PostScript_Name` again to - * retrieve it. FreeType follows Adobe TechNote #5902, 'Generating - * PostScript Names for Fonts Using OpenType Font Variations'. + * Only very few AFM files come with track kerning data; please refer to + * Adobe's AFM specification for more details. + */ + FT_EXPORT( FT_Error ) + FT_Get_Track_Kerning( FT_Face face, + FT_Fixed point_size, + FT_Int degree, + FT_Fixed* akerning ); + + + /************************************************************************** * - * https://download.macromedia.com/pub/developer/opentype/tech-notes/5902.AdobePSNameGeneration.html + * @section: + * character_mapping * - * [Since 2.9] Special PostScript names for named instances are only - * returned if the named instance is set with @FT_Set_Named_Instance (and - * the font has corresponding entries in its 'fvar' table). If - * @FT_IS_VARIATION returns true, the algorithmically derived PostScript - * name is provided, not looking up special entries for named instances. */ - FT_EXPORT( const char* ) - FT_Get_Postscript_Name( FT_Face face ); - /************************************************************************** * @@ -3823,6 +4336,13 @@ FT_BEGIN_HEADER FT_UInt *agindex ); + /************************************************************************** + * + * @section: + * face_creation + * + */ + /************************************************************************** * * @function: @@ -3921,13 +4441,21 @@ FT_BEGIN_HEADER FT_Parameter* properties ); + /************************************************************************** + * + * @section: + * information_retrieval + * + */ + /************************************************************************** * * @function: * FT_Get_Name_Index * * @description: - * Return the glyph index of a given glyph name. + * Return the glyph index of a given glyph name. This only works + * for those faces where @FT_HAS_GLYPH_NAMES returns true. * * @input: * face :: @@ -3938,12 +4466,108 @@ FT_BEGIN_HEADER * * @return: * The glyph index. 0~means 'undefined character code'. + * + * @note: + * Acceptable glyph names might come from the [Adobe Glyph + * List](https://github.com/adobe-type-tools/agl-aglfn). See + * @FT_Get_Glyph_Name for the inverse functionality. + * + * This function has limited capabilities if the config macro + * `FT_CONFIG_OPTION_POSTSCRIPT_NAMES` is not defined in `ftoption.h`: + * It then works only for fonts that actually embed glyph names (which + * many recent OpenType fonts do not). */ FT_EXPORT( FT_UInt ) FT_Get_Name_Index( FT_Face face, const FT_String* glyph_name ); + /************************************************************************** + * + * @function: + * FT_Get_Glyph_Name + * + * @description: + * Retrieve the ASCII name of a given glyph in a face. This only works + * for those faces where @FT_HAS_GLYPH_NAMES returns true. + * + * @input: + * face :: + * A handle to a source face object. + * + * glyph_index :: + * The glyph index. + * + * buffer_max :: + * The maximum number of bytes available in the buffer. + * + * @output: + * buffer :: + * A pointer to a target buffer where the name is copied to. + * + * @return: + * FreeType error code. 0~means success. + * + * @note: + * An error is returned if the face doesn't provide glyph names or if the + * glyph index is invalid. In all cases of failure, the first byte of + * `buffer` is set to~0 to indicate an empty name. + * + * The glyph name is truncated to fit within the buffer if it is too + * long. The returned string is always zero-terminated. + * + * Be aware that FreeType reorders glyph indices internally so that glyph + * index~0 always corresponds to the 'missing glyph' (called '.notdef'). + * + * This function has limited capabilities if the config macro + * `FT_CONFIG_OPTION_POSTSCRIPT_NAMES` is not defined in `ftoption.h`: + * It then works only for fonts that actually embed glyph names (which + * many recent OpenType fonts do not). + */ + FT_EXPORT( FT_Error ) + FT_Get_Glyph_Name( FT_Face face, + FT_UInt glyph_index, + FT_Pointer buffer, + FT_UInt buffer_max ); + + + /************************************************************************** + * + * @function: + * FT_Get_Postscript_Name + * + * @description: + * Retrieve the ASCII PostScript name of a given face, if available. + * This only works with PostScript, TrueType, and OpenType fonts. + * + * @input: + * face :: + * A handle to the source face object. + * + * @return: + * A pointer to the face's PostScript name. `NULL` if unavailable. + * + * @note: + * The returned pointer is owned by the face and is destroyed with it. + * + * For variation fonts, this string changes if you select a different + * instance, and you have to call `FT_Get_PostScript_Name` again to + * retrieve it. FreeType follows Adobe TechNote #5902, 'Generating + * PostScript Names for Fonts Using OpenType Font Variations'. + * + * https://download.macromedia.com/pub/developer/opentype/tech-notes/5902.AdobePSNameGeneration.html + * + * [Since 2.9] Special PostScript names for named instances are only + * returned if the named instance is set with @FT_Set_Named_Instance (and + * the font has corresponding entries in its 'fvar' table or is the + * default named instance). If @FT_IS_VARIATION returns true, the + * algorithmically derived PostScript name is provided, not looking up + * special entries for named instances. + */ + FT_EXPORT( const char* ) + FT_Get_Postscript_Name( FT_Face face ); + + /************************************************************************** * * @enum: @@ -4030,175 +4654,6 @@ FT_BEGIN_HEADER FT_Matrix *p_transform ); - /************************************************************************** - * - * @section: - * layer_management - * - * @title: - * Glyph Layer Management - * - * @abstract: - * Retrieving and manipulating OpenType's 'COLR' table data. - * - * @description: - * The functions described here allow access of colored glyph layer data - * in OpenType's 'COLR' tables. - */ - - - /************************************************************************** - * - * @struct: - * FT_LayerIterator - * - * @description: - * This iterator object is needed for @FT_Get_Color_Glyph_Layer. - * - * @fields: - * num_layers :: - * The number of glyph layers for the requested glyph index. Will be - * set by @FT_Get_Color_Glyph_Layer. - * - * layer :: - * The current layer. Will be set by @FT_Get_Color_Glyph_Layer. - * - * p :: - * An opaque pointer into 'COLR' table data. The caller must set this - * to `NULL` before the first call of @FT_Get_Color_Glyph_Layer. - */ - typedef struct FT_LayerIterator_ - { - FT_UInt num_layers; - FT_UInt layer; - FT_Byte* p; - - } FT_LayerIterator; - - - /************************************************************************** - * - * @function: - * FT_Get_Color_Glyph_Layer - * - * @description: - * This is an interface to the 'COLR' table in OpenType fonts to - * iteratively retrieve the colored glyph layers associated with the - * current glyph slot. - * - * https://docs.microsoft.com/en-us/typography/opentype/spec/colr - * - * The glyph layer data for a given glyph index, if present, provides an - * alternative, multi-colour glyph representation: Instead of rendering - * the outline or bitmap with the given glyph index, glyphs with the - * indices and colors returned by this function are rendered layer by - * layer. - * - * The returned elements are ordered in the z~direction from bottom to - * top; the 'n'th element should be rendered with the associated palette - * color and blended on top of the already rendered layers (elements 0, - * 1, ..., n-1). - * - * @input: - * face :: - * A handle to the parent face object. - * - * base_glyph :: - * The glyph index the colored glyph layers are associated with. - * - * @inout: - * iterator :: - * An @FT_LayerIterator object. For the first call you should set - * `iterator->p` to `NULL`. For all following calls, simply use the - * same object again. - * - * @output: - * aglyph_index :: - * The glyph index of the current layer. - * - * acolor_index :: - * The color index into the font face's color palette of the current - * layer. The value 0xFFFF is special; it doesn't reference a palette - * entry but indicates that the text foreground color should be used - * instead (to be set up by the application outside of FreeType). - * - * The color palette can be retrieved with @FT_Palette_Select. - * - * @return: - * Value~1 if everything is OK. If there are no more layers (or if there - * are no layers at all), value~0 gets returned. In case of an error, - * value~0 is returned also. - * - * @note: - * This function is necessary if you want to handle glyph layers by - * yourself. In particular, functions that operate with @FT_GlyphRec - * objects (like @FT_Get_Glyph or @FT_Glyph_To_Bitmap) don't have access - * to this information. - * - * Note that @FT_Render_Glyph is able to handle colored glyph layers - * automatically if the @FT_LOAD_COLOR flag is passed to a previous call - * to @FT_Load_Glyph. [This is an experimental feature.] - * - * @example: - * ``` - * FT_Color* palette; - * FT_LayerIterator iterator; - * - * FT_Bool have_layers; - * FT_UInt layer_glyph_index; - * FT_UInt layer_color_index; - * - * - * error = FT_Palette_Select( face, palette_index, &palette ); - * if ( error ) - * palette = NULL; - * - * iterator.p = NULL; - * have_layers = FT_Get_Color_Glyph_Layer( face, - * glyph_index, - * &layer_glyph_index, - * &layer_color_index, - * &iterator ); - * - * if ( palette && have_layers ) - * { - * do - * { - * FT_Color layer_color; - * - * - * if ( layer_color_index == 0xFFFF ) - * layer_color = text_foreground_color; - * else - * layer_color = palette[layer_color_index]; - * - * // Load and render glyph `layer_glyph_index', then - * // blend resulting pixmap (using color `layer_color') - * // with previously created pixmaps. - * - * } while ( FT_Get_Color_Glyph_Layer( face, - * glyph_index, - * &layer_glyph_index, - * &layer_color_index, - * &iterator ) ); - * } - * ``` - */ - FT_EXPORT( FT_Bool ) - FT_Get_Color_Glyph_Layer( FT_Face face, - FT_UInt base_glyph, - FT_UInt *aglyph_index, - FT_UInt *acolor_index, - FT_LayerIterator* iterator ); - - - /************************************************************************** - * - * @section: - * base_interface - * - */ - /************************************************************************** * * @enum: @@ -4282,6 +4737,7 @@ FT_BEGIN_HEADER * * @since: * 2.3.8 + * */ FT_EXPORT( FT_UShort ) FT_Get_FSType_Flags( FT_Face face ); @@ -4375,6 +4831,7 @@ FT_BEGIN_HEADER * * @since: * 2.3.6 + * */ FT_EXPORT( FT_UInt ) FT_Face_GetCharVariantIndex( FT_Face face, @@ -4411,6 +4868,7 @@ FT_BEGIN_HEADER * * @since: * 2.3.6 + * */ FT_EXPORT( FT_Int ) FT_Face_GetCharVariantIsDefault( FT_Face face, @@ -4442,6 +4900,7 @@ FT_BEGIN_HEADER * * @since: * 2.3.6 + * */ FT_EXPORT( FT_UInt32* ) FT_Face_GetVariantSelectors( FT_Face face ); @@ -4475,6 +4934,7 @@ FT_BEGIN_HEADER * * @since: * 2.3.6 + * */ FT_EXPORT( FT_UInt32* ) FT_Face_GetVariantsOfChar( FT_Face face, @@ -4509,6 +4969,7 @@ FT_BEGIN_HEADER * * @since: * 2.3.6 + * */ FT_EXPORT( FT_UInt32* ) FT_Face_GetCharsOfVariant( FT_Face face, @@ -4528,7 +4989,8 @@ FT_BEGIN_HEADER * * @description: * This section contains various functions used to perform computations - * on 16.16 fixed-float numbers or 2d vectors. + * on 16.16 fixed-point numbers or 2D vectors. FreeType does not use + * floating-point data types. * * **Attention**: Most arithmetic functions take `FT_Long` as arguments. * For historical reasons, FreeType was designed under the assumption @@ -4732,32 +5194,10 @@ FT_BEGIN_HEADER /************************************************************************** * * @section: - * version - * - * @title: - * FreeType Version - * - * @abstract: - * Functions and macros related to FreeType versions. - * - * @description: - * Note that those functions and macros are of limited use because even a - * new release of FreeType with only documentation changes increases the - * version number. - * - * @order: - * FT_Library_Version - * - * FREETYPE_MAJOR - * FREETYPE_MINOR - * FREETYPE_PATCH - * - * FT_Face_CheckTrueTypePatents - * FT_Face_SetUnpatentedHinting + * library_setup * */ - /************************************************************************** * * @enum: @@ -4781,7 +5221,7 @@ FT_BEGIN_HEADER * */ #define FREETYPE_MAJOR 2 -#define FREETYPE_MINOR 10 +#define FREETYPE_MINOR 13 #define FREETYPE_PATCH 2 @@ -4824,6 +5264,13 @@ FT_BEGIN_HEADER FT_Int *apatch ); + /************************************************************************** + * + * @section: + * other_api_data + * + */ + /************************************************************************** * * @function: @@ -4844,6 +5291,7 @@ FT_BEGIN_HEADER * * @since: * 2.3.5 + * */ FT_EXPORT( FT_Bool ) FT_Face_CheckTrueTypePatents( FT_Face face ); @@ -4872,6 +5320,7 @@ FT_BEGIN_HEADER * * @since: * 2.3.5 + * */ FT_EXPORT( FT_Bool ) FT_Face_SetUnpatentedHinting( FT_Face face, diff --git a/src/font/freetype-2.10.2/include/freetype/ftadvanc.h b/3rdparty/freetype-2.13.2/include/freetype/ftadvanc.h similarity index 98% rename from src/font/freetype-2.10.2/include/freetype/ftadvanc.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftadvanc.h index c30472bfd..4560ded6d 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftadvanc.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftadvanc.h @@ -4,7 +4,7 @@ * * Quick computation of advance widths (specification only). * - * Copyright (C) 2008-2020 by + * Copyright (C) 2008-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,8 +20,7 @@ #define FTADVANC_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" @@ -96,6 +95,7 @@ FT_BEGIN_HEADER * load_flags :: * A set of bit flags similar to those used when calling * @FT_Load_Glyph, used to determine what kind of advances you need. + * * @output: * padvance :: * The advance value. If scaling is performed (based on the value of diff --git a/src/font/freetype-2.10.2/include/freetype/ftbbox.h b/3rdparty/freetype-2.13.2/include/freetype/ftbbox.h similarity index 97% rename from src/font/freetype-2.10.2/include/freetype/ftbbox.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftbbox.h index 294f99697..fc21740fc 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftbbox.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftbbox.h @@ -4,7 +4,7 @@ * * FreeType exact bbox computation (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -31,8 +31,7 @@ #define FTBBOX_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" diff --git a/src/font/freetype-2.10.2/include/freetype/ftbdf.h b/3rdparty/freetype-2.13.2/include/freetype/ftbdf.h similarity index 98% rename from src/font/freetype-2.10.2/include/freetype/ftbdf.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftbdf.h index 61db27c8f..e8ce64312 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftbdf.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftbdf.h @@ -4,7 +4,7 @@ * * FreeType API for accessing BDF-specific strings (specification). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,7 @@ #ifndef FTBDF_H_ #define FTBDF_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" diff --git a/src/font/freetype-2.10.2/include/freetype/ftbitmap.h b/3rdparty/freetype-2.13.2/include/freetype/ftbitmap.h similarity index 98% rename from src/font/freetype-2.10.2/include/freetype/ftbitmap.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftbitmap.h index 6c5545576..eb6b4b1ee 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftbitmap.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftbitmap.h @@ -4,7 +4,7 @@ * * FreeType utility functions for bitmaps (specification). * - * Copyright (C) 2004-2020 by + * Copyright (C) 2004-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,9 +20,8 @@ #define FTBITMAP_H_ -#include -#include FT_FREETYPE_H -#include FT_COLOR_H +#include +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" diff --git a/src/font/freetype-2.10.2/include/freetype/ftbzip2.h b/3rdparty/freetype-2.13.2/include/freetype/ftbzip2.h similarity index 95% rename from src/font/freetype-2.10.2/include/freetype/ftbzip2.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftbzip2.h index cb8e8458e..7d29f4682 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftbzip2.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftbzip2.h @@ -4,7 +4,7 @@ * * Bzip2-compressed stream support. * - * Copyright (C) 2010-2020 by + * Copyright (C) 2010-2023 by * Joel Klinghed. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,7 @@ #ifndef FTBZIP2_H_ #define FTBZIP2_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" @@ -43,6 +42,16 @@ FT_BEGIN_HEADER * Using bzip2-compressed font files. * * @description: + * In certain builds of the library, bzip2 compression recognition is + * automatically handled when calling @FT_New_Face or @FT_Open_Face. + * This means that if no font driver is capable of handling the raw + * compressed file, the library will try to open a bzip2 compressed + * stream from it and re-open the face with it. + * + * The stream implementation is very basic and resets the decompression + * process each time seeking backwards is needed within the stream, + * which significantly undermines the performance. + * * This section contains the declaration of Bzip2-specific functions. * */ @@ -75,15 +84,6 @@ FT_BEGIN_HEADER * **not** call `FT_Stream_Close` on the source stream. None of the * stream objects will be released to the heap. * - * The stream implementation is very basic and resets the decompression - * process each time seeking backwards is needed within the stream. - * - * In certain builds of the library, bzip2 compression recognition is - * automatically handled when calling @FT_New_Face or @FT_Open_Face. - * This means that if no font driver is capable of handling the raw - * compressed file, the library will try to open a bzip2 compressed - * stream from it and re-open the face with it. - * * This function may return `FT_Err_Unimplemented_Feature` if your build * of FreeType was not compiled with bzip2 support. */ diff --git a/src/font/freetype-2.10.2/include/freetype/ftcache.h b/3rdparty/freetype-2.13.2/include/freetype/ftcache.h similarity index 93% rename from src/font/freetype-2.10.2/include/freetype/ftcache.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftcache.h index d82c4815c..a2072e26b 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftcache.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftcache.h @@ -4,7 +4,7 @@ * * FreeType Cache subsystem (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,8 +20,7 @@ #define FTCACHE_H_ -#include -#include FT_GLYPH_H +#include FT_BEGIN_HEADER @@ -44,61 +43,61 @@ FT_BEGIN_HEADER * objects, as well as caching information like character maps and glyph * images while limiting their maximum memory usage. * - * Note that all types and functions begin with the `FTC_` prefix. + * Note that all types and functions begin with the `FTC_` prefix rather + * than the usual `FT_` prefix in the rest of FreeType. * - * The cache is highly portable and thus doesn't know anything about the - * fonts installed on your system, or how to access them. This implies - * the following scheme: + * The cache is highly portable and, thus, doesn't know anything about + * the fonts installed on your system, or how to access them. Therefore, + * it requires the following. * - * First, available or installed font faces are uniquely identified by - * @FTC_FaceID values, provided to the cache by the client. Note that - * the cache only stores and compares these values, and doesn't try to - * interpret them in any way. + * * @FTC_FaceID, an arbitrary non-zero value that uniquely identifies + * available or installed font faces, has to be provided to the + * cache by the client. Note that the cache only stores and compares + * these values and doesn't try to interpret them in any way, but they + * have to be persistent on the client side. * - * Second, the cache calls, only when needed, a client-provided function - * to convert an @FTC_FaceID into a new @FT_Face object. The latter is - * then completely managed by the cache, including its termination - * through @FT_Done_Face. To monitor termination of face objects, the - * finalizer callback in the `generic` field of the @FT_Face object can - * be used, which might also be used to store the @FTC_FaceID of the - * face. + * * @FTC_Face_Requester, a method to convert an @FTC_FaceID into a new + * @FT_Face object when necessary, has to be provided to the cache by + * the client. The @FT_Face object is completely managed by the cache, + * including its termination through @FT_Done_Face. To monitor + * termination of face objects, the finalizer callback in the `generic` + * field of the @FT_Face object can be used, which might also be used + * to store the @FTC_FaceID of the face. * - * Clients are free to map face IDs to anything else. The most simple - * usage is to associate them to a (pathname,face_index) pair that is - * used to call @FT_New_Face. However, more complex schemes are also - * possible. + * Clients are free to map face IDs to anything useful. The most simple + * usage is, for example, to associate them to a `{pathname,face_index}` + * pair that is then used by @FTC_Face_Requester to call @FT_New_Face. + * However, more complex schemes are also possible. * * Note that for the cache to work correctly, the face ID values must be * **persistent**, which means that the contents they point to should not * change at runtime, or that their value should not become invalid. - * * If this is unavoidable (e.g., when a font is uninstalled at runtime), - * you should call @FTC_Manager_RemoveFaceID as soon as possible, to let + * you should call @FTC_Manager_RemoveFaceID as soon as possible to let * the cache get rid of any references to the old @FTC_FaceID it may keep * internally. Failure to do so will lead to incorrect behaviour or even - * crashes. + * crashes in @FTC_Face_Requester. * * To use the cache, start with calling @FTC_Manager_New to create a new * @FTC_Manager object, which models a single cache instance. You can * then look up @FT_Face and @FT_Size objects with - * @FTC_Manager_LookupFace and @FTC_Manager_LookupSize, respectively. - * - * If you want to use the charmap caching, call @FTC_CMapCache_New, then - * later use @FTC_CMapCache_Lookup to perform the equivalent of - * @FT_Get_Char_Index, only much faster. - * - * If you want to use the @FT_Glyph caching, call @FTC_ImageCache, then - * later use @FTC_ImageCache_Lookup to retrieve the corresponding - * @FT_Glyph objects from the cache. + * @FTC_Manager_LookupFace and @FTC_Manager_LookupSize, respectively, and + * use them in any FreeType work stream. You can also cache other + * FreeType objects as follows. * - * If you need lots of small bitmaps, it is much more memory efficient to - * call @FTC_SBitCache_New followed by @FTC_SBitCache_Lookup. This - * returns @FTC_SBitRec structures, which are used to store small bitmaps - * directly. (A small bitmap is one whose metrics and dimensions all fit - * into 8-bit integers). + * * If you want to use the charmap caching, call @FTC_CMapCache_New, + * then later use @FTC_CMapCache_Lookup to perform the equivalent of + * @FT_Get_Char_Index, only much faster. * - * We hope to also provide a kerning cache in the near future. + * * If you want to use the @FT_Glyph caching, call @FTC_ImageCache_New, + * then later use @FTC_ImageCache_Lookup to retrieve the corresponding + * @FT_Glyph objects from the cache. * + * * If you need lots of small bitmaps, it is much more memory-efficient + * to call @FTC_SBitCache_New followed by @FTC_SBitCache_Lookup. This + * returns @FTC_SBitRec structures, which are used to store small + * bitmaps directly. (A small bitmap is one whose metrics and + * dimensions all fit into 8-bit integers). * * @order: * FTC_Manager @@ -425,7 +424,7 @@ FT_BEGIN_HEADER * pixel :: * A Boolean. If 1, the `width` and `height` fields are interpreted as * integer pixel character sizes. Otherwise, they are expressed as - * 1/64th of points. + * 1/64 of points. * * x_res :: * Only used when `pixel` is value~0 to indicate the horizontal diff --git a/src/font/freetype-2.10.2/include/freetype/ftchapters.h b/3rdparty/freetype-2.13.2/include/freetype/ftchapters.h similarity index 84% rename from src/font/freetype-2.10.2/include/freetype/ftchapters.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftchapters.h index 2ee26973e..7566fbd10 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftchapters.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftchapters.h @@ -15,6 +15,7 @@ * General Remarks * * @sections: + * preamble * header_inclusion * user_allocation * @@ -30,9 +31,28 @@ * Core API * * @sections: - * version * basic_types - * base_interface + * library_setup + * face_creation + * font_testing_macros + * sizing_and_scaling + * glyph_retrieval + * character_mapping + * information_retrieval + * other_api_data + * + */ + + + /************************************************************************** + * + * @chapter: + * extended_api + * + * @title: + * Extended API + * + * @sections: * glyph_variants * color_management * layer_management @@ -61,6 +81,7 @@ * cid_fonts * pfr_fonts * winfnt_fonts + * svg_fonts * font_formats * gasp_table * @@ -81,6 +102,7 @@ * t1_cid_driver * tt_driver * pcf_driver + * ot_svg_driver * properties * parameter_tags * lcd_rendering @@ -123,6 +145,7 @@ * gzip * lzw * bzip2 + * debugging_apis * */ diff --git a/src/font/freetype-2.10.2/include/freetype/ftcid.h b/3rdparty/freetype-2.13.2/include/freetype/ftcid.h similarity index 98% rename from src/font/freetype-2.10.2/include/freetype/ftcid.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftcid.h index 85b74e004..ef2293902 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftcid.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftcid.h @@ -4,7 +4,7 @@ * * FreeType API for accessing CID font information (specification). * - * Copyright (C) 2007-2020 by + * Copyright (C) 2007-2023 by * Dereg Clegg and Michael Toftdal. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,7 @@ #ifndef FTCID_H_ #define FTCID_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" diff --git a/3rdparty/freetype-2.13.2/include/freetype/ftcolor.h b/3rdparty/freetype-2.13.2/include/freetype/ftcolor.h new file mode 100644 index 000000000..eae200fdf --- /dev/null +++ b/3rdparty/freetype-2.13.2/include/freetype/ftcolor.h @@ -0,0 +1,1667 @@ +/**************************************************************************** + * + * ftcolor.h + * + * FreeType's glyph color management (specification). + * + * Copyright (C) 2018-2023 by + * David Turner, Robert Wilhelm, and Werner Lemberg. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + +#ifndef FTCOLOR_H_ +#define FTCOLOR_H_ + +#include + +#ifdef FREETYPE_H +#error "freetype.h of FreeType 1 has been loaded!" +#error "Please fix the directory search order for header files" +#error "so that freetype.h of FreeType 2 is found first." +#endif + + +FT_BEGIN_HEADER + + + /************************************************************************** + * + * @section: + * color_management + * + * @title: + * Glyph Color Management + * + * @abstract: + * Retrieving and manipulating OpenType's 'CPAL' table data. + * + * @description: + * The functions described here allow access and manipulation of color + * palette entries in OpenType's 'CPAL' tables. + */ + + + /************************************************************************** + * + * @struct: + * FT_Color + * + * @description: + * This structure models a BGRA color value of a 'CPAL' palette entry. + * + * The used color space is sRGB; the colors are not pre-multiplied, and + * alpha values must be explicitly set. + * + * @fields: + * blue :: + * Blue value. + * + * green :: + * Green value. + * + * red :: + * Red value. + * + * alpha :: + * Alpha value, giving the red, green, and blue color's opacity. + * + * @since: + * 2.10 + */ + typedef struct FT_Color_ + { + FT_Byte blue; + FT_Byte green; + FT_Byte red; + FT_Byte alpha; + + } FT_Color; + + + /************************************************************************** + * + * @enum: + * FT_PALETTE_XXX + * + * @description: + * A list of bit field constants used in the `palette_flags` array of the + * @FT_Palette_Data structure to indicate for which background a palette + * with a given index is usable. + * + * @values: + * FT_PALETTE_FOR_LIGHT_BACKGROUND :: + * The palette is appropriate to use when displaying the font on a + * light background such as white. + * + * FT_PALETTE_FOR_DARK_BACKGROUND :: + * The palette is appropriate to use when displaying the font on a dark + * background such as black. + * + * @since: + * 2.10 + */ +#define FT_PALETTE_FOR_LIGHT_BACKGROUND 0x01 +#define FT_PALETTE_FOR_DARK_BACKGROUND 0x02 + + + /************************************************************************** + * + * @struct: + * FT_Palette_Data + * + * @description: + * This structure holds the data of the 'CPAL' table. + * + * @fields: + * num_palettes :: + * The number of palettes. + * + * palette_name_ids :: + * An optional read-only array of palette name IDs with `num_palettes` + * elements, corresponding to entries like 'dark' or 'light' in the + * font's 'name' table. + * + * An empty name ID in the 'CPAL' table gets represented as value + * 0xFFFF. + * + * `NULL` if the font's 'CPAL' table doesn't contain appropriate data. + * + * palette_flags :: + * An optional read-only array of palette flags with `num_palettes` + * elements. Possible values are an ORed combination of + * @FT_PALETTE_FOR_LIGHT_BACKGROUND and + * @FT_PALETTE_FOR_DARK_BACKGROUND. + * + * `NULL` if the font's 'CPAL' table doesn't contain appropriate data. + * + * num_palette_entries :: + * The number of entries in a single palette. All palettes have the + * same size. + * + * palette_entry_name_ids :: + * An optional read-only array of palette entry name IDs with + * `num_palette_entries`. In each palette, entries with the same index + * have the same function. For example, index~0 might correspond to + * string 'outline' in the font's 'name' table to indicate that this + * palette entry is used for outlines, index~1 might correspond to + * 'fill' to indicate the filling color palette entry, etc. + * + * An empty entry name ID in the 'CPAL' table gets represented as value + * 0xFFFF. + * + * `NULL` if the font's 'CPAL' table doesn't contain appropriate data. + * + * @note: + * Use function @FT_Get_Sfnt_Name to map name IDs and entry name IDs to + * name strings. + * + * Use function @FT_Palette_Select to get the colors associated with a + * palette entry. + * + * @since: + * 2.10 + */ + typedef struct FT_Palette_Data_ { + FT_UShort num_palettes; + const FT_UShort* palette_name_ids; + const FT_UShort* palette_flags; + + FT_UShort num_palette_entries; + const FT_UShort* palette_entry_name_ids; + + } FT_Palette_Data; + + + /************************************************************************** + * + * @function: + * FT_Palette_Data_Get + * + * @description: + * Retrieve the face's color palette data. + * + * @input: + * face :: + * The source face handle. + * + * @output: + * apalette :: + * A pointer to an @FT_Palette_Data structure. + * + * @return: + * FreeType error code. 0~means success. + * + * @note: + * All arrays in the returned @FT_Palette_Data structure are read-only. + * + * This function always returns an error if the config macro + * `TT_CONFIG_OPTION_COLOR_LAYERS` is not defined in `ftoption.h`. + * + * @since: + * 2.10 + */ + FT_EXPORT( FT_Error ) + FT_Palette_Data_Get( FT_Face face, + FT_Palette_Data *apalette ); + + + /************************************************************************** + * + * @function: + * FT_Palette_Select + * + * @description: + * This function has two purposes. + * + * (1) It activates a palette for rendering color glyphs, and + * + * (2) it retrieves all (unmodified) color entries of this palette. This + * function returns a read-write array, which means that a calling + * application can modify the palette entries on demand. + * + * A corollary of (2) is that calling the function, then modifying some + * values, then calling the function again with the same arguments resets + * all color entries to the original 'CPAL' values; all user modifications + * are lost. + * + * @input: + * face :: + * The source face handle. + * + * palette_index :: + * The palette index. + * + * @output: + * apalette :: + * An array of color entries for a palette with index `palette_index`, + * having `num_palette_entries` elements (as found in the + * `FT_Palette_Data` structure). If `apalette` is set to `NULL`, no + * array gets returned (and no color entries can be modified). + * + * In case the font doesn't support color palettes, `NULL` is returned. + * + * @return: + * FreeType error code. 0~means success. + * + * @note: + * The array pointed to by `apalette_entries` is owned and managed by + * FreeType. + * + * This function always returns an error if the config macro + * `TT_CONFIG_OPTION_COLOR_LAYERS` is not defined in `ftoption.h`. + * + * @since: + * 2.10 + */ + FT_EXPORT( FT_Error ) + FT_Palette_Select( FT_Face face, + FT_UShort palette_index, + FT_Color* *apalette ); + + + /************************************************************************** + * + * @function: + * FT_Palette_Set_Foreground_Color + * + * @description: + * 'COLR' uses palette index 0xFFFF to indicate a 'text foreground + * color'. This function sets this value. + * + * @input: + * face :: + * The source face handle. + * + * foreground_color :: + * An `FT_Color` structure to define the text foreground color. + * + * @return: + * FreeType error code. 0~means success. + * + * @note: + * If this function isn't called, the text foreground color is set to + * white opaque (BGRA value 0xFFFFFFFF) if + * @FT_PALETTE_FOR_DARK_BACKGROUND is present for the current palette, + * and black opaque (BGRA value 0x000000FF) otherwise, including the case + * that no palette types are available in the 'CPAL' table. + * + * This function always returns an error if the config macro + * `TT_CONFIG_OPTION_COLOR_LAYERS` is not defined in `ftoption.h`. + * + * @since: + * 2.10 + */ + FT_EXPORT( FT_Error ) + FT_Palette_Set_Foreground_Color( FT_Face face, + FT_Color foreground_color ); + + + /************************************************************************** + * + * @section: + * layer_management + * + * @title: + * Glyph Layer Management + * + * @abstract: + * Retrieving and manipulating OpenType's 'COLR' table data. + * + * @description: + * The functions described here allow access of colored glyph layer data + * in OpenType's 'COLR' tables. + */ + + + /************************************************************************** + * + * @struct: + * FT_LayerIterator + * + * @description: + * This iterator object is needed for @FT_Get_Color_Glyph_Layer. + * + * @fields: + * num_layers :: + * The number of glyph layers for the requested glyph index. Will be + * set by @FT_Get_Color_Glyph_Layer. + * + * layer :: + * The current layer. Will be set by @FT_Get_Color_Glyph_Layer. + * + * p :: + * An opaque pointer into 'COLR' table data. The caller must set this + * to `NULL` before the first call of @FT_Get_Color_Glyph_Layer. + */ + typedef struct FT_LayerIterator_ + { + FT_UInt num_layers; + FT_UInt layer; + FT_Byte* p; + + } FT_LayerIterator; + + + /************************************************************************** + * + * @function: + * FT_Get_Color_Glyph_Layer + * + * @description: + * This is an interface to the 'COLR' table in OpenType fonts to + * iteratively retrieve the colored glyph layers associated with the + * current glyph slot. + * + * https://docs.microsoft.com/en-us/typography/opentype/spec/colr + * + * The glyph layer data for a given glyph index, if present, provides an + * alternative, multi-color glyph representation: Instead of rendering + * the outline or bitmap with the given glyph index, glyphs with the + * indices and colors returned by this function are rendered layer by + * layer. + * + * The returned elements are ordered in the z~direction from bottom to + * top; the 'n'th element should be rendered with the associated palette + * color and blended on top of the already rendered layers (elements 0, + * 1, ..., n-1). + * + * @input: + * face :: + * A handle to the parent face object. + * + * base_glyph :: + * The glyph index the colored glyph layers are associated with. + * + * @inout: + * iterator :: + * An @FT_LayerIterator object. For the first call you should set + * `iterator->p` to `NULL`. For all following calls, simply use the + * same object again. + * + * @output: + * aglyph_index :: + * The glyph index of the current layer. + * + * acolor_index :: + * The color index into the font face's color palette of the current + * layer. The value 0xFFFF is special; it doesn't reference a palette + * entry but indicates that the text foreground color should be used + * instead (to be set up by the application outside of FreeType). + * + * The color palette can be retrieved with @FT_Palette_Select. + * + * @return: + * Value~1 if everything is OK. If there are no more layers (or if there + * are no layers at all), value~0 gets returned. In case of an error, + * value~0 is returned also. + * + * @note: + * This function is necessary if you want to handle glyph layers by + * yourself. In particular, functions that operate with @FT_GlyphRec + * objects (like @FT_Get_Glyph or @FT_Glyph_To_Bitmap) don't have access + * to this information. + * + * Note that @FT_Render_Glyph is able to handle colored glyph layers + * automatically if the @FT_LOAD_COLOR flag is passed to a previous call + * to @FT_Load_Glyph. [This is an experimental feature.] + * + * @example: + * ``` + * FT_Color* palette; + * FT_LayerIterator iterator; + * + * FT_Bool have_layers; + * FT_UInt layer_glyph_index; + * FT_UInt layer_color_index; + * + * + * error = FT_Palette_Select( face, palette_index, &palette ); + * if ( error ) + * palette = NULL; + * + * iterator.p = NULL; + * have_layers = FT_Get_Color_Glyph_Layer( face, + * glyph_index, + * &layer_glyph_index, + * &layer_color_index, + * &iterator ); + * + * if ( palette && have_layers ) + * { + * do + * { + * FT_Color layer_color; + * + * + * if ( layer_color_index == 0xFFFF ) + * layer_color = text_foreground_color; + * else + * layer_color = palette[layer_color_index]; + * + * // Load and render glyph `layer_glyph_index', then + * // blend resulting pixmap (using color `layer_color') + * // with previously created pixmaps. + * + * } while ( FT_Get_Color_Glyph_Layer( face, + * glyph_index, + * &layer_glyph_index, + * &layer_color_index, + * &iterator ) ); + * } + * ``` + * + * @since: + * 2.10 + */ + FT_EXPORT( FT_Bool ) + FT_Get_Color_Glyph_Layer( FT_Face face, + FT_UInt base_glyph, + FT_UInt *aglyph_index, + FT_UInt *acolor_index, + FT_LayerIterator* iterator ); + + + /************************************************************************** + * + * @enum: + * FT_PaintFormat + * + * @description: + * Enumeration describing the different paint format types of the v1 + * extensions to the 'COLR' table, see + * 'https://github.com/googlefonts/colr-gradients-spec'. + * + * The enumeration values loosely correspond with the format numbers of + * the specification: FreeType always returns a fully specified 'Paint' + * structure for the 'Transform', 'Translate', 'Scale', 'Rotate', and + * 'Skew' table types even though the specification has different formats + * depending on whether or not a center is specified, whether the scale + * is uniform in x and y~direction or not, etc. Also, only non-variable + * format identifiers are listed in this enumeration; as soon as support + * for variable 'COLR' v1 fonts is implemented, interpolation is + * performed dependent on axis coordinates, which are configured on the + * @FT_Face through @FT_Set_Var_Design_Coordinates. This implies that + * always static, readily interpolated values are returned in the 'Paint' + * structures. + * + * @since: + * 2.13 + */ + typedef enum FT_PaintFormat_ + { + FT_COLR_PAINTFORMAT_COLR_LAYERS = 1, + FT_COLR_PAINTFORMAT_SOLID = 2, + FT_COLR_PAINTFORMAT_LINEAR_GRADIENT = 4, + FT_COLR_PAINTFORMAT_RADIAL_GRADIENT = 6, + FT_COLR_PAINTFORMAT_SWEEP_GRADIENT = 8, + FT_COLR_PAINTFORMAT_GLYPH = 10, + FT_COLR_PAINTFORMAT_COLR_GLYPH = 11, + FT_COLR_PAINTFORMAT_TRANSFORM = 12, + FT_COLR_PAINTFORMAT_TRANSLATE = 14, + FT_COLR_PAINTFORMAT_SCALE = 16, + FT_COLR_PAINTFORMAT_ROTATE = 24, + FT_COLR_PAINTFORMAT_SKEW = 28, + FT_COLR_PAINTFORMAT_COMPOSITE = 32, + FT_COLR_PAINT_FORMAT_MAX = 33, + FT_COLR_PAINTFORMAT_UNSUPPORTED = 255 + + } FT_PaintFormat; + + + /************************************************************************** + * + * @struct: + * FT_ColorStopIterator + * + * @description: + * This iterator object is needed for @FT_Get_Colorline_Stops. It keeps + * state while iterating over the stops of an @FT_ColorLine, representing + * the `ColorLine` struct of the v1 extensions to 'COLR', see + * 'https://github.com/googlefonts/colr-gradients-spec'. Do not manually + * modify fields of this iterator. + * + * @fields: + * num_color_stops :: + * The number of color stops for the requested glyph index. Set by + * @FT_Get_Paint. + * + * current_color_stop :: + * The current color stop. Set by @FT_Get_Colorline_Stops. + * + * p :: + * An opaque pointer into 'COLR' table data. Set by @FT_Get_Paint. + * Updated by @FT_Get_Colorline_Stops. + * + * read_variable :: + * A boolean keeping track of whether variable color lines are to be + * read. Set by @FT_Get_Paint. + * + * @since: + * 2.13 + */ + typedef struct FT_ColorStopIterator_ + { + FT_UInt num_color_stops; + FT_UInt current_color_stop; + + FT_Byte* p; + + FT_Bool read_variable; + + } FT_ColorStopIterator; + + + /************************************************************************** + * + * @struct: + * FT_ColorIndex + * + * @description: + * A structure representing a `ColorIndex` value of the 'COLR' v1 + * extensions, see 'https://github.com/googlefonts/colr-gradients-spec'. + * + * @fields: + * palette_index :: + * The palette index into a 'CPAL' palette. + * + * alpha :: + * Alpha transparency value multiplied with the value from 'CPAL'. + * + * @since: + * 2.13 + */ + typedef struct FT_ColorIndex_ + { + FT_UInt16 palette_index; + FT_F2Dot14 alpha; + + } FT_ColorIndex; + + + /************************************************************************** + * + * @struct: + * FT_ColorStop + * + * @description: + * A structure representing a `ColorStop` value of the 'COLR' v1 + * extensions, see 'https://github.com/googlefonts/colr-gradients-spec'. + * + * @fields: + * stop_offset :: + * The stop offset along the gradient, expressed as a 16.16 fixed-point + * coordinate. + * + * color :: + * The color information for this stop, see @FT_ColorIndex. + * + * @since: + * 2.13 + */ + typedef struct FT_ColorStop_ + { + FT_Fixed stop_offset; + FT_ColorIndex color; + + } FT_ColorStop; + + + /************************************************************************** + * + * @enum: + * FT_PaintExtend + * + * @description: + * An enumeration representing the 'Extend' mode of the 'COLR' v1 + * extensions, see 'https://github.com/googlefonts/colr-gradients-spec'. + * It describes how the gradient fill continues at the other boundaries. + * + * @since: + * 2.13 + */ + typedef enum FT_PaintExtend_ + { + FT_COLR_PAINT_EXTEND_PAD = 0, + FT_COLR_PAINT_EXTEND_REPEAT = 1, + FT_COLR_PAINT_EXTEND_REFLECT = 2 + + } FT_PaintExtend; + + + /************************************************************************** + * + * @struct: + * FT_ColorLine + * + * @description: + * A structure representing a `ColorLine` value of the 'COLR' v1 + * extensions, see 'https://github.com/googlefonts/colr-gradients-spec'. + * It describes a list of color stops along the defined gradient. + * + * @fields: + * extend :: + * The extend mode at the outer boundaries, see @FT_PaintExtend. + * + * color_stop_iterator :: + * The @FT_ColorStopIterator used to enumerate and retrieve the + * actual @FT_ColorStop's. + * + * @since: + * 2.13 + */ + typedef struct FT_ColorLine_ + { + FT_PaintExtend extend; + FT_ColorStopIterator color_stop_iterator; + + } FT_ColorLine; + + + /************************************************************************** + * + * @struct: + * FT_Affine23 + * + * @description: + * A structure used to store a 2x3 matrix. Coefficients are in + * 16.16 fixed-point format. The computation performed is + * + * ``` + * x' = x*xx + y*xy + dx + * y' = x*yx + y*yy + dy + * ``` + * + * @fields: + * xx :: + * Matrix coefficient. + * + * xy :: + * Matrix coefficient. + * + * dx :: + * x translation. + * + * yx :: + * Matrix coefficient. + * + * yy :: + * Matrix coefficient. + * + * dy :: + * y translation. + * + * @since: + * 2.13 + */ + typedef struct FT_Affine_23_ + { + FT_Fixed xx, xy, dx; + FT_Fixed yx, yy, dy; + + } FT_Affine23; + + + /************************************************************************** + * + * @enum: + * FT_Composite_Mode + * + * @description: + * An enumeration listing the 'COLR' v1 composite modes used in + * @FT_PaintComposite. For more details on each paint mode, see + * 'https://www.w3.org/TR/compositing-1/#porterduffcompositingoperators'. + * + * @since: + * 2.13 + */ + typedef enum FT_Composite_Mode_ + { + FT_COLR_COMPOSITE_CLEAR = 0, + FT_COLR_COMPOSITE_SRC = 1, + FT_COLR_COMPOSITE_DEST = 2, + FT_COLR_COMPOSITE_SRC_OVER = 3, + FT_COLR_COMPOSITE_DEST_OVER = 4, + FT_COLR_COMPOSITE_SRC_IN = 5, + FT_COLR_COMPOSITE_DEST_IN = 6, + FT_COLR_COMPOSITE_SRC_OUT = 7, + FT_COLR_COMPOSITE_DEST_OUT = 8, + FT_COLR_COMPOSITE_SRC_ATOP = 9, + FT_COLR_COMPOSITE_DEST_ATOP = 10, + FT_COLR_COMPOSITE_XOR = 11, + FT_COLR_COMPOSITE_PLUS = 12, + FT_COLR_COMPOSITE_SCREEN = 13, + FT_COLR_COMPOSITE_OVERLAY = 14, + FT_COLR_COMPOSITE_DARKEN = 15, + FT_COLR_COMPOSITE_LIGHTEN = 16, + FT_COLR_COMPOSITE_COLOR_DODGE = 17, + FT_COLR_COMPOSITE_COLOR_BURN = 18, + FT_COLR_COMPOSITE_HARD_LIGHT = 19, + FT_COLR_COMPOSITE_SOFT_LIGHT = 20, + FT_COLR_COMPOSITE_DIFFERENCE = 21, + FT_COLR_COMPOSITE_EXCLUSION = 22, + FT_COLR_COMPOSITE_MULTIPLY = 23, + FT_COLR_COMPOSITE_HSL_HUE = 24, + FT_COLR_COMPOSITE_HSL_SATURATION = 25, + FT_COLR_COMPOSITE_HSL_COLOR = 26, + FT_COLR_COMPOSITE_HSL_LUMINOSITY = 27, + FT_COLR_COMPOSITE_MAX = 28 + + } FT_Composite_Mode; + + + /************************************************************************** + * + * @struct: + * FT_OpaquePaint + * + * @description: + * A structure representing an offset to a `Paint` value stored in any + * of the paint tables of a 'COLR' v1 font. Compare Offset<24> there. + * When 'COLR' v1 paint tables represented by FreeType objects such as + * @FT_PaintColrLayers, @FT_PaintComposite, or @FT_PaintTransform + * reference downstream nested paint tables, we do not immediately + * retrieve them but encapsulate their location in this type. Use + * @FT_Get_Paint to retrieve the actual @FT_COLR_Paint object that + * describes the details of the respective paint table. + * + * @fields: + * p :: + * An internal offset to a Paint table, needs to be set to NULL before + * passing this struct as an argument to @FT_Get_Paint. + * + * insert_root_transform :: + * An internal boolean to track whether an initial root transform is + * to be provided. Do not set this value. + * + * @since: + * 2.13 + */ + typedef struct FT_Opaque_Paint_ + { + FT_Byte* p; + FT_Bool insert_root_transform; + } FT_OpaquePaint; + + + /************************************************************************** + * + * @struct: + * FT_PaintColrLayers + * + * @description: + * A structure representing a `PaintColrLayers` table of a 'COLR' v1 + * font. This table describes a set of layers that are to be composited + * with composite mode `FT_COLR_COMPOSITE_SRC_OVER`. The return value + * of this function is an @FT_LayerIterator initialized so that it can + * be used with @FT_Get_Paint_Layers to retrieve the @FT_OpaquePaint + * objects as references to each layer. + * + * @fields: + * layer_iterator :: + * The layer iterator that describes the layers of this paint. + * + * @since: + * 2.13 + */ + typedef struct FT_PaintColrLayers_ + { + FT_LayerIterator layer_iterator; + + } FT_PaintColrLayers; + + + /************************************************************************** + * + * @struct: + * FT_PaintSolid + * + * @description: + * A structure representing a `PaintSolid` value of the 'COLR' v1 + * extensions, see 'https://github.com/googlefonts/colr-gradients-spec'. + * Using a `PaintSolid` value means that the glyph layer filled with + * this paint is solid-colored and does not contain a gradient. + * + * @fields: + * color :: + * The color information for this solid paint, see @FT_ColorIndex. + * + * @since: + * 2.13 + */ + typedef struct FT_PaintSolid_ + { + FT_ColorIndex color; + + } FT_PaintSolid; + + + /************************************************************************** + * + * @struct: + * FT_PaintLinearGradient + * + * @description: + * A structure representing a `PaintLinearGradient` value of the 'COLR' + * v1 extensions, see + * 'https://github.com/googlefonts/colr-gradients-spec'. The glyph + * layer filled with this paint is drawn filled with a linear gradient. + * + * @fields: + * colorline :: + * The @FT_ColorLine information for this paint, i.e., the list of + * color stops along the gradient. + * + * p0 :: + * The starting point of the gradient definition in font units + * represented as a 16.16 fixed-point `FT_Vector`. + * + * p1 :: + * The end point of the gradient definition in font units + * represented as a 16.16 fixed-point `FT_Vector`. + * + * p2 :: + * Optional point~p2 to rotate the gradient in font units + * represented as a 16.16 fixed-point `FT_Vector`. + * Otherwise equal to~p0. + * + * @since: + * 2.13 + */ + typedef struct FT_PaintLinearGradient_ + { + FT_ColorLine colorline; + + /* TODO: Potentially expose those as x0, y0 etc. */ + FT_Vector p0; + FT_Vector p1; + FT_Vector p2; + + } FT_PaintLinearGradient; + + + /************************************************************************** + * + * @struct: + * FT_PaintRadialGradient + * + * @description: + * A structure representing a `PaintRadialGradient` value of the 'COLR' + * v1 extensions, see + * 'https://github.com/googlefonts/colr-gradients-spec'. The glyph + * layer filled with this paint is drawn filled with a radial gradient. + * + * @fields: + * colorline :: + * The @FT_ColorLine information for this paint, i.e., the list of + * color stops along the gradient. + * + * c0 :: + * The center of the starting point of the radial gradient in font + * units represented as a 16.16 fixed-point `FT_Vector`. + * + * r0 :: + * The radius of the starting circle of the radial gradient in font + * units represented as a 16.16 fixed-point value. + * + * c1 :: + * The center of the end point of the radial gradient in font units + * represented as a 16.16 fixed-point `FT_Vector`. + * + * r1 :: + * The radius of the end circle of the radial gradient in font + * units represented as a 16.16 fixed-point value. + * + * @since: + * 2.13 + */ + typedef struct FT_PaintRadialGradient_ + { + FT_ColorLine colorline; + + FT_Vector c0; + FT_Pos r0; + FT_Vector c1; + FT_Pos r1; + + } FT_PaintRadialGradient; + + + /************************************************************************** + * + * @struct: + * FT_PaintSweepGradient + * + * @description: + * A structure representing a `PaintSweepGradient` value of the 'COLR' + * v1 extensions, see + * 'https://github.com/googlefonts/colr-gradients-spec'. The glyph + * layer filled with this paint is drawn filled with a sweep gradient + * from `start_angle` to `end_angle`. + * + * @fields: + * colorline :: + * The @FT_ColorLine information for this paint, i.e., the list of + * color stops along the gradient. + * + * center :: + * The center of the sweep gradient in font units represented as a + * vector of 16.16 fixed-point values. + * + * start_angle :: + * The start angle of the sweep gradient in 16.16 fixed-point + * format specifying degrees divided by 180.0 (as in the + * spec). Multiply by 180.0f to receive degrees value. Values are + * given counter-clockwise, starting from the (positive) y~axis. + * + * end_angle :: + * The end angle of the sweep gradient in 16.16 fixed-point + * format specifying degrees divided by 180.0 (as in the + * spec). Multiply by 180.0f to receive degrees value. Values are + * given counter-clockwise, starting from the (positive) y~axis. + * + * @since: + * 2.13 + */ + typedef struct FT_PaintSweepGradient_ + { + FT_ColorLine colorline; + + FT_Vector center; + FT_Fixed start_angle; + FT_Fixed end_angle; + + } FT_PaintSweepGradient; + + + /************************************************************************** + * + * @struct: + * FT_PaintGlyph + * + * @description: + * A structure representing a 'COLR' v1 `PaintGlyph` paint table. + * + * @fields: + * paint :: + * An opaque paint object pointing to a `Paint` table that serves as + * the fill for the glyph ID. + * + * glyphID :: + * The glyph ID from the 'glyf' table, which serves as the contour + * information that is filled with paint. + * + * @since: + * 2.13 + */ + typedef struct FT_PaintGlyph_ + { + FT_OpaquePaint paint; + FT_UInt glyphID; + + } FT_PaintGlyph; + + + /************************************************************************** + * + * @struct: + * FT_PaintColrGlyph + * + * @description: + * A structure representing a 'COLR' v1 `PaintColorGlyph` paint table. + * + * @fields: + * glyphID :: + * The glyph ID from the `BaseGlyphV1List` table that is drawn for + * this paint. + * + * @since: + * 2.13 + */ + typedef struct FT_PaintColrGlyph_ + { + FT_UInt glyphID; + + } FT_PaintColrGlyph; + + + /************************************************************************** + * + * @struct: + * FT_PaintTransform + * + * @description: + * A structure representing a 'COLR' v1 `PaintTransform` paint table. + * + * @fields: + * paint :: + * An opaque paint that is subject to being transformed. + * + * affine :: + * A 2x3 transformation matrix in @FT_Affine23 format containing + * 16.16 fixed-point values. + * + * @since: + * 2.13 + */ + typedef struct FT_PaintTransform_ + { + FT_OpaquePaint paint; + FT_Affine23 affine; + + } FT_PaintTransform; + + + /************************************************************************** + * + * @struct: + * FT_PaintTranslate + * + * @description: + * A structure representing a 'COLR' v1 `PaintTranslate` paint table. + * Used for translating downstream paints by a given x and y~delta. + * + * @fields: + * paint :: + * An @FT_OpaquePaint object referencing the paint that is to be + * rotated. + * + * dx :: + * Translation in x~direction in font units represented as a + * 16.16 fixed-point value. + * + * dy :: + * Translation in y~direction in font units represented as a + * 16.16 fixed-point value. + * + * @since: + * 2.13 + */ + typedef struct FT_PaintTranslate_ + { + FT_OpaquePaint paint; + + FT_Fixed dx; + FT_Fixed dy; + + } FT_PaintTranslate; + + + /************************************************************************** + * + * @struct: + * FT_PaintScale + * + * @description: + * A structure representing all of the 'COLR' v1 'PaintScale*' paint + * tables. Used for scaling downstream paints by a given x and y~scale, + * with a given center. This structure is used for all 'PaintScale*' + * types that are part of specification; fields of this structure are + * filled accordingly. If there is a center, the center values are set, + * otherwise they are set to the zero coordinate. If the source font + * file has 'PaintScaleUniform*' set, the scale values are set + * accordingly to the same value. + * + * @fields: + * paint :: + * An @FT_OpaquePaint object referencing the paint that is to be + * scaled. + * + * scale_x :: + * Scale factor in x~direction represented as a + * 16.16 fixed-point value. + * + * scale_y :: + * Scale factor in y~direction represented as a + * 16.16 fixed-point value. + * + * center_x :: + * x~coordinate of center point to scale from represented as a + * 16.16 fixed-point value. + * + * center_y :: + * y~coordinate of center point to scale from represented as a + * 16.16 fixed-point value. + * + * @since: + * 2.13 + */ + typedef struct FT_PaintScale_ + { + FT_OpaquePaint paint; + + FT_Fixed scale_x; + FT_Fixed scale_y; + + FT_Fixed center_x; + FT_Fixed center_y; + + } FT_PaintScale; + + + /************************************************************************** + * + * @struct: + * FT_PaintRotate + * + * @description: + * A structure representing a 'COLR' v1 `PaintRotate` paint table. Used + * for rotating downstream paints with a given center and angle. + * + * @fields: + * paint :: + * An @FT_OpaquePaint object referencing the paint that is to be + * rotated. + * + * angle :: + * The rotation angle that is to be applied in degrees divided by + * 180.0 (as in the spec) represented as a 16.16 fixed-point + * value. Multiply by 180.0f to receive degrees value. + * + * center_x :: + * The x~coordinate of the pivot point of the rotation in font + * units represented as a 16.16 fixed-point value. + * + * center_y :: + * The y~coordinate of the pivot point of the rotation in font + * units represented as a 16.16 fixed-point value. + * + * @since: + * 2.13 + */ + + typedef struct FT_PaintRotate_ + { + FT_OpaquePaint paint; + + FT_Fixed angle; + + FT_Fixed center_x; + FT_Fixed center_y; + + } FT_PaintRotate; + + + /************************************************************************** + * + * @struct: + * FT_PaintSkew + * + * @description: + * A structure representing a 'COLR' v1 `PaintSkew` paint table. Used + * for skewing or shearing downstream paints by a given center and + * angle. + * + * @fields: + * paint :: + * An @FT_OpaquePaint object referencing the paint that is to be + * skewed. + * + * x_skew_angle :: + * The skewing angle in x~direction in degrees divided by 180.0 + * (as in the spec) represented as a 16.16 fixed-point + * value. Multiply by 180.0f to receive degrees. + * + * y_skew_angle :: + * The skewing angle in y~direction in degrees divided by 180.0 + * (as in the spec) represented as a 16.16 fixed-point + * value. Multiply by 180.0f to receive degrees. + * + * center_x :: + * The x~coordinate of the pivot point of the skew in font units + * represented as a 16.16 fixed-point value. + * + * center_y :: + * The y~coordinate of the pivot point of the skew in font units + * represented as a 16.16 fixed-point value. + * + * @since: + * 2.13 + */ + typedef struct FT_PaintSkew_ + { + FT_OpaquePaint paint; + + FT_Fixed x_skew_angle; + FT_Fixed y_skew_angle; + + FT_Fixed center_x; + FT_Fixed center_y; + + } FT_PaintSkew; + + + /************************************************************************** + * + * @struct: + * FT_PaintComposite + * + * @description: + * A structure representing a 'COLR' v1 `PaintComposite` paint table. + * Used for compositing two paints in a 'COLR' v1 directed acyclic graph. + * + * @fields: + * source_paint :: + * An @FT_OpaquePaint object referencing the source that is to be + * composited. + * + * composite_mode :: + * An @FT_Composite_Mode enum value determining the composition + * operation. + * + * backdrop_paint :: + * An @FT_OpaquePaint object referencing the backdrop paint that + * `source_paint` is composited onto. + * + * @since: + * 2.13 + */ + typedef struct FT_PaintComposite_ + { + FT_OpaquePaint source_paint; + FT_Composite_Mode composite_mode; + FT_OpaquePaint backdrop_paint; + + } FT_PaintComposite; + + + /************************************************************************** + * + * @union: + * FT_COLR_Paint + * + * @description: + * A union object representing format and details of a paint table of a + * 'COLR' v1 font, see + * 'https://github.com/googlefonts/colr-gradients-spec'. Use + * @FT_Get_Paint to retrieve a @FT_COLR_Paint for an @FT_OpaquePaint + * object. + * + * @fields: + * format :: + * The gradient format for this Paint structure. + * + * u :: + * Union of all paint table types: + * + * * @FT_PaintColrLayers + * * @FT_PaintGlyph + * * @FT_PaintSolid + * * @FT_PaintLinearGradient + * * @FT_PaintRadialGradient + * * @FT_PaintSweepGradient + * * @FT_PaintTransform + * * @FT_PaintTranslate + * * @FT_PaintRotate + * * @FT_PaintSkew + * * @FT_PaintComposite + * * @FT_PaintColrGlyph + * + * @since: + * 2.13 + */ + typedef struct FT_COLR_Paint_ + { + FT_PaintFormat format; + + union + { + FT_PaintColrLayers colr_layers; + FT_PaintGlyph glyph; + FT_PaintSolid solid; + FT_PaintLinearGradient linear_gradient; + FT_PaintRadialGradient radial_gradient; + FT_PaintSweepGradient sweep_gradient; + FT_PaintTransform transform; + FT_PaintTranslate translate; + FT_PaintScale scale; + FT_PaintRotate rotate; + FT_PaintSkew skew; + FT_PaintComposite composite; + FT_PaintColrGlyph colr_glyph; + + } u; + + } FT_COLR_Paint; + + + /************************************************************************** + * + * @enum: + * FT_Color_Root_Transform + * + * @description: + * An enumeration to specify whether @FT_Get_Color_Glyph_Paint is to + * return a root transform to configure the client's graphics context + * matrix. + * + * @values: + * FT_COLOR_INCLUDE_ROOT_TRANSFORM :: + * Do include the root transform as the initial @FT_COLR_Paint object. + * + * FT_COLOR_NO_ROOT_TRANSFORM :: + * Do not output an initial root transform. + * + * @since: + * 2.13 + */ + typedef enum FT_Color_Root_Transform_ + { + FT_COLOR_INCLUDE_ROOT_TRANSFORM, + FT_COLOR_NO_ROOT_TRANSFORM, + + FT_COLOR_ROOT_TRANSFORM_MAX + + } FT_Color_Root_Transform; + + + /************************************************************************** + * + * @struct: + * FT_ClipBox + * + * @description: + * A structure representing a 'COLR' v1 'ClipBox' table. 'COLR' v1 + * glyphs may optionally define a clip box for aiding allocation or + * defining a maximum drawable region. Use @FT_Get_Color_Glyph_ClipBox + * to retrieve it. + * + * @fields: + * bottom_left :: + * The bottom left corner of the clip box as an @FT_Vector with + * fixed-point coordinates in 26.6 format. + * + * top_left :: + * The top left corner of the clip box as an @FT_Vector with + * fixed-point coordinates in 26.6 format. + * + * top_right :: + * The top right corner of the clip box as an @FT_Vector with + * fixed-point coordinates in 26.6 format. + * + * bottom_right :: + * The bottom right corner of the clip box as an @FT_Vector with + * fixed-point coordinates in 26.6 format. + * + * @since: + * 2.13 + */ + typedef struct FT_ClipBox_ + { + FT_Vector bottom_left; + FT_Vector top_left; + FT_Vector top_right; + FT_Vector bottom_right; + + } FT_ClipBox; + + + /************************************************************************** + * + * @function: + * FT_Get_Color_Glyph_Paint + * + * @description: + * This is the starting point and interface to color gradient + * information in a 'COLR' v1 table in OpenType fonts to recursively + * retrieve the paint tables for the directed acyclic graph of a colored + * glyph, given a glyph ID. + * + * https://github.com/googlefonts/colr-gradients-spec + * + * In a 'COLR' v1 font, each color glyph defines a directed acyclic + * graph of nested paint tables, such as `PaintGlyph`, `PaintSolid`, + * `PaintLinearGradient`, `PaintRadialGradient`, and so on. Using this + * function and specifying a glyph ID, one retrieves the root paint + * table for this glyph ID. + * + * This function allows control whether an initial root transform is + * returned to configure scaling, transform, and translation correctly + * on the client's graphics context. The initial root transform is + * computed and returned according to the values configured for @FT_Size + * and @FT_Set_Transform on the @FT_Face object, see below for details + * of the `root_transform` parameter. This has implications for a + * client 'COLR' v1 implementation: When this function returns an + * initially computed root transform, at the time of executing the + * @FT_PaintGlyph operation, the contours should be retrieved using + * @FT_Load_Glyph at unscaled, untransformed size. This is because the + * root transform applied to the graphics context will take care of + * correct scaling. + * + * Alternatively, to allow hinting of contours, at the time of executing + * @FT_Load_Glyph, the current graphics context transformation matrix + * can be decomposed into a scaling matrix and a remainder, and + * @FT_Load_Glyph can be used to retrieve the contours at scaled size. + * Care must then be taken to blit or clip to the graphics context with + * taking this remainder transformation into account. + * + * @input: + * face :: + * A handle to the parent face object. + * + * base_glyph :: + * The glyph index for which to retrieve the root paint table. + * + * root_transform :: + * Specifies whether an initially computed root is returned by the + * @FT_PaintTransform operation to account for the activated size + * (see @FT_Activate_Size) and the configured transform and translate + * (see @FT_Set_Transform). + * + * This root transform is returned before nodes of the glyph graph of + * the font are returned. Subsequent @FT_COLR_Paint structures + * contain unscaled and untransformed values. The inserted root + * transform enables the client application to apply an initial + * transform to its graphics context. When executing subsequent + * FT_COLR_Paint operations, values from @FT_COLR_Paint operations + * will ultimately be correctly scaled because of the root transform + * applied to the graphics context. Use + * @FT_COLOR_INCLUDE_ROOT_TRANSFORM to include the root transform, use + * @FT_COLOR_NO_ROOT_TRANSFORM to not include it. The latter may be + * useful when traversing the 'COLR' v1 glyph graph and reaching a + * @FT_PaintColrGlyph. When recursing into @FT_PaintColrGlyph and + * painting that inline, no additional root transform is needed as it + * has already been applied to the graphics context at the beginning + * of drawing this glyph. + * + * @output: + * paint :: + * The @FT_OpaquePaint object that references the actual paint table. + * + * The respective actual @FT_COLR_Paint object is retrieved via + * @FT_Get_Paint. + * + * @return: + * Value~1 if everything is OK. If no color glyph is found, or the root + * paint could not be retrieved, value~0 gets returned. In case of an + * error, value~0 is returned also. + * + * @since: + * 2.13 + */ + FT_EXPORT( FT_Bool ) + FT_Get_Color_Glyph_Paint( FT_Face face, + FT_UInt base_glyph, + FT_Color_Root_Transform root_transform, + FT_OpaquePaint* paint ); + + + /************************************************************************** + * + * @function: + * FT_Get_Color_Glyph_ClipBox + * + * @description: + * Search for a 'COLR' v1 clip box for the specified `base_glyph` and + * fill the `clip_box` parameter with the 'COLR' v1 'ClipBox' information + * if one is found. + * + * @input: + * face :: + * A handle to the parent face object. + * + * base_glyph :: + * The glyph index for which to retrieve the clip box. + * + * @output: + * clip_box :: + * The clip box for the requested `base_glyph` if one is found. The + * clip box is computed taking scale and transformations configured on + * the @FT_Face into account. @FT_ClipBox contains @FT_Vector values + * in 26.6 format. + * + * @return: + * Value~1 if a clip box is found. If no clip box is found or an error + * occured, value~0 is returned. + * + * @note: + * To retrieve the clip box in font units, reset scale to units-per-em + * and remove transforms configured using @FT_Set_Transform. + * + * @since: + * 2.13 + */ + FT_EXPORT( FT_Bool ) + FT_Get_Color_Glyph_ClipBox( FT_Face face, + FT_UInt base_glyph, + FT_ClipBox* clip_box ); + + + /************************************************************************** + * + * @function: + * FT_Get_Paint_Layers + * + * @description: + * Access the layers of a `PaintColrLayers` table. + * + * If the root paint of a color glyph, or a nested paint of a 'COLR' + * glyph is a `PaintColrLayers` table, this function retrieves the + * layers of the `PaintColrLayers` table. + * + * The @FT_PaintColrLayers object contains an @FT_LayerIterator, which + * is used here to iterate over the layers. Each layer is returned as + * an @FT_OpaquePaint object, which then can be used with @FT_Get_Paint + * to retrieve the actual paint object. + * + * @input: + * face :: + * A handle to the parent face object. + * + * @inout: + * iterator :: + * The @FT_LayerIterator from an @FT_PaintColrLayers object, for which + * the layers are to be retrieved. The internal state of the iterator + * is incremented after one call to this function for retrieving one + * layer. + * + * @output: + * paint :: + * The @FT_OpaquePaint object that references the actual paint table. + * The respective actual @FT_COLR_Paint object is retrieved via + * @FT_Get_Paint. + * + * @return: + * Value~1 if everything is OK. Value~0 gets returned when the paint + * object can not be retrieved or any other error occurs. + * + * @since: + * 2.13 + */ + FT_EXPORT( FT_Bool ) + FT_Get_Paint_Layers( FT_Face face, + FT_LayerIterator* iterator, + FT_OpaquePaint* paint ); + + + /************************************************************************** + * + * @function: + * FT_Get_Colorline_Stops + * + * @description: + * This is an interface to color gradient information in a 'COLR' v1 + * table in OpenType fonts to iteratively retrieve the gradient and + * solid fill information for colored glyph layers for a specified glyph + * ID. + * + * https://github.com/googlefonts/colr-gradients-spec + * + * @input: + * face :: + * A handle to the parent face object. + * + * @inout: + * iterator :: + * The retrieved @FT_ColorStopIterator, configured on an @FT_ColorLine, + * which in turn got retrieved via paint information in + * @FT_PaintLinearGradient or @FT_PaintRadialGradient. + * + * @output: + * color_stop :: + * Color index and alpha value for the retrieved color stop. + * + * @return: + * Value~1 if everything is OK. If there are no more color stops, + * value~0 gets returned. In case of an error, value~0 is returned + * also. + * + * @since: + * 2.13 + */ + FT_EXPORT( FT_Bool ) + FT_Get_Colorline_Stops( FT_Face face, + FT_ColorStop* color_stop, + FT_ColorStopIterator* iterator ); + + + /************************************************************************** + * + * @function: + * FT_Get_Paint + * + * @description: + * Access the details of a paint using an @FT_OpaquePaint opaque paint + * object, which internally stores the offset to the respective `Paint` + * object in the 'COLR' table. + * + * @input: + * face :: + * A handle to the parent face object. + * + * opaque_paint :: + * The opaque paint object for which the underlying @FT_COLR_Paint + * data is to be retrieved. + * + * @output: + * paint :: + * The specific @FT_COLR_Paint object containing information coming + * from one of the font's `Paint*` tables. + * + * @return: + * Value~1 if everything is OK. Value~0 if no details can be found for + * this paint or any other error occured. + * + * @since: + * 2.13 + */ + FT_EXPORT( FT_Bool ) + FT_Get_Paint( FT_Face face, + FT_OpaquePaint opaque_paint, + FT_COLR_Paint* paint ); + + /* */ + + +FT_END_HEADER + +#endif /* FTCOLOR_H_ */ + + +/* END */ diff --git a/src/font/freetype-2.10.2/include/freetype/ftdriver.h b/3rdparty/freetype-2.13.2/include/freetype/ftdriver.h similarity index 92% rename from src/font/freetype-2.10.2/include/freetype/ftdriver.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftdriver.h index 19b666ecb..7af7465bc 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftdriver.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftdriver.h @@ -4,7 +4,7 @@ * * FreeType API for controlling driver modules (specification only). * - * Copyright (C) 2017-2020 by + * Copyright (C) 2017-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,9 +19,8 @@ #ifndef FTDRIVER_H_ #define FTDRIVER_H_ -#include -#include FT_FREETYPE_H -#include FT_PARAMETER_TAGS_H +#include +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" @@ -54,10 +53,10 @@ FT_BEGIN_HEADER * reasons. * * Available properties are @increase-x-height, @no-stem-darkening - * (experimental), @darkening-parameters (experimental), @warping - * (experimental), @glyph-to-script-map (experimental), @fallback-script - * (experimental), and @default-script (experimental), as documented in - * the @properties section. + * (experimental), @darkening-parameters (experimental), + * @glyph-to-script-map (experimental), @fallback-script (experimental), + * and @default-script (experimental), as documented in the @properties + * section. * */ @@ -85,15 +84,15 @@ FT_BEGIN_HEADER * @properties section. * * - * **Hinting and antialiasing principles of the new engine** + * **Hinting and anti-aliasing principles of the new engine** * * The rasterizer is positioning horizontal features (e.g., ascender * height & x-height, or crossbars) on the pixel grid and minimizing the - * amount of antialiasing applied to them, while placing vertical + * amount of anti-aliasing applied to them, while placing vertical * features (vertical stems) on the pixel grid without hinting, thus * representing the stem position and weight accurately. Sometimes the * vertical stems may be only partially black. In this context, - * 'antialiasing' means that stems are not positioned exactly on pixel + * 'anti-aliasing' means that stems are not positioned exactly on pixel * borders, causing a fuzzy appearance. * * There are two principles behind this approach. @@ -109,7 +108,7 @@ FT_BEGIN_HEADER * sizes are comparable to kerning values and thus would be noticeable * (and distracting) while reading if hinting were applied. * - * One of the reasons to not hint horizontally is antialiasing for LCD + * One of the reasons to not hint horizontally is anti-aliasing for LCD * screens: The pixel geometry of modern displays supplies three vertical * subpixels as the eye moves horizontally across each visible pixel. On * devices where we can be certain this characteristic is present a @@ -117,7 +116,7 @@ FT_BEGIN_HEADER * weight. In Western writing systems this turns out to be the more * critical direction anyway; the weights and spacing of vertical stems * (see above) are central to Armenian, Cyrillic, Greek, and Latin type - * designs. Even when the rasterizer uses greyscale antialiasing instead + * designs. Even when the rasterizer uses greyscale anti-aliasing instead * of color (a necessary compromise when one doesn't know the screen * characteristics), the unhinted vertical features preserve the design's * weight and spacing much better than aliased type would. @@ -135,7 +134,7 @@ FT_BEGIN_HEADER * each being rounded to the nearest pixel edge, taking care of overshoot * suppression at small sizes, stem darkening, and scaling. * - * Hstems (this is, hint values defined in the font to help align + * Hstems (that is, hint values defined in the font to help align * horizontal features) that fall within a blue zone are said to be * 'captured' and are aligned to that zone. Uncaptured stems are moved * in one of four ways, top edge up or down, bottom edge up or down. @@ -213,16 +212,14 @@ FT_BEGIN_HEADER * @description: * While FreeType's TrueType driver doesn't expose API functions by * itself, it is possible to control its behaviour with @FT_Property_Set - * and @FT_Property_Get. The following lists the available properties - * together with the necessary macros and structures. - * - * The TrueType driver's module name is 'truetype'. + * and @FT_Property_Get. * - * A single property @interpreter-version is available, as documented in - * the @properties section. + * The TrueType driver's module name is 'truetype'; a single property + * @interpreter-version is available, as documented in the @properties + * section. * - * We start with a list of definitions, kindly provided by Greg - * Hitchcock. + * To help understand the differences between interpreter versions, we + * introduce a list of definitions, kindly provided by Greg Hitchcock. * * _Bi-Level Rendering_ * @@ -301,6 +298,31 @@ FT_BEGIN_HEADER */ + /************************************************************************** + * + * @section: + * ot_svg_driver + * + * @title: + * The SVG driver + * + * @abstract: + * Controlling the external rendering of OT-SVG glyphs. + * + * @description: + * By default, FreeType can only load the 'SVG~' table of OpenType fonts + * if configuration macro `FT_CONFIG_OPTION_SVG` is defined. To make it + * render SVG glyphs, an external SVG rendering library is needed. All + * details on the interface between FreeType and the external library + * via function hooks can be found in section @svg_fonts. + * + * The OT-SVG driver's module name is 'ot-svg'; it supports a single + * property called @svg-hooks, documented below in the @properties + * section. + * + */ + + /************************************************************************** * * @section: @@ -363,12 +385,8 @@ FT_BEGIN_HEADER * The same holds for the Type~1 and CID modules if compiled with * `T1_CONFIG_OPTION_OLD_ENGINE`. * - * For the 'cff' module, the default engine is 'freetype' if - * `CFF_CONFIG_OPTION_OLD_ENGINE` is defined, and 'adobe' otherwise. - * - * For both the 'type1' and 't1cid' modules, the default engine is - * 'freetype' if `T1_CONFIG_OPTION_OLD_ENGINE` is defined, and 'adobe' - * otherwise. + * For the 'cff' module, the default engine is 'adobe'. For both the + * 'type1' and 't1cid' modules, the default engine is 'adobe', too. * * @note: * This property can be used with @FT_Property_Get also. @@ -427,12 +445,8 @@ FT_BEGIN_HEADER * counteracts the 'thinning out' of glyphs, making text remain readable * at smaller sizes. * - * By default, the Adobe engines for CFF, Type~1, and CID fonts darken - * stems at smaller sizes, regardless of hinting, to enhance contrast. - * Setting this property, stem darkening gets switched off. - * * For the auto-hinter, stem-darkening is experimental currently and thus - * switched off by default (this is, `no-stem-darkening` is set to TRUE + * switched off by default (that is, `no-stem-darkening` is set to TRUE * by default). Total consistency with the CFF driver is not achieved * right now because the emboldening method differs and glyphs must be * scaled down on the Y-axis to keep outline points inside their @@ -637,11 +651,8 @@ FT_BEGIN_HEADER * Windows~98; only grayscale and B/W rasterizing is supported. * * TT_INTERPRETER_VERSION_38 :: - * Version~38 corresponds to MS rasterizer v.1.9; it is roughly - * equivalent to the hinting provided by DirectWrite ClearType (as can - * be found, for example, in the Internet Explorer~9 running on - * Windows~7). It is used in FreeType to select the 'Infinality' - * subpixel hinting code. The code may be removed in a future version. + * Version~38 is the same Version~40. The original 'Infinality' code is + * no longer available. * * TT_INTERPRETER_VERSION_40 :: * Version~40 corresponds to MS rasterizer v.2.1; it is roughly @@ -806,6 +817,39 @@ FT_BEGIN_HEADER * 2.5 */ + /************************************************************************** + * + * @property: + * svg-hooks + * + * @description: + * Set up the interface between FreeType and an extern SVG rendering + * library like 'librsvg'. All details on the function hooks can be + * found in section @svg_fonts. + * + * @example: + * The following example code expects that the four hook functions + * `svg_*` are defined elsewhere. Error handling is omitted, too. + * + * ``` + * FT_Library library; + * SVG_RendererHooks hooks = { + * (SVG_Lib_Init_Func)svg_init, + * (SVG_Lib_Free_Func)svg_free, + * (SVG_Lib_Render_Func)svg_render, + * (SVG_Lib_Preset_Slot_Func)svg_preset_slot }; + * + * + * FT_Init_FreeType( &library ); + * + * FT_Property_Set( library, "ot-svg", + * "svg-hooks", &hooks ); + * ``` + * + * @since: + * 2.12 + */ + /************************************************************************** * @@ -1171,48 +1215,18 @@ FT_BEGIN_HEADER * warping * * @description: - * **Experimental only** + * **Obsolete** * - * If FreeType gets compiled with option `AF_CONFIG_OPTION_USE_WARPER` to - * activate the warp hinting code in the auto-hinter, this property - * switches warping on and off. + * This property was always experimental and probably never worked + * correctly. It was entirely removed from the FreeType~2 sources. This + * entry is only here for historical reference. * - * Warping only works in 'normal' auto-hinting mode replacing it. The - * idea of the code is to slightly scale and shift a glyph along the + * Warping only worked in 'normal' auto-hinting mode replacing it. The + * idea of the code was to slightly scale and shift a glyph along the * non-hinted dimension (which is usually the horizontal axis) so that as - * much of its segments are aligned (more or less) to the grid. To find + * much of its segments were aligned (more or less) to the grid. To find * out a glyph's optimal scaling and shifting value, various parameter - * combinations are tried and scored. - * - * By default, warping is off. - * - * @note: - * This property can be used with @FT_Property_Get also. - * - * This property can be set via the `FREETYPE_PROPERTIES` environment - * variable (using values 1 and 0 for 'on' and 'off', respectively). - * - * The warping code can also change advance widths. Have a look at the - * `lsb_delta` and `rsb_delta` fields in the @FT_GlyphSlotRec structure - * for details on improving inter-glyph distances while rendering. - * - * Since warping is a global property of the auto-hinter it is best to - * change its value before rendering any face. Otherwise, you should - * reload all faces that get auto-hinted in 'normal' hinting mode. - * - * @example: - * This example shows how to switch on warping (omitting the error - * handling). - * - * ``` - * FT_Library library; - * FT_Bool warping = 1; - * - * - * FT_Init_FreeType( &library ); - * - * FT_Property_Set( library, "autofitter", "warping", &warping ); - * ``` + * combinations were tried and scored. * * @since: * 2.6 diff --git a/src/font/freetype-2.10.2/include/freetype/fterrdef.h b/3rdparty/freetype-2.13.2/include/freetype/fterrdef.h similarity index 97% rename from src/font/freetype-2.10.2/include/freetype/fterrdef.h rename to 3rdparty/freetype-2.13.2/include/freetype/fterrdef.h index 895d2d4dc..d59b3cc2d 100644 --- a/src/font/freetype-2.10.2/include/freetype/fterrdef.h +++ b/3rdparty/freetype-2.13.2/include/freetype/fterrdef.h @@ -4,7 +4,7 @@ * * FreeType error codes (specification). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -101,6 +101,8 @@ "too many hints" ) FT_ERRORDEF_( Invalid_Pixel_Size, 0x17, "invalid pixel size" ) + FT_ERRORDEF_( Invalid_SVG_Document, 0x18, + "invalid SVG document" ) /* handle errors */ @@ -234,6 +236,8 @@ "found FDEF or IDEF opcode in glyf bytecode" ) FT_ERRORDEF_( Missing_Bitmap, 0x9D, "missing bitmap in strike" ) + FT_ERRORDEF_( Missing_SVG_Hooks, 0x9E, + "SVG hooks have not been set" ) /* CFF, CID, and Type 1 errors */ diff --git a/src/font/freetype-2.10.2/include/freetype/fterrors.h b/3rdparty/freetype-2.13.2/include/freetype/fterrors.h similarity index 89% rename from src/font/freetype-2.10.2/include/freetype/fterrors.h rename to 3rdparty/freetype-2.13.2/include/freetype/fterrors.h index 771bc5db5..15ef3f76b 100644 --- a/src/font/freetype-2.10.2/include/freetype/fterrors.h +++ b/3rdparty/freetype-2.13.2/include/freetype/fterrors.h @@ -4,7 +4,7 @@ * * FreeType error code handling (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -29,7 +29,7 @@ * * @description: * The header file `fterrors.h` (which is automatically included by - * `freetype.h` defines the handling of FreeType's enumeration + * `freetype.h`) defines the handling of FreeType's enumeration * constants. It can also be used to generate error message strings * with a small macro trick explained below. * @@ -89,7 +89,7 @@ * const char* err_msg; * } ft_errors[] = * - * #include FT_ERRORS_H + * #include * ``` * * An alternative to using an array is a switch statement. @@ -124,7 +124,7 @@ /* include module base error codes */ -#include FT_MODULE_ERRORS_H +#include /*******************************************************************/ @@ -197,7 +197,7 @@ /* now include the error codes */ -#include FT_ERROR_DEFINITIONS_H +#include #ifdef FT_ERROR_END_LIST @@ -232,11 +232,16 @@ #undef FT_ERR_PREFIX #endif - /* FT_INCLUDE_ERR_PROTOS: Control if function prototypes should be */ - /* included with `#include FT_ERRORS_H'. This is */ - /* only true where `FT_ERRORDEF` is undefined. */ - /* FT_ERR_PROTOS_DEFINED: Actual multiple-inclusion protection of */ - /* `fterrors.h`. */ + /* FT_INCLUDE_ERR_PROTOS: Control whether function prototypes should be */ + /* included with */ + /* */ + /* #include */ + /* */ + /* This is only true where `FT_ERRORDEF` is */ + /* undefined. */ + /* */ + /* FT_ERR_PROTOS_DEFINED: Actual multiple-inclusion protection of */ + /* `fterrors.h`. */ #ifdef FT_INCLUDE_ERR_PROTOS #undef FT_INCLUDE_ERR_PROTOS @@ -276,6 +281,8 @@ FT_BEGIN_HEADER FT_EXPORT( const char* ) FT_Error_String( FT_Error error_code ); + /* */ + FT_END_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/ftfntfmt.h b/3rdparty/freetype-2.13.2/include/freetype/ftfntfmt.h similarity index 96% rename from src/font/freetype-2.10.2/include/freetype/ftfntfmt.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftfntfmt.h index ad5a1d416..c0018fc83 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftfntfmt.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftfntfmt.h @@ -4,7 +4,7 @@ * * Support functions for font formats. * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,7 @@ #ifndef FTFNTFMT_H_ #define FTFNTFMT_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" diff --git a/src/font/freetype-2.10.2/include/freetype/ftgasp.h b/3rdparty/freetype-2.13.2/include/freetype/ftgasp.h similarity index 98% rename from src/font/freetype-2.10.2/include/freetype/ftgasp.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftgasp.h index aca1a1329..d5f19add8 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftgasp.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftgasp.h @@ -4,7 +4,7 @@ * * Access of TrueType's 'gasp' table (specification). * - * Copyright (C) 2007-2020 by + * Copyright (C) 2007-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,7 @@ #ifndef FTGASP_H_ #define FTGASP_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" diff --git a/src/font/freetype-2.10.2/include/freetype/ftglyph.h b/3rdparty/freetype-2.13.2/include/freetype/ftglyph.h similarity index 83% rename from src/font/freetype-2.10.2/include/freetype/ftglyph.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftglyph.h index ec515a369..4658895f7 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftglyph.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftglyph.h @@ -4,7 +4,7 @@ * * FreeType convenience functions to handle glyphs (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -33,8 +33,7 @@ #define FTGLYPH_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" @@ -127,7 +126,7 @@ FT_BEGIN_HEADER * * @description: * A handle to an object used to model a bitmap glyph image. This is a - * sub-class of @FT_Glyph, and a pointer to @FT_BitmapGlyphRec. + * 'sub-class' of @FT_Glyph, and a pointer to @FT_BitmapGlyphRec. */ typedef struct FT_BitmapGlyphRec_* FT_BitmapGlyph; @@ -143,7 +142,7 @@ FT_BEGIN_HEADER * * @fields: * root :: - * The root @FT_Glyph fields. + * The root fields of @FT_Glyph. * * left :: * The left-side bearing, i.e., the horizontal distance from the @@ -182,7 +181,7 @@ FT_BEGIN_HEADER * * @description: * A handle to an object used to model an outline glyph image. This is a - * sub-class of @FT_Glyph, and a pointer to @FT_OutlineGlyphRec. + * 'sub-class' of @FT_Glyph, and a pointer to @FT_OutlineGlyphRec. */ typedef struct FT_OutlineGlyphRec_* FT_OutlineGlyph; @@ -223,6 +222,92 @@ FT_BEGIN_HEADER } FT_OutlineGlyphRec; + /************************************************************************** + * + * @type: + * FT_SvgGlyph + * + * @description: + * A handle to an object used to model an SVG glyph. This is a + * 'sub-class' of @FT_Glyph, and a pointer to @FT_SvgGlyphRec. + * + * @since: + * 2.12 + */ + typedef struct FT_SvgGlyphRec_* FT_SvgGlyph; + + + /************************************************************************** + * + * @struct: + * FT_SvgGlyphRec + * + * @description: + * A structure used for OT-SVG glyphs. This is a 'sub-class' of + * @FT_GlyphRec. + * + * @fields: + * root :: + * The root @FT_GlyphRec fields. + * + * svg_document :: + * A pointer to the SVG document. + * + * svg_document_length :: + * The length of `svg_document`. + * + * glyph_index :: + * The index of the glyph to be rendered. + * + * metrics :: + * A metrics object storing the size information. + * + * units_per_EM :: + * The size of the EM square. + * + * start_glyph_id :: + * The first glyph ID in the glyph range covered by this document. + * + * end_glyph_id :: + * The last glyph ID in the glyph range covered by this document. + * + * transform :: + * A 2x2 transformation matrix to apply to the glyph while rendering + * it. + * + * delta :: + * Translation to apply to the glyph while rendering. + * + * @note: + * The Glyph Management API requires @FT_Glyph or its 'sub-class' to have + * all the information needed to completely define the glyph's rendering. + * Outline-based glyphs can directly apply transformations to the outline + * but this is not possible for an SVG document that hasn't been parsed. + * Therefore, the transformation is stored along with the document. In + * the absence of a 'ViewBox' or 'Width'/'Height' attribute, the size of + * the ViewPort should be assumed to be 'units_per_EM'. + */ + typedef struct FT_SvgGlyphRec_ + { + FT_GlyphRec root; + + FT_Byte* svg_document; + FT_ULong svg_document_length; + + FT_UInt glyph_index; + + FT_Size_Metrics metrics; + FT_UShort units_per_EM; + + FT_UShort start_glyph_id; + FT_UShort end_glyph_id; + + FT_Matrix transform; + FT_Vector delta; + + } FT_SvgGlyphRec; + + /************************************************************************** * * @function: @@ -270,7 +355,7 @@ FT_BEGIN_HEADER * * @output: * aglyph :: - * A handle to the glyph object. + * A handle to the glyph object. `NULL` in case of error. * * @return: * FreeType error code. 0~means success. @@ -300,7 +385,7 @@ FT_BEGIN_HEADER * * @output: * target :: - * A handle to the target glyph object. 0~in case of error. + * A handle to the target glyph object. `NULL` in case of error. * * @return: * FreeType error code. 0~means success. @@ -328,7 +413,7 @@ FT_BEGIN_HEADER * * delta :: * A pointer to a 2d vector to apply. Coordinates are expressed in - * 1/64th of a pixel. + * 1/64 of a pixel. * * @return: * FreeType error code (if not 0, the glyph format is not scalable). @@ -338,9 +423,9 @@ FT_BEGIN_HEADER * vector. */ FT_EXPORT( FT_Error ) - FT_Glyph_Transform( FT_Glyph glyph, - FT_Matrix* matrix, - FT_Vector* delta ); + FT_Glyph_Transform( FT_Glyph glyph, + const FT_Matrix* matrix, + const FT_Vector* delta ); /************************************************************************** @@ -415,7 +500,7 @@ FT_BEGIN_HEADER * @output: * acbox :: * The glyph coordinate bounding box. Coordinates are expressed in - * 1/64th of pixels if it is grid-fitted. + * 1/64 of pixels if it is grid-fitted. * * @note: * Coordinates are relative to the glyph origin, using the y~upwards @@ -499,9 +584,9 @@ FT_BEGIN_HEADER * The glyph image is translated with the `origin` vector before * rendering. * - * The first parameter is a pointer to an @FT_Glyph handle, that will be + * The first parameter is a pointer to an @FT_Glyph handle that will be * _replaced_ by this function (with newly allocated data). Typically, - * you would use (omitting error handling): + * you would do something like the following (omitting error handling). * * ``` * FT_Glyph glyph; @@ -518,7 +603,7 @@ FT_BEGIN_HEADER * if ( glyph->format != FT_GLYPH_FORMAT_BITMAP ) * { * error = FT_Glyph_To_Bitmap( &glyph, FT_RENDER_MODE_NORMAL, - * 0, 1 ); + * 0, 1 ); * if ( error ) // `glyph' unchanged * ... * } @@ -533,7 +618,7 @@ FT_BEGIN_HEADER * FT_Done_Glyph( glyph ); * ``` * - * Here is another example, again without error handling: + * Here is another example, again without error handling. * * ``` * FT_Glyph glyphs[MAX_GLYPHS] @@ -570,10 +655,10 @@ FT_BEGIN_HEADER * ``` */ FT_EXPORT( FT_Error ) - FT_Glyph_To_Bitmap( FT_Glyph* the_glyph, - FT_Render_Mode render_mode, - FT_Vector* origin, - FT_Bool destroy ); + FT_Glyph_To_Bitmap( FT_Glyph* the_glyph, + FT_Render_Mode render_mode, + const FT_Vector* origin, + FT_Bool destroy ); /************************************************************************** @@ -586,7 +671,7 @@ FT_BEGIN_HEADER * * @input: * glyph :: - * A handle to the target glyph object. + * A handle to the target glyph object. Can be `NULL`. */ FT_EXPORT( void ) FT_Done_Glyph( FT_Glyph glyph ); diff --git a/src/font/freetype-2.10.2/include/freetype/ftgxval.h b/3rdparty/freetype-2.13.2/include/freetype/ftgxval.h similarity index 99% rename from src/font/freetype-2.10.2/include/freetype/ftgxval.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftgxval.h index 691a73b94..e8de9a6ed 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftgxval.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftgxval.h @@ -4,7 +4,7 @@ * * FreeType API for validating TrueTypeGX/AAT tables (specification). * - * Copyright (C) 2004-2020 by + * Copyright (C) 2004-2023 by * Masatake YAMATO, Redhat K.K, * David Turner, Robert Wilhelm, and Werner Lemberg. * @@ -28,8 +28,7 @@ #ifndef FTGXVAL_H_ #define FTGXVAL_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" diff --git a/src/font/freetype-2.10.2/include/freetype/ftgzip.h b/3rdparty/freetype-2.13.2/include/freetype/ftgzip.h similarity index 97% rename from src/font/freetype-2.10.2/include/freetype/ftgzip.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftgzip.h index f588c8503..443ec29db 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftgzip.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftgzip.h @@ -4,7 +4,7 @@ * * Gzip-compressed stream support. * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,7 @@ #ifndef FTGZIP_H_ #define FTGZIP_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" @@ -43,6 +42,16 @@ FT_BEGIN_HEADER * Using gzip-compressed font files. * * @description: + * In certain builds of the library, gzip compression recognition is + * automatically handled when calling @FT_New_Face or @FT_Open_Face. + * This means that if no font driver is capable of handling the raw + * compressed file, the library will try to open a gzipped stream from it + * and re-open the face with it. + * + * The stream implementation is very basic and resets the decompression + * process each time seeking backwards is needed within the stream, + * which significantly undermines the performance. + * * This section contains the declaration of Gzip-specific functions. * */ @@ -75,15 +84,6 @@ FT_BEGIN_HEADER * **not** call `FT_Stream_Close` on the source stream. None of the * stream objects will be released to the heap. * - * The stream implementation is very basic and resets the decompression - * process each time seeking backwards is needed within the stream. - * - * In certain builds of the library, gzip compression recognition is - * automatically handled when calling @FT_New_Face or @FT_Open_Face. - * This means that if no font driver is capable of handling the raw - * compressed file, the library will try to open a gzipped stream from it - * and re-open the face with it. - * * This function may return `FT_Err_Unimplemented_Feature` if your build * of FreeType was not compiled with zlib support. */ diff --git a/src/font/freetype-2.10.2/include/freetype/ftimage.h b/3rdparty/freetype-2.13.2/include/freetype/ftimage.h similarity index 88% rename from src/font/freetype-2.10.2/include/freetype/ftimage.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftimage.h index 185967c1b..6baa81256 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftimage.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftimage.h @@ -5,7 +5,7 @@ * FreeType glyph image formats and default raster interface * (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,7 +19,7 @@ /************************************************************************** * * Note: A 'raster' is simply a scan-line converter, used to render - * FT_Outlines into FT_Bitmaps. + * `FT_Outline`s into `FT_Bitmap`s. * */ @@ -28,12 +28,6 @@ #define FTIMAGE_H_ - /* STANDALONE_ is from ftgrays.c */ -#ifndef STANDALONE_ -#include -#endif - - FT_BEGIN_HEADER @@ -202,6 +196,11 @@ FT_BEGIN_HEADER #define ft_pixel_mode_pal2 FT_PIXEL_MODE_GRAY2 #define ft_pixel_mode_pal4 FT_PIXEL_MODE_GRAY4 + /* */ + + /* For debugging, the @FT_Pixel_Mode enumeration must stay in sync */ + /* with the `pixel_modes` array in file `ftobjs.c`. */ + /************************************************************************** * @@ -257,6 +256,12 @@ FT_BEGIN_HEADER * palette :: * A typeless pointer to the bitmap palette; this field is intended for * paletted pixel modes. Not used currently. + * + * @note: + * `width` and `rows` refer to the *physical* size of the bitmap, not the + * *logical* one. For example, if @FT_Pixel_Mode is set to + * `FT_PIXEL_MODE_LCD`, the logical width is a just a third of the + * physical one. */ typedef struct FT_Bitmap_ { @@ -401,6 +406,13 @@ FT_BEGIN_HEADER * if @FT_OUTLINE_IGNORE_DROPOUTS is set. See below for more * information. * + * FT_OUTLINE_OVERLAP :: + * [Since 2.10.3] This flag indicates that this outline contains + * overlapping contours and the anti-aliased renderer should perform + * oversampling to mitigate possible artifacts. This flag should _not_ + * be set for well designed glyphs without overlaps because it quadruples + * the rendering time. + * * FT_OUTLINE_HIGH_PRECISION :: * This flag indicates that the scan-line converter should try to * convert this outline to bitmaps with the highest possible quality. @@ -432,6 +444,7 @@ FT_BEGIN_HEADER #define FT_OUTLINE_IGNORE_DROPOUTS 0x8 #define FT_OUTLINE_SMART_DROPOUTS 0x10 #define FT_OUTLINE_INCLUDE_STUBS 0x20 +#define FT_OUTLINE_OVERLAP 0x40 #define FT_OUTLINE_HIGH_PRECISION 0x100 #define FT_OUTLINE_SINGLE_PASS 0x200 @@ -688,11 +701,13 @@ FT_BEGIN_HEADER * to get a simple enumeration without assigning special numbers. */ #ifndef FT_IMAGE_TAG -#define FT_IMAGE_TAG( value, _x1, _x2, _x3, _x4 ) \ - value = ( ( (unsigned long)_x1 << 24 ) | \ - ( (unsigned long)_x2 << 16 ) | \ - ( (unsigned long)_x3 << 8 ) | \ - (unsigned long)_x4 ) + +#define FT_IMAGE_TAG( value, _x1, _x2, _x3, _x4 ) \ + value = ( ( FT_STATIC_BYTE_CAST( unsigned long, _x1 ) << 24 ) | \ + ( FT_STATIC_BYTE_CAST( unsigned long, _x2 ) << 16 ) | \ + ( FT_STATIC_BYTE_CAST( unsigned long, _x3 ) << 8 ) | \ + FT_STATIC_BYTE_CAST( unsigned long, _x4 ) ) + #endif /* FT_IMAGE_TAG */ @@ -732,6 +747,10 @@ FT_BEGIN_HEADER * contours. Some Type~1 fonts, like those in the Hershey family, * contain glyphs in this format. These are described as @FT_Outline, * but FreeType isn't currently capable of rendering them correctly. + * + * FT_GLYPH_FORMAT_SVG :: + * [Since 2.12] The glyph is represented by an SVG document in the + * 'SVG~' table. */ typedef enum FT_Glyph_Format_ { @@ -740,7 +759,8 @@ FT_BEGIN_HEADER FT_IMAGE_TAG( FT_GLYPH_FORMAT_COMPOSITE, 'c', 'o', 'm', 'p' ), FT_IMAGE_TAG( FT_GLYPH_FORMAT_BITMAP, 'b', 'i', 't', 's' ), FT_IMAGE_TAG( FT_GLYPH_FORMAT_OUTLINE, 'o', 'u', 't', 'l' ), - FT_IMAGE_TAG( FT_GLYPH_FORMAT_PLOTTER, 'p', 'l', 'o', 't' ) + FT_IMAGE_TAG( FT_GLYPH_FORMAT_PLOTTER, 'p', 'l', 'o', 't' ), + FT_IMAGE_TAG( FT_GLYPH_FORMAT_SVG, 'S', 'V', 'G', ' ' ) } FT_Glyph_Format; @@ -765,17 +785,6 @@ FT_BEGIN_HEADER /*************************************************************************/ - /************************************************************************** - * - * A raster is a scan converter, in charge of rendering an outline into a - * bitmap. This section contains the public API for rasters. - * - * Note that in FreeType 2, all rasters are now encapsulated within - * specific modules called 'renderers'. See `ftrender.h` for more details - * on renderers. - * - */ - /************************************************************************** * @@ -789,16 +798,35 @@ FT_BEGIN_HEADER * How vectorial outlines are converted into bitmaps and pixmaps. * * @description: - * This section contains technical definitions. + * A raster or a rasterizer is a scan converter in charge of producing a + * pixel coverage bitmap that can be used as an alpha channel when + * compositing a glyph with a background. FreeType comes with two + * rasterizers: bilevel `raster1` and anti-aliased `smooth` are two + * separate modules. They are usually called from the high-level + * @FT_Load_Glyph or @FT_Render_Glyph functions and produce the entire + * coverage bitmap at once, while staying largely invisible to users. + * + * Instead of working with complete coverage bitmaps, it is also possible + * to intercept consecutive pixel runs on the same scanline with the same + * coverage, called _spans_, and process them individually. Only the + * `smooth` rasterizer permits this when calling @FT_Outline_Render with + * @FT_Raster_Params as described below. + * + * Working with either complete bitmaps or spans it is important to think + * of them as colorless coverage objects suitable as alpha channels to + * blend arbitrary colors with a background. For best results, it is + * recommended to use gamma correction, too. + * + * This section also describes the public API needed to set up alternative + * @FT_Renderer modules. * * @order: - * FT_Raster * FT_Span * FT_SpanFunc - * * FT_Raster_Params * FT_RASTER_FLAG_XXX * + * FT_Raster * FT_Raster_NewFunc * FT_Raster_DoneFunc * FT_Raster_ResetFunc @@ -809,26 +837,14 @@ FT_BEGIN_HEADER */ - /************************************************************************** - * - * @type: - * FT_Raster - * - * @description: - * An opaque handle (pointer) to a raster object. Each object can be - * used independently to convert an outline into a bitmap or pixmap. - */ - typedef struct FT_RasterRec_* FT_Raster; - - /************************************************************************** * * @struct: * FT_Span * * @description: - * A structure used to model a single span of gray pixels when rendering - * an anti-aliased bitmap. + * A structure to model a single span of consecutive pixels when + * rendering an anti-aliased bitmap. * * @fields: * x :: @@ -845,8 +861,8 @@ FT_BEGIN_HEADER * This structure is used by the span drawing callback type named * @FT_SpanFunc that takes the y~coordinate of the span as a parameter. * - * The coverage value is always between 0 and 255. If you want less gray - * values, the callback function has to reduce them. + * The anti-aliased rasterizer produces coverage values from 0 to 255, + * that is, from completely transparent to completely opaque. */ typedef struct FT_Span_ { @@ -864,8 +880,8 @@ FT_BEGIN_HEADER * * @description: * A function used as a call-back by the anti-aliased renderer in order - * to let client applications draw themselves the gray pixel spans on - * each scan line. + * to let client applications draw themselves the pixel spans on each + * scan line. * * @input: * y :: @@ -881,11 +897,12 @@ FT_BEGIN_HEADER * User-supplied data that is passed to the callback. * * @note: - * This callback allows client applications to directly render the gray - * spans of the anti-aliased bitmap to any kind of surfaces. + * This callback allows client applications to directly render the spans + * of the anti-aliased bitmap to any kind of surfaces. * * This can be used to write anti-aliased outlines directly to a given - * background bitmap, and even perform translucency. + * background bitmap using alpha compositing. It can also be used for + * oversampling and averaging. */ typedef void (*FT_SpanFunc)( int y, @@ -955,11 +972,17 @@ FT_BEGIN_HEADER * will be clipped to a box specified in the `clip_box` field of the * @FT_Raster_Params structure. Otherwise, the `clip_box` is * effectively set to the bounding box and all spans are generated. + * + * FT_RASTER_FLAG_SDF :: + * This flag is set to indicate that a signed distance field glyph + * image should be generated. This is only used while rendering with + * the @FT_RENDER_MODE_SDF render mode. */ #define FT_RASTER_FLAG_DEFAULT 0x0 #define FT_RASTER_FLAG_AA 0x1 #define FT_RASTER_FLAG_DIRECT 0x2 #define FT_RASTER_FLAG_CLIP 0x4 +#define FT_RASTER_FLAG_SDF 0x8 /* these constants are deprecated; use the corresponding */ /* `FT_RASTER_FLAG_XXX` values instead */ @@ -1004,20 +1027,26 @@ FT_BEGIN_HEADER * User-supplied data that is passed to each drawing callback. * * clip_box :: - * An optional clipping box. It is only used in direct rendering mode. - * Note that coordinates here should be expressed in _integer_ pixels - * (and not in 26.6 fixed-point units). + * An optional span clipping box expressed in _integer_ pixels + * (not in 26.6 fixed-point units). * * @note: - * An anti-aliased glyph bitmap is drawn if the @FT_RASTER_FLAG_AA bit - * flag is set in the `flags` field, otherwise a monochrome bitmap is - * generated. - * - * If the @FT_RASTER_FLAG_DIRECT bit flag is set in `flags`, the raster - * will call the `gray_spans` callback to draw gray pixel spans. This - * allows direct composition over a pre-existing bitmap through - * user-provided callbacks to perform the span drawing and composition. - * Not supported by the monochrome rasterizer. + * The @FT_RASTER_FLAG_AA bit flag must be set in the `flags` to + * generate an anti-aliased glyph bitmap, otherwise a monochrome bitmap + * is generated. The `target` should have appropriate pixel mode and its + * dimensions define the clipping region. + * + * If both @FT_RASTER_FLAG_AA and @FT_RASTER_FLAG_DIRECT bit flags + * are set in `flags`, the raster calls an @FT_SpanFunc callback + * `gray_spans` with `user` data as an argument ignoring `target`. This + * allows direct composition over a pre-existing user surface to perform + * the span drawing and composition. To optionally clip the spans, set + * the @FT_RASTER_FLAG_CLIP flag and `clip_box`. The monochrome raster + * does not support the direct mode. + * + * The gray-level rasterizer always uses 256 gray levels. If you want + * fewer gray levels, you have to use @FT_RASTER_FLAG_DIRECT and reduce + * the levels in the callback function. */ typedef struct FT_Raster_Params_ { @@ -1034,6 +1063,23 @@ FT_BEGIN_HEADER } FT_Raster_Params; + /************************************************************************** + * + * @type: + * FT_Raster + * + * @description: + * An opaque handle (pointer) to a raster object. Each object can be + * used independently to convert an outline into a bitmap or pixmap. + * + * @note: + * In FreeType 2, all rasters are now encapsulated within specific + * @FT_Renderer modules and only used in their context. + * + */ + typedef struct FT_RasterRec_* FT_Raster; + + /************************************************************************** * * @functype: diff --git a/src/font/freetype-2.10.2/include/freetype/ftincrem.h b/3rdparty/freetype-2.13.2/include/freetype/ftincrem.h similarity index 92% rename from src/font/freetype-2.10.2/include/freetype/ftincrem.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftincrem.h index 8c00cfe41..2d4f5def2 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftincrem.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftincrem.h @@ -4,7 +4,7 @@ * * FreeType incremental loading (specification). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,9 +19,8 @@ #ifndef FTINCREM_H_ #define FTINCREM_H_ -#include -#include FT_FREETYPE_H -#include FT_PARAMETER_TAGS_H +#include +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" @@ -214,9 +213,14 @@ FT_BEGIN_HEADER * * @description: * A function used to retrieve the basic metrics of a given glyph index - * before accessing its data. This is necessary because, in certain - * formats like TrueType, the metrics are stored in a different place - * from the glyph images proper. + * before accessing its data. This allows for handling font types such + * as PCL~XL Format~1, Class~2 downloaded TrueType fonts, where the glyph + * metrics (`hmtx` and `vmtx` tables) are permitted to be omitted from + * the font, and the relevant metrics included in the header of the glyph + * outline data. Importantly, this is not intended to allow custom glyph + * metrics (for example, Postscript Metrics dictionaries), because that + * conflicts with the requirements of outline hinting. Such custom + * metrics must be handled separately, by the calling application. * * @input: * incremental :: @@ -236,7 +240,7 @@ FT_BEGIN_HEADER * * @output: * ametrics :: - * The replacement glyph metrics in font units. + * The glyph metrics in font units. * */ typedef FT_Error @@ -265,7 +269,7 @@ FT_BEGIN_HEADER * * get_glyph_metrics :: * The function to get glyph metrics. May be null if the font does not - * provide overriding glyph metrics. + * require it. * */ typedef struct FT_Incremental_FuncsRec_ diff --git a/src/font/freetype-2.10.2/include/freetype/ftlcdfil.h b/3rdparty/freetype-2.13.2/include/freetype/ftlcdfil.h similarity index 84% rename from src/font/freetype-2.10.2/include/freetype/ftlcdfil.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftlcdfil.h index c5516d0e0..d3723e16f 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftlcdfil.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftlcdfil.h @@ -5,7 +5,7 @@ * FreeType API for color filtering of subpixel bitmap glyphs * (specification). * - * Copyright (C) 2006-2020 by + * Copyright (C) 2006-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,9 +20,8 @@ #ifndef FTLCDFIL_H_ #define FTLCDFIL_H_ -#include -#include FT_FREETYPE_H -#include FT_PARAMETER_TAGS_H +#include +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" @@ -45,9 +44,9 @@ FT_BEGIN_HEADER * API to control subpixel rendering. * * @description: - * FreeType provides two alternative subpixel rendering technologies. + * FreeType provides two alternative subpixel rendering technologies. * Should you define `FT_CONFIG_OPTION_SUBPIXEL_RENDERING` in your - * `ftoption.h` file, this enables patented ClearType-style rendering. + * `ftoption.h` file, this enables ClearType-style rendering. * Otherwise, Harmony LCD rendering is enabled. These technologies are * controlled differently and API described below, although always * available, performs its function when appropriate method is enabled @@ -56,13 +55,12 @@ FT_BEGIN_HEADER * ClearType-style LCD rendering exploits the color-striped structure of * LCD pixels, increasing the available resolution in the direction of * the stripe (usually horizontal RGB) by a factor of~3. Using the - * subpixels coverages unfiltered can create severe color fringes + * subpixel coverages unfiltered can create severe color fringes * especially when rendering thin features. Indeed, to produce * black-on-white text, the nearby color subpixels must be dimmed - * equally. - * - * A good 5-tap FIR filter should be applied to subpixel coverages - * regardless of pixel boundaries and should have these properties: + * evenly. Therefore, an equalizing 5-tap FIR filter should be applied + * to subpixel coverages regardless of pixel boundaries and should have + * these properties: * * 1. It should be symmetrical, like {~a, b, c, b, a~}, to avoid * any shifts in appearance. @@ -85,7 +83,7 @@ FT_BEGIN_HEADER * Harmony LCD rendering is suitable to panels with any regular subpixel * structure, not just monitors with 3 color striped subpixels, as long * as the color subpixels have fixed positions relative to the pixel - * center. In this case, each color channel is then rendered separately + * center. In this case, each color channel can be rendered separately * after shifting the outline opposite to the subpixel shift so that the * coverage maps are aligned. This method is immune to color fringes * because the shifts do not change integral coverage. @@ -102,9 +100,9 @@ FT_BEGIN_HEADER * clockwise. Harmony with default LCD geometry is equivalent to * ClearType with light filter. * - * As a result of ClearType filtering or Harmony rendering, the - * dimensions of LCD bitmaps can be either wider or taller than the - * dimensions of the corresponding outline with regard to the pixel grid. + * As a result of ClearType filtering or Harmony shifts, the resulting + * dimensions of LCD bitmaps can be slightly wider or taller than the + * dimensions the original outline with regard to the pixel grid. * For example, for @FT_RENDER_MODE_LCD, the filter adds 2~subpixels to * the left, and 2~subpixels to the right. The bitmap offset values are * adjusted accordingly, so clients shouldn't need to modify their layout @@ -139,11 +137,11 @@ FT_BEGIN_HEADER * * FT_LCD_FILTER_DEFAULT :: * This is a beveled, normalized, and color-balanced five-tap filter - * with weights of [0x08 0x4D 0x56 0x4D 0x08] in 1/256th units. + * with weights of [0x08 0x4D 0x56 0x4D 0x08] in 1/256 units. * * FT_LCD_FILTER_LIGHT :: * this is a boxy, normalized, and color-balanced three-tap filter with - * weights of [0x00 0x55 0x56 0x55 0x00] in 1/256th units. + * weights of [0x00 0x55 0x56 0x55 0x00] in 1/256 units. * * FT_LCD_FILTER_LEGACY :: * FT_LCD_FILTER_LEGACY1 :: @@ -177,7 +175,7 @@ FT_BEGIN_HEADER * FT_Library_SetLcdFilter * * @description: - * This function is used to apply color filtering to LCD decimated + * This function is used to change filter applied to LCD decimated * bitmaps, like the ones used when calling @FT_Render_Glyph with * @FT_RENDER_MODE_LCD or @FT_RENDER_MODE_LCD_V. * @@ -196,15 +194,14 @@ FT_BEGIN_HEADER * FreeType error code. 0~means success. * * @note: - * This feature is always disabled by default. Clients must make an - * explicit call to this function with a `filter` value other than - * @FT_LCD_FILTER_NONE in order to enable it. + * Since 2.10.3 the LCD filtering is enabled with @FT_LCD_FILTER_DEFAULT. + * It is no longer necessary to call this function explicitly except + * to choose a different filter or disable filtering altogether with + * @FT_LCD_FILTER_NONE. * - * Due to **PATENTS** covering subpixel rendering, this function doesn't - * do anything except returning `FT_Err_Unimplemented_Feature` if the - * configuration macro `FT_CONFIG_OPTION_SUBPIXEL_RENDERING` is not - * defined in your build of the library, which should correspond to all - * default builds of FreeType. + * This function does nothing but returns `FT_Err_Unimplemented_Feature` + * if the configuration macro `FT_CONFIG_OPTION_SUBPIXEL_RENDERING` is + * not defined in your build of the library. * * @since: * 2.3.0 @@ -229,17 +226,15 @@ FT_BEGIN_HEADER * * weights :: * A pointer to an array; the function copies the first five bytes and - * uses them to specify the filter weights in 1/256th units. + * uses them to specify the filter weights in 1/256 units. * * @return: * FreeType error code. 0~means success. * * @note: - * Due to **PATENTS** covering subpixel rendering, this function doesn't - * do anything except returning `FT_Err_Unimplemented_Feature` if the - * configuration macro `FT_CONFIG_OPTION_SUBPIXEL_RENDERING` is not - * defined in your build of the library, which should correspond to all - * default builds of FreeType. + * This function does nothing but returns `FT_Err_Unimplemented_Feature` + * if the configuration macro `FT_CONFIG_OPTION_SUBPIXEL_RENDERING` is + * not defined in your build of the library. * * LCD filter weights can also be set per face using @FT_Face_Properties * with @FT_PARAM_TAG_LCD_FILTER_WEIGHTS. diff --git a/src/font/freetype-2.10.2/include/freetype/ftlist.h b/3rdparty/freetype-2.13.2/include/freetype/ftlist.h similarity index 98% rename from src/font/freetype-2.10.2/include/freetype/ftlist.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftlist.h index 3f6079f24..b55313133 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftlist.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftlist.h @@ -4,7 +4,7 @@ * * Generic list support for FreeType (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -28,8 +28,7 @@ #define FTLIST_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" diff --git a/3rdparty/freetype-2.13.2/include/freetype/ftlogging.h b/3rdparty/freetype-2.13.2/include/freetype/ftlogging.h new file mode 100644 index 000000000..53b8b8964 --- /dev/null +++ b/3rdparty/freetype-2.13.2/include/freetype/ftlogging.h @@ -0,0 +1,184 @@ +/**************************************************************************** + * + * ftlogging.h + * + * Additional debugging APIs. + * + * Copyright (C) 2020-2023 by + * David Turner, Robert Wilhelm, and Werner Lemberg. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + +#ifndef FTLOGGING_H_ +#define FTLOGGING_H_ + + +#include +#include FT_CONFIG_CONFIG_H + + +FT_BEGIN_HEADER + + + /************************************************************************** + * + * @section: + * debugging_apis + * + * @title: + * External Debugging APIs + * + * @abstract: + * Public APIs to control the `FT_DEBUG_LOGGING` macro. + * + * @description: + * This section contains the declarations of public functions that + * enables fine control of what the `FT_DEBUG_LOGGING` macro outputs. + * + */ + + + /************************************************************************** + * + * @function: + * FT_Trace_Set_Level + * + * @description: + * Change the levels of tracing components of FreeType at run time. + * + * @input: + * tracing_level :: + * New tracing value. + * + * @example: + * The following call makes FreeType trace everything but the 'memory' + * component. + * + * ``` + * FT_Trace_Set_Level( "any:7 memory:0" ); + * ``` + * + * @note: + * This function does nothing if compilation option `FT_DEBUG_LOGGING` + * isn't set. + * + * @since: + * 2.11 + * + */ + FT_EXPORT( void ) + FT_Trace_Set_Level( const char* tracing_level ); + + + /************************************************************************** + * + * @function: + * FT_Trace_Set_Default_Level + * + * @description: + * Reset tracing value of FreeType's components to the default value + * (i.e., to the value of the `FT2_DEBUG` environment value or to NULL + * if `FT2_DEBUG` is not set). + * + * @note: + * This function does nothing if compilation option `FT_DEBUG_LOGGING` + * isn't set. + * + * @since: + * 2.11 + * + */ + FT_EXPORT( void ) + FT_Trace_Set_Default_Level( void ); + + + /************************************************************************** + * + * @functype: + * FT_Custom_Log_Handler + * + * @description: + * A function typedef that is used to handle the logging of tracing and + * debug messages on a file system. + * + * @input: + * ft_component :: + * The name of `FT_COMPONENT` from which the current debug or error + * message is produced. + * + * fmt :: + * Actual debug or tracing message. + * + * args:: + * Arguments of debug or tracing messages. + * + * @since: + * 2.11 + * + */ + typedef void + (*FT_Custom_Log_Handler)( const char* ft_component, + const char* fmt, + va_list args ); + + + /************************************************************************** + * + * @function: + * FT_Set_Log_Handler + * + * @description: + * A function to set a custom log handler. + * + * @input: + * handler :: + * New logging function. + * + * @note: + * This function does nothing if compilation option `FT_DEBUG_LOGGING` + * isn't set. + * + * @since: + * 2.11 + * + */ + FT_EXPORT( void ) + FT_Set_Log_Handler( FT_Custom_Log_Handler handler ); + + + /************************************************************************** + * + * @function: + * FT_Set_Default_Log_Handler + * + * @description: + * A function to undo the effect of @FT_Set_Log_Handler, resetting the + * log handler to FreeType's built-in version. + * + * @note: + * This function does nothing if compilation option `FT_DEBUG_LOGGING` + * isn't set. + * + * @since: + * 2.11 + * + */ + FT_EXPORT( void ) + FT_Set_Default_Log_Handler( void ); + + /* */ + + +FT_END_HEADER + +#endif /* FTLOGGING_H_ */ + + +/* END */ diff --git a/src/font/freetype-2.10.2/include/freetype/ftlzw.h b/3rdparty/freetype-2.13.2/include/freetype/ftlzw.h similarity index 95% rename from src/font/freetype-2.10.2/include/freetype/ftlzw.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftlzw.h index 37a53c1b3..adfd17247 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftlzw.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftlzw.h @@ -4,7 +4,7 @@ * * LZW-compressed stream support. * - * Copyright (C) 2004-2020 by + * Copyright (C) 2004-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,7 @@ #ifndef FTLZW_H_ #define FTLZW_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" @@ -43,6 +42,16 @@ FT_BEGIN_HEADER * Using LZW-compressed font files. * * @description: + * In certain builds of the library, LZW compression recognition is + * automatically handled when calling @FT_New_Face or @FT_Open_Face. + * This means that if no font driver is capable of handling the raw + * compressed file, the library will try to open a LZW stream from it and + * re-open the face with it. + * + * The stream implementation is very basic and resets the decompression + * process each time seeking backwards is needed within the stream, + * which significantly undermines the performance. + * * This section contains the declaration of LZW-specific functions. * */ @@ -73,15 +82,6 @@ FT_BEGIN_HEADER * **not** call `FT_Stream_Close` on the source stream. None of the * stream objects will be released to the heap. * - * The stream implementation is very basic and resets the decompression - * process each time seeking backwards is needed within the stream - * - * In certain builds of the library, LZW compression recognition is - * automatically handled when calling @FT_New_Face or @FT_Open_Face. - * This means that if no font driver is capable of handling the raw - * compressed file, the library will try to open a LZW stream from it and - * re-open the face with it. - * * This function may return `FT_Err_Unimplemented_Feature` if your build * of FreeType was not compiled with LZW support. */ diff --git a/src/font/freetype-2.10.2/include/freetype/ftmac.h b/3rdparty/freetype-2.13.2/include/freetype/ftmac.h similarity index 99% rename from src/font/freetype-2.10.2/include/freetype/ftmac.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftmac.h index c1a0aa373..a91e38f9e 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftmac.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftmac.h @@ -4,7 +4,7 @@ * * Additional Mac-specific API. * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * Just van Rossum, David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -29,7 +29,6 @@ #define FTMAC_H_ -#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/ftmm.h b/3rdparty/freetype-2.13.2/include/freetype/ftmm.h similarity index 89% rename from src/font/freetype-2.10.2/include/freetype/ftmm.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftmm.h index 0d839942b..d145128a9 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftmm.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftmm.h @@ -4,7 +4,7 @@ * * FreeType Multiple Master font interface (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,8 +20,7 @@ #define FTMM_H_ -#include -#include FT_TYPE1_TABLES_H +#include FT_BEGIN_HEADER @@ -48,6 +47,9 @@ FT_BEGIN_HEADER * MM fonts, others will work with all three types. They are similar * enough that a consistent interface makes sense. * + * For Adobe MM fonts, macro @FT_IS_SFNT returns false. For GX and + * OpenType variation fonts, it returns true. + * */ @@ -151,7 +153,7 @@ FT_BEGIN_HEADER * @note: * The fields `minimum`, `def`, and `maximum` are 16.16 fractional values * for TrueType GX and OpenType variation fonts. For Adobe MM fonts, the - * values are integers. + * values are whole numbers (i.e., the fractional part is zero). */ typedef struct FT_Var_Axis_ { @@ -396,6 +398,10 @@ FT_BEGIN_HEADER * FreeType error code. 0~means success. * * @note: + * The design coordinates are 16.16 fractional values for TrueType GX and + * OpenType variation fonts. For Adobe MM fonts, the values are supposed + * to be whole numbers (i.e., the fractional part is zero). + * * [Since 2.8.1] To reset all axes to the default values, call the * function with `num_coords` set to zero and `coords` set to `NULL`. * [Since 2.9] 'Default values' means the currently selected named @@ -438,6 +444,11 @@ FT_BEGIN_HEADER * @return: * FreeType error code. 0~means success. * + * @note: + * The design coordinates are 16.16 fractional values for TrueType GX and + * OpenType variation fonts. For Adobe MM fonts, the values are whole + * numbers (i.e., the fractional part is zero). + * * @since: * 2.7.1 */ @@ -469,9 +480,9 @@ FT_BEGIN_HEADER * the number of axes, use default values for the remaining axes. * * coords :: - * The design coordinates array (each element must be between 0 and 1.0 - * for Adobe MM fonts, and between -1.0 and 1.0 for TrueType GX and - * OpenType variation fonts). + * The design coordinates array. Each element is a 16.16 fractional + * value and must be between 0 and 1.0 for Adobe MM fonts, and between + * -1.0 and 1.0 for TrueType GX and OpenType variation fonts. * * @return: * FreeType error code. 0~means success. @@ -516,7 +527,7 @@ FT_BEGIN_HEADER * * @output: * coords :: - * The normalized blend coordinates array. + * The normalized blend coordinates array (as 16.16 fractional values). * * @return: * FreeType error code. 0~means success. @@ -591,10 +602,12 @@ FT_BEGIN_HEADER * * @note: * Adobe Multiple Master fonts limit the number of designs, and thus the - * length of the weight vector to~16. + * length of the weight vector to 16~elements. * - * If `len` is zero and `weightvector` is `NULL`, the weight vector array - * is reset to the default values. + * If `len` is larger than zero, this function sets the + * @FT_FACE_FLAG_VARIATION bit in @FT_Face's `face_flags` field (i.e., + * @FT_IS_VARIATION will return true). If `len` is zero, this bit flag + * is unset and the weight vector array is reset to the default values. * * The Adobe documentation also states that the values in the * WeightVector array must total 1.0 +/-~0.001. In practice this does @@ -742,6 +755,45 @@ FT_BEGIN_HEADER FT_Set_Named_Instance( FT_Face face, FT_UInt instance_index ); + + /************************************************************************** + * + * @function: + * FT_Get_Default_Named_Instance + * + * @description: + * Retrieve the index of the default named instance, to be used with + * @FT_Set_Named_Instance. + * + * The default instance of a variation font is that instance for which + * the nth axis coordinate is equal to `axis[n].def` (as specified in the + * @FT_MM_Var structure), with~n covering all axes. + * + * FreeType synthesizes a named instance for the default instance if the + * font does not contain such an entry. + * + * @input: + * face :: + * A handle to the source face. + * + * @output: + * instance_index :: + * The index of the default named instance. + * + * @return: + * FreeType error code. 0~means success. + * + * @note: + * For Adobe MM fonts (which don't have named instances) this function + * always returns zero for `instance_index`. + * + * @since: + * 2.13.1 + */ + FT_EXPORT( FT_Error ) + FT_Get_Default_Named_Instance( FT_Face face, + FT_UInt *instance_index ); + /* */ diff --git a/src/font/freetype-2.10.2/include/freetype/ftmodapi.h b/3rdparty/freetype-2.13.2/include/freetype/ftmodapi.h similarity index 94% rename from src/font/freetype-2.10.2/include/freetype/ftmodapi.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftmodapi.h index 01cb5fba8..c8f0c2c2a 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftmodapi.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftmodapi.h @@ -4,7 +4,7 @@ * * FreeType modules public interface (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,8 +20,7 @@ #define FTMODAPI_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" @@ -46,10 +45,12 @@ FT_BEGIN_HEADER * * @description: * The definitions below are used to manage modules within FreeType. - * Modules can be added, upgraded, and removed at runtime. Additionally, - * some module properties can be controlled also. + * Internal and external modules can be added, upgraded, and removed at + * runtime. For example, an alternative renderer or proprietary font + * driver can be registered and prioritized. Additionally, some module + * properties can also be controlled. * - * Here is a list of possible values of the `module_name` field in the + * Here is a list of existing values of the `module_name` field in the * @FT_Module_Class structure. * * ``` @@ -65,7 +66,7 @@ FT_BEGIN_HEADER * psnames * raster1 * sfnt - * smooth, smooth-lcd, smooth-lcdv + * smooth * truetype * type1 * type42 @@ -87,6 +88,7 @@ FT_BEGIN_HEADER * FT_Remove_Module * FT_Add_Default_Modules * + * FT_FACE_DRIVER_NAME * FT_Property_Set * FT_Property_Get * FT_Set_Default_Properties @@ -329,6 +331,27 @@ FT_BEGIN_HEADER FT_Module module ); + /************************************************************************** + * + * @macro: + * FT_FACE_DRIVER_NAME + * + * @description: + * A macro that retrieves the name of a font driver from a face object. + * + * @note: + * The font driver name is a valid `module_name` for @FT_Property_Set + * and @FT_Property_Get. This is not the same as @FT_Get_Font_Format. + * + * @since: + * 2.11 + * + */ +#define FT_FACE_DRIVER_NAME( face ) \ + ( ( *FT_REINTERPRET_CAST( FT_Module_Class**, \ + ( face )->driver ) )->module_name ) + + /************************************************************************** * * @function: @@ -486,8 +509,7 @@ FT_BEGIN_HEADER * * ``` * FREETYPE_PROPERTIES=truetype:interpreter-version=35 \ - * cff:no-stem-darkening=1 \ - * autofitter:warping=1 + * cff:no-stem-darkening=0 * ``` * * @inout: diff --git a/src/font/freetype-2.10.2/include/freetype/ftmoderr.h b/3rdparty/freetype-2.13.2/include/freetype/ftmoderr.h similarity index 97% rename from src/font/freetype-2.10.2/include/freetype/ftmoderr.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftmoderr.h index 5e6aeeb43..c8c892dcc 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftmoderr.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftmoderr.h @@ -4,7 +4,7 @@ * * FreeType module error offsets (specification). * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -94,7 +94,7 @@ * const char* mod_err_msg * } ft_mod_errors[] = * - * #include FT_MODULE_ERRORS_H + * #include * ``` * */ @@ -171,6 +171,7 @@ FT_MODERRDEF( Type42, 0x1400, "Type 42 module" ) FT_MODERRDEF( Winfonts, 0x1500, "Windows FON/FNT module" ) FT_MODERRDEF( GXvalid, 0x1600, "GX validation module" ) + FT_MODERRDEF( Sdf, 0x1700, "Signed distance field raster module" ) #ifdef FT_MODERR_END_LIST diff --git a/src/font/freetype-2.10.2/include/freetype/ftotval.h b/3rdparty/freetype-2.13.2/include/freetype/ftotval.h similarity index 98% rename from src/font/freetype-2.10.2/include/freetype/ftotval.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftotval.h index 6f46c414b..011bdfc83 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftotval.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftotval.h @@ -4,7 +4,7 @@ * * FreeType API for validating OpenType tables (specification). * - * Copyright (C) 2004-2020 by + * Copyright (C) 2004-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -30,8 +30,7 @@ #ifndef FTOTVAL_H_ #define FTOTVAL_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" diff --git a/src/font/freetype-2.10.2/include/freetype/ftoutln.h b/3rdparty/freetype-2.13.2/include/freetype/ftoutln.h similarity index 94% rename from src/font/freetype-2.10.2/include/freetype/ftoutln.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftoutln.h index fa295b0ab..f9329ca40 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftoutln.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftoutln.h @@ -5,7 +5,7 @@ * Support for the FT_Outline type used to store glyph shapes of * most scalable font formats (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -21,8 +21,7 @@ #define FTOUTLN_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" @@ -110,14 +109,16 @@ FT_BEGIN_HEADER * FreeType error code. 0~means success. * * @note: - * A contour that contains a single point only is represented by a 'move - * to' operation followed by 'line to' to the same point. In most cases, - * it is best to filter this out before using the outline for stroking - * purposes (otherwise it would result in a visible dot when round caps - * are used). + * Degenerate contours, segments, and Bezier arcs may be reported. In + * most cases, it is best to filter these out before using the outline + * for stroking or other path modification purposes (which may cause + * degenerate segments to become non-degenrate and visible, like when + * stroke caps are used or the path is otherwise outset). Some glyph + * outlines may contain deliberate degenerate single points for mark + * attachement. * * Similarly, the function returns success for an empty outline also - * (doing nothing, this is, not calling any emitter); if necessary, you + * (doing nothing, that is, not calling any emitter); if necessary, you * should filter this out, too. */ FT_EXPORT( FT_Error ) @@ -483,19 +484,13 @@ FT_BEGIN_HEADER * FreeType error code. 0~means success. * * @note: - * This advanced function uses @FT_Raster_Params as an argument, - * allowing FreeType rasterizer to be used for direct composition, - * translucency, etc. You should know how to set up @FT_Raster_Params - * for this function to work. - * + * This advanced function uses @FT_Raster_Params as an argument. * The field `params.source` will be set to `outline` before the scan * converter is called, which means that the value you give to it is - * actually ignored. - * - * The gray-level rasterizer always uses 256 gray levels. If you want - * less gray levels, you have to provide your own span callback. See the - * @FT_RASTER_FLAG_DIRECT value of the `flags` field in the - * @FT_Raster_Params structure for more details. + * actually ignored. Either `params.target` must point to preallocated + * bitmap, or @FT_RASTER_FLAG_DIRECT must be set in `params.flags` + * allowing FreeType rasterizer to be used for direct composition, + * translucency, etc. See @FT_Raster_Params for more details. */ FT_EXPORT( FT_Error ) FT_Outline_Render( FT_Library library, diff --git a/src/font/freetype-2.10.2/include/freetype/ftparams.h b/3rdparty/freetype-2.13.2/include/freetype/ftparams.h similarity index 91% rename from src/font/freetype-2.10.2/include/freetype/ftparams.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftparams.h index 255c6bb16..6a9f243bc 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftparams.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftparams.h @@ -4,7 +4,7 @@ * * FreeType API for possible FT_Parameter tags (specification only). * - * Copyright (C) 2017-2020 by + * Copyright (C) 2017-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,7 @@ #ifndef FTPARAMS_H_ #define FTPARAMS_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" @@ -113,6 +112,21 @@ FT_BEGIN_HEADER FT_MAKE_TAG( 'i', 'n', 'c', 'r' ) + /************************************************************************** + * + * @enum: + * FT_PARAM_TAG_IGNORE_SBIX + * + * @description: + * A tag for @FT_Parameter to make @FT_Open_Face ignore an 'sbix' table + * while loading a font. Use this if @FT_FACE_FLAG_SBIX is set and you + * want to access the outline glyphs in the font. + * + */ +#define FT_PARAM_TAG_IGNORE_SBIX \ + FT_MAKE_TAG( 'i', 's', 'b', 'x' ) + + /************************************************************************** * * @enum: diff --git a/src/font/freetype-2.10.2/include/freetype/ftpfr.h b/3rdparty/freetype-2.13.2/include/freetype/ftpfr.h similarity index 96% rename from src/font/freetype-2.10.2/include/freetype/ftpfr.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftpfr.h index 58fbbb78d..7111d40a0 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftpfr.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftpfr.h @@ -4,7 +4,7 @@ * * FreeType API for accessing PFR-specific data (specification only). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,7 @@ #ifndef FTPFR_H_ #define FTPFR_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" @@ -162,7 +161,7 @@ FT_BEGIN_HEADER * * @note: * You can use the `x_scale` or `y_scale` results of @FT_Get_PFR_Metrics - * to convert the advance to device subpixels (i.e., 1/64th of pixels). + * to convert the advance to device subpixels (i.e., 1/64 of pixels). */ FT_EXPORT( FT_Error ) FT_Get_PFR_Advance( FT_Face face, diff --git a/src/font/freetype-2.10.2/include/freetype/ftrender.h b/3rdparty/freetype-2.13.2/include/freetype/ftrender.h similarity index 97% rename from src/font/freetype-2.10.2/include/freetype/ftrender.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftrender.h index 684511190..0b6fad32e 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftrender.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftrender.h @@ -4,7 +4,7 @@ * * FreeType renderer modules public interface (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,9 +20,8 @@ #define FTRENDER_H_ -#include -#include FT_MODULE_H -#include FT_GLYPH_H +#include +#include FT_BEGIN_HEADER @@ -159,7 +158,7 @@ FT_BEGIN_HEADER FT_Renderer_GetCBoxFunc get_glyph_cbox; FT_Renderer_SetModeFunc set_mode; - FT_Raster_Funcs* raster_class; + const FT_Raster_Funcs* raster_class; } FT_Renderer_Class; diff --git a/src/font/freetype-2.10.2/include/freetype/ftsizes.h b/3rdparty/freetype-2.13.2/include/freetype/ftsizes.h similarity index 98% rename from src/font/freetype-2.10.2/include/freetype/ftsizes.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftsizes.h index 7dc929521..7bfb1aed4 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftsizes.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftsizes.h @@ -4,7 +4,7 @@ * * FreeType size objects management (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -29,8 +29,7 @@ #define FTSIZES_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" diff --git a/src/font/freetype-2.10.2/include/freetype/ftsnames.h b/3rdparty/freetype-2.13.2/include/freetype/ftsnames.h similarity index 98% rename from src/font/freetype-2.10.2/include/freetype/ftsnames.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftsnames.h index 298276063..9d5d22bb2 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftsnames.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftsnames.h @@ -7,7 +7,7 @@ * * This is _not_ used to retrieve glyph names! * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -23,9 +23,8 @@ #define FTSNAMES_H_ -#include -#include FT_FREETYPE_H -#include FT_PARAMETER_TAGS_H +#include +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" diff --git a/src/font/freetype-2.10.2/include/freetype/ftstroke.h b/3rdparty/freetype-2.13.2/include/freetype/ftstroke.h similarity index 99% rename from src/font/freetype-2.10.2/include/freetype/ftstroke.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftstroke.h index 141af7d0b..b3d90802a 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftstroke.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftstroke.h @@ -4,7 +4,7 @@ * * FreeType path stroker (specification). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,9 +19,8 @@ #ifndef FTSTROKE_H_ #define FTSTROKE_H_ -#include -#include FT_OUTLINE_H -#include FT_GLYPH_H +#include +#include FT_BEGIN_HEADER @@ -44,7 +43,7 @@ FT_BEGIN_HEADER * borders of the stroke. * * This can be useful to generate 'bordered' glyph, i.e., glyphs - * displayed with a coloured (and anti-aliased) border around their + * displayed with a colored (and anti-aliased) border around their * shape. * * @order: @@ -294,7 +293,7 @@ FT_BEGIN_HEADER * * miter_limit :: * The maximum reciprocal sine of half-angle at the miter join, - * expressed as 16.16 fixed point value. + * expressed as 16.16 fixed-point value. * * @note: * The `radius` is expressed in the same units as the outline diff --git a/src/font/freetype-2.10.2/include/freetype/ftsynth.h b/3rdparty/freetype-2.13.2/include/freetype/ftsynth.h similarity index 72% rename from src/font/freetype-2.10.2/include/freetype/ftsynth.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftsynth.h index 3882e69e6..af90967dd 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftsynth.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftsynth.h @@ -5,7 +5,7 @@ * FreeType synthesizing code for emboldening and slanting * (specification). * - * Copyright (C) 2000-2020 by + * Copyright (C) 2000-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -45,8 +45,7 @@ #define FTSYNTH_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" @@ -69,10 +68,31 @@ FT_BEGIN_HEADER FT_EXPORT( void ) FT_GlyphSlot_Embolden( FT_GlyphSlot slot ); - /* Slant an outline glyph to the right by about 12 degrees. */ + /* Precisely adjust the glyph weight either horizontally or vertically. */ + /* The `xdelta` and `ydelta` values are fractions of the face Em size */ + /* (in fixed-point format). Considering that a regular face would have */ + /* stem widths on the order of 0.1 Em, a delta of 0.05 (0x0CCC) should */ + /* be very noticeable. To increase or decrease the weight, use positive */ + /* or negative values, respectively. */ + FT_EXPORT( void ) + FT_GlyphSlot_AdjustWeight( FT_GlyphSlot slot, + FT_Fixed xdelta, + FT_Fixed ydelta ); + + + /* Slant an outline glyph to the right by about 12 degrees. */ FT_EXPORT( void ) FT_GlyphSlot_Oblique( FT_GlyphSlot slot ); + /* Slant an outline glyph by a given sine of an angle. You can apply */ + /* slant along either x- or y-axis by choosing a corresponding non-zero */ + /* argument. If both slants are non-zero, some affine transformation */ + /* will result. */ + FT_EXPORT( void ) + FT_GlyphSlot_Slant( FT_GlyphSlot slot, + FT_Fixed xslant, + FT_Fixed yslant ); + /* */ diff --git a/src/font/freetype-2.10.2/include/freetype/ftsystem.h b/3rdparty/freetype-2.13.2/include/freetype/ftsystem.h similarity index 96% rename from src/font/freetype-2.10.2/include/freetype/ftsystem.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftsystem.h index f7fecb53f..3a08f4912 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftsystem.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftsystem.h @@ -4,7 +4,7 @@ * * FreeType low-level system interface definition (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,7 +20,6 @@ #define FTSYSTEM_H_ -#include FT_BEGIN_HEADER @@ -230,7 +229,7 @@ FT_BEGIN_HEADER * A handle to the source stream. * * offset :: - * The offset of read in stream (always from start). + * The offset from the start of the stream to seek to. * * buffer :: * The address of the read buffer. @@ -239,11 +238,9 @@ FT_BEGIN_HEADER * The number of bytes to read from the stream. * * @return: - * The number of bytes effectively read by the stream. - * - * @note: - * This function might be called to perform a seek or skip operation with - * a `count` of~0. A non-zero return value then indicates an error. + * If count >~0, return the number of bytes effectively read by the + * stream (after seeking to `offset`). If count ==~0, return the status + * of the seek operation (non-zero indicates an error). * */ typedef unsigned long diff --git a/src/font/freetype-2.10.2/include/freetype/fttrigon.h b/3rdparty/freetype-2.13.2/include/freetype/fttrigon.h similarity index 99% rename from src/font/freetype-2.10.2/include/freetype/fttrigon.h rename to 3rdparty/freetype-2.13.2/include/freetype/fttrigon.h index 968df1fbf..294981a6f 100644 --- a/src/font/freetype-2.10.2/include/freetype/fttrigon.h +++ b/3rdparty/freetype-2.13.2/include/freetype/fttrigon.h @@ -4,7 +4,7 @@ * * FreeType trigonometric functions (specification). * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,7 +19,7 @@ #ifndef FTTRIGON_H_ #define FTTRIGON_H_ -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" diff --git a/src/font/freetype-2.10.2/include/freetype/fttypes.h b/3rdparty/freetype-2.13.2/include/freetype/fttypes.h similarity index 94% rename from src/font/freetype-2.10.2/include/freetype/fttypes.h rename to 3rdparty/freetype-2.13.2/include/freetype/fttypes.h index cb785d98b..5b109f0c7 100644 --- a/src/font/freetype-2.10.2/include/freetype/fttypes.h +++ b/3rdparty/freetype-2.13.2/include/freetype/fttypes.h @@ -4,7 +4,7 @@ * * FreeType simple types definitions (specification only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -22,8 +22,8 @@ #include #include FT_CONFIG_CONFIG_H -#include FT_SYSTEM_H -#include FT_IMAGE_H +#include +#include #include @@ -45,7 +45,10 @@ FT_BEGIN_HEADER * @description: * This section contains the basic data types defined by FreeType~2, * ranging from simple scalar types to bitmap descriptors. More - * font-specific structures are defined in a different section. + * font-specific structures are defined in a different section. Note + * that FreeType does not use floating-point data types. Fractional + * values are represented by fixed-point integers, with lower bits + * storing the fractional part. * * @order: * FT_Byte @@ -413,7 +416,7 @@ FT_BEGIN_HEADER typedef struct FT_Data_ { const FT_Byte* pointer; - FT_Int length; + FT_UInt length; } FT_Data; @@ -479,18 +482,17 @@ FT_BEGIN_HEADER * * @description: * This macro converts four-letter tags that are used to label TrueType - * tables into an unsigned long, to be used within FreeType. + * tables into an `FT_Tag` type, to be used within FreeType. * * @note: * The produced values **must** be 32-bit integers. Don't redefine this * macro. */ -#define FT_MAKE_TAG( _x1, _x2, _x3, _x4 ) \ - (FT_Tag) \ - ( ( (FT_ULong)_x1 << 24 ) | \ - ( (FT_ULong)_x2 << 16 ) | \ - ( (FT_ULong)_x3 << 8 ) | \ - (FT_ULong)_x4 ) +#define FT_MAKE_TAG( _x1, _x2, _x3, _x4 ) \ + ( ( FT_STATIC_BYTE_CAST( FT_Tag, _x1 ) << 24 ) | \ + ( FT_STATIC_BYTE_CAST( FT_Tag, _x2 ) << 16 ) | \ + ( FT_STATIC_BYTE_CAST( FT_Tag, _x3 ) << 8 ) | \ + FT_STATIC_BYTE_CAST( FT_Tag, _x4 ) ) /*************************************************************************/ @@ -588,7 +590,7 @@ FT_BEGIN_HEADER #define FT_IS_EMPTY( list ) ( (list).head == 0 ) -#define FT_BOOL( x ) ( (FT_Bool)( (x) != 0 ) ) +#define FT_BOOL( x ) FT_STATIC_CAST( FT_Bool, (x) != 0 ) /* concatenate C tokens */ #define FT_ERR_XCAT( x, y ) x ## y diff --git a/src/font/freetype-2.10.2/include/freetype/ftwinfnt.h b/3rdparty/freetype-2.13.2/include/freetype/ftwinfnt.h similarity index 98% rename from src/font/freetype-2.10.2/include/freetype/ftwinfnt.h rename to 3rdparty/freetype-2.13.2/include/freetype/ftwinfnt.h index bacb8aa37..7b701ea59 100644 --- a/src/font/freetype-2.10.2/include/freetype/ftwinfnt.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ftwinfnt.h @@ -4,7 +4,7 @@ * * FreeType API for accessing Windows fnt-specific data. * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,7 @@ #ifndef FTWINFNT_H_ #define FTWINFNT_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" @@ -56,7 +55,7 @@ FT_BEGIN_HEADER * FT_WinFNT_ID_XXX * * @description: - * A list of valid values for the `charset` byte in @FT_WinFNT_HeaderRec. + * A list of valid values for the `charset` byte in @FT_WinFNT_HeaderRec. * Exact mapping tables for the various 'cpXXXX' encodings (except for * 'cp1361') can be found at 'ftp://ftp.unicode.org/Public/' in the * `MAPPINGS/VENDORS/MICSFT/WINDOWS` subdirectory. 'cp1361' is roughly a diff --git a/src/font/freetype-2.10.2/include/freetype/internal/autohint.h b/3rdparty/freetype-2.13.2/include/freetype/internal/autohint.h similarity index 97% rename from src/font/freetype-2.10.2/include/freetype/internal/autohint.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/autohint.h index 438f9c175..bf9c8b7cf 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/autohint.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/autohint.h @@ -4,7 +4,7 @@ * * High-level 'autohint' module-specific interface (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -70,8 +70,7 @@ */ -#include -#include FT_FREETYPE_H +#include FT_BEGIN_HEADER @@ -208,6 +207,9 @@ FT_BEGIN_HEADER } FT_AutoHinter_InterfaceRec, *FT_AutoHinter_Interface; +#define FT_DECLARE_AUTOHINTER_INTERFACE( class_ ) \ + FT_CALLBACK_TABLE const FT_AutoHinter_InterfaceRec class_; + #define FT_DEFINE_AUTOHINTER_INTERFACE( \ class_, \ reset_face_, \ diff --git a/src/font/freetype-2.10.2/include/freetype/internal/cffotypes.h b/3rdparty/freetype-2.13.2/include/freetype/internal/cffotypes.h similarity index 90% rename from src/font/freetype-2.10.2/include/freetype/internal/cffotypes.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/cffotypes.h index 207eeda5f..50d535384 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/cffotypes.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/cffotypes.h @@ -4,7 +4,7 @@ * * Basic OpenType/CFF object type definitions (specification). * - * Copyright (C) 2017-2020 by + * Copyright (C) 2017-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,12 +19,11 @@ #ifndef CFFOTYPES_H_ #define CFFOTYPES_H_ -#include -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_CFF_TYPES_H -#include FT_INTERNAL_TRUETYPE_TYPES_H -#include FT_SERVICE_POSTSCRIPT_CMAPS_H -#include FT_INTERNAL_POSTSCRIPT_HINTS_H +#include +#include +#include +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/cfftypes.h b/3rdparty/freetype-2.13.2/include/freetype/internal/cfftypes.h similarity index 97% rename from src/font/freetype-2.10.2/include/freetype/internal/cfftypes.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/cfftypes.h index 40b0fc73c..c2521764c 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/cfftypes.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/cfftypes.h @@ -5,7 +5,7 @@ * Basic OpenType/CFF type definitions and interface (specification * only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -21,13 +21,12 @@ #define CFFTYPES_H_ -#include -#include FT_FREETYPE_H -#include FT_TYPE1_TABLES_H -#include FT_INTERNAL_SERVICE_H -#include FT_SERVICE_POSTSCRIPT_CMAPS_H -#include FT_INTERNAL_POSTSCRIPT_HINTS_H -#include FT_INTERNAL_TYPE1_TYPES_H +#include +#include +#include +#include +#include +#include FT_BEGIN_HEADER @@ -316,7 +315,7 @@ FT_BEGIN_HEADER /* The normal stack then points to these values instead of the DICT */ /* because all other operators in Private DICT clear the stack. */ /* `blend_stack' could be cleared at each operator other than blend. */ - /* Blended values are stored as 5-byte fixed point values. */ + /* Blended values are stored as 5-byte fixed-point values. */ FT_Byte* blend_stack; /* base of stack allocation */ FT_Byte* blend_top; /* first empty slot */ diff --git a/3rdparty/freetype-2.13.2/include/freetype/internal/compiler-macros.h b/3rdparty/freetype-2.13.2/include/freetype/internal/compiler-macros.h new file mode 100644 index 000000000..6f6765097 --- /dev/null +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/compiler-macros.h @@ -0,0 +1,343 @@ +/**************************************************************************** + * + * internal/compiler-macros.h + * + * Compiler-specific macro definitions used internally by FreeType. + * + * Copyright (C) 2020-2023 by + * David Turner, Robert Wilhelm, and Werner Lemberg. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + +#ifndef INTERNAL_COMPILER_MACROS_H_ +#define INTERNAL_COMPILER_MACROS_H_ + +#include + +FT_BEGIN_HEADER + + /* Fix compiler warning with sgi compiler. */ +#if defined( __sgi ) && !defined( __GNUC__ ) +# if defined( _COMPILER_VERSION ) && ( _COMPILER_VERSION >= 730 ) +# pragma set woff 3505 +# endif +#endif + + /* Fix compiler warning with sgi compiler. */ +#if defined( __sgi ) && !defined( __GNUC__ ) +# if defined( _COMPILER_VERSION ) && ( _COMPILER_VERSION >= 730 ) +# pragma set woff 3505 +# endif +#endif + + /* Newer compilers warn for fall-through case statements. */ +#ifndef FALL_THROUGH +# if ( defined( __STDC_VERSION__ ) && __STDC_VERSION__ > 201710L ) || \ + ( defined( __cplusplus ) && __cplusplus > 201402L ) +# define FALL_THROUGH [[__fallthrough__]] +# elif ( defined( __GNUC__ ) && __GNUC__ >= 7 ) || \ + ( defined( __clang__ ) && \ + ( defined( __apple_build_version__ ) \ + ? __apple_build_version__ >= 12000000 \ + : __clang_major__ >= 10 ) ) +# define FALL_THROUGH __attribute__(( __fallthrough__ )) +# else +# define FALL_THROUGH ( (void)0 ) +# endif +#endif + + /* + * When defining a macro that expands to a non-trivial C statement, use + * FT_BEGIN_STMNT and FT_END_STMNT to enclose the macro's body. This + * ensures there are no surprises when the macro is invoked in conditional + * branches. + * + * Example: + * + * #define LOG( ... ) \ + * FT_BEGIN_STMNT \ + * if ( logging_enabled ) \ + * log( __VA_ARGS__ ); \ + * FT_END_STMNT + */ +#define FT_BEGIN_STMNT do { +#define FT_END_STMNT } while ( 0 ) + + /* + * FT_DUMMY_STMNT expands to an empty C statement. Useful for + * conditionally defined statement macros. + * + * Example: + * + * #ifdef BUILD_CONFIG_LOGGING + * #define LOG( ... ) \ + * FT_BEGIN_STMNT \ + * if ( logging_enabled ) \ + * log( __VA_ARGS__ ); \ + * FT_END_STMNT + * #else + * # define LOG( ... ) FT_DUMMY_STMNT + * #endif + */ +#define FT_DUMMY_STMNT FT_BEGIN_STMNT FT_END_STMNT + +#ifdef __UINTPTR_TYPE__ + /* + * GCC and Clang both provide a `__UINTPTR_TYPE__` that can be used to + * avoid a dependency on `stdint.h`. + */ +# define FT_UINT_TO_POINTER( x ) (void *)(__UINTPTR_TYPE__)(x) +#elif defined( _WIN64 ) + /* only 64bit Windows uses the LLP64 data model, i.e., */ + /* 32-bit integers, 64-bit pointers. */ +# define FT_UINT_TO_POINTER( x ) (void *)(unsigned __int64)(x) +#else +# define FT_UINT_TO_POINTER( x ) (void *)(unsigned long)(x) +#endif + + /* + * Use `FT_TYPEOF( type )` to cast a value to `type`. This is useful to + * suppress signedness compilation warnings in macros. + * + * Example: + * + * #define PAD_( x, n ) ( (x) & ~FT_TYPEOF( x )( (n) - 1 ) ) + * + * (The `typeof` condition is taken from gnulib's `intprops.h` header + * file.) + */ +#if ( ( defined( __GNUC__ ) && __GNUC__ >= 2 ) || \ + ( defined( __IBMC__ ) && __IBMC__ >= 1210 && \ + defined( __IBM__TYPEOF__ ) ) || \ + ( defined( __SUNPRO_C ) && __SUNPRO_C >= 0x5110 && !__STDC__ ) ) +#define FT_TYPEOF( type ) ( __typeof__ ( type ) ) +#else +#define FT_TYPEOF( type ) /* empty */ +#endif + + /* + * Mark a function declaration as internal to the library. This ensures + * that it will not be exposed by default to client code, and helps + * generate smaller and faster code on ELF-based platforms. Place this + * before a function declaration. + */ + + /* Visual C, mingw */ +#if defined( _WIN32 ) +#define FT_INTERNAL_FUNCTION_ATTRIBUTE /* empty */ + + /* gcc, clang */ +#elif ( defined( __GNUC__ ) && __GNUC__ >= 4 ) || defined( __clang__ ) +#define FT_INTERNAL_FUNCTION_ATTRIBUTE \ + __attribute__(( visibility( "hidden" ) )) + + /* Sun */ +#elif defined( __SUNPRO_C ) && __SUNPRO_C >= 0x550 +#define FT_INTERNAL_FUNCTION_ATTRIBUTE __hidden + +#else +#define FT_INTERNAL_FUNCTION_ATTRIBUTE /* empty */ +#endif + + /* + * FreeType supports compilation of its C sources with a C++ compiler (in + * C++ mode); this introduces a number of subtle issues. + * + * The main one is that a C++ function declaration and its definition must + * have the same 'linkage'. Because all FreeType headers declare their + * functions with C linkage (i.e., within an `extern "C" { ... }` block + * due to the magic of FT_BEGIN_HEADER and FT_END_HEADER), their + * definition in FreeType sources should also be prefixed with `extern + * "C"` when compiled in C++ mode. + * + * The `FT_FUNCTION_DECLARATION` and `FT_FUNCTION_DEFINITION` macros are + * provided to deal with this case, as well as `FT_CALLBACK_DEF` and its + * siblings below. + */ + + /* + * `FT_FUNCTION_DECLARATION( type )` can be used to write a C function + * declaration to ensure it will have C linkage when the library is built + * with a C++ compiler. The parameter is the function's return type, so a + * declaration would look like + * + * FT_FUNCTION_DECLARATION( int ) + * foo( int x ); + * + * NOTE: This requires that all uses are inside of `FT_BEGIN_HEADER ... + * FT_END_HEADER` blocks, which guarantees that the declarations have C + * linkage when the headers are included by C++ sources. + * + * NOTE: Do not use directly. Use `FT_LOCAL`, `FT_BASE`, and `FT_EXPORT` + * instead. + */ +#define FT_FUNCTION_DECLARATION( x ) extern x + + /* + * Same as `FT_FUNCTION_DECLARATION`, but for function definitions instead. + * + * NOTE: Do not use directly. Use `FT_LOCAL_DEF`, `FT_BASE_DEF`, and + * `FT_EXPORT_DEF` instead. + */ +#ifdef __cplusplus +#define FT_FUNCTION_DEFINITION( x ) extern "C" x +#else +#define FT_FUNCTION_DEFINITION( x ) x +#endif + + /* + * Use `FT_LOCAL` and `FT_LOCAL_DEF` to declare and define, respectively, + * an internal FreeType function that is only used by the sources of a + * single `src/module/` directory. This ensures that the functions are + * turned into static ones at build time, resulting in smaller and faster + * code. + */ +#ifdef FT_MAKE_OPTION_SINGLE_OBJECT + +#define FT_LOCAL( x ) static x +#define FT_LOCAL_DEF( x ) static x + +#else + +#define FT_LOCAL( x ) FT_INTERNAL_FUNCTION_ATTRIBUTE \ + FT_FUNCTION_DECLARATION( x ) +#define FT_LOCAL_DEF( x ) FT_FUNCTION_DEFINITION( x ) + +#endif /* FT_MAKE_OPTION_SINGLE_OBJECT */ + + /* + * Use `FT_LOCAL_ARRAY` and `FT_LOCAL_ARRAY_DEF` to declare and define, + * respectively, a constant array that must be accessed from several + * sources in the same `src/module/` sub-directory, and which are internal + * to the library. + */ +#define FT_LOCAL_ARRAY( x ) FT_INTERNAL_FUNCTION_ATTRIBUTE \ + extern const x +#define FT_LOCAL_ARRAY_DEF( x ) FT_FUNCTION_DEFINITION( const x ) + + /* + * `Use FT_BASE` and `FT_BASE_DEF` to declare and define, respectively, an + * internal library function that is used by more than a single module. + */ +#define FT_BASE( x ) FT_INTERNAL_FUNCTION_ATTRIBUTE \ + FT_FUNCTION_DECLARATION( x ) +#define FT_BASE_DEF( x ) FT_FUNCTION_DEFINITION( x ) + + + /* + * NOTE: Conditionally define `FT_EXPORT_VAR` due to its definition in + * `src/smooth/ftgrays.h` to make the header more portable. + */ +#ifndef FT_EXPORT_VAR +#define FT_EXPORT_VAR( x ) FT_FUNCTION_DECLARATION( x ) +#endif + + /* + * When compiling FreeType as a DLL or DSO with hidden visibility, + * some systems/compilers need a special attribute in front OR after + * the return type of function declarations. + * + * Two macros are used within the FreeType source code to define + * exported library functions: `FT_EXPORT` and `FT_EXPORT_DEF`. + * + * - `FT_EXPORT( return_type )` + * + * is used in a function declaration, as in + * + * ``` + * FT_EXPORT( FT_Error ) + * FT_Init_FreeType( FT_Library* alibrary ); + * ``` + * + * - `FT_EXPORT_DEF( return_type )` + * + * is used in a function definition, as in + * + * ``` + * FT_EXPORT_DEF( FT_Error ) + * FT_Init_FreeType( FT_Library* alibrary ) + * { + * ... some code ... + * return FT_Err_Ok; + * } + * ``` + * + * You can provide your own implementation of `FT_EXPORT` and + * `FT_EXPORT_DEF` here if you want. + * + * To export a variable, use `FT_EXPORT_VAR`. + */ + + /* See `freetype/config/public-macros.h` for the `FT_EXPORT` definition */ +#define FT_EXPORT_DEF( x ) FT_FUNCTION_DEFINITION( x ) + + /* + * The following macros are needed to compile the library with a + * C++ compiler and with 16bit compilers. + */ + + /* + * This is special. Within C++, you must specify `extern "C"` for + * functions which are used via function pointers, and you also + * must do that for structures which contain function pointers to + * assure C linkage -- it's not possible to have (local) anonymous + * functions which are accessed by (global) function pointers. + * + * + * FT_CALLBACK_DEF is used to _define_ a callback function, + * located in the same source code file as the structure that uses + * it. FT_COMPARE_DEF, in addition, ensures the `cdecl` calling + * convention on x86, required by the C library function `qsort`. + * + * FT_BASE_CALLBACK and FT_BASE_CALLBACK_DEF are used to declare + * and define a callback function, respectively, in a similar way + * as FT_BASE and FT_BASE_DEF work. + * + * FT_CALLBACK_TABLE is used to _declare_ a constant variable that + * contains pointers to callback functions. + * + * FT_CALLBACK_TABLE_DEF is used to _define_ a constant variable + * that contains pointers to callback functions. + * + * + * Some 16bit compilers have to redefine these macros to insert + * the infamous `_cdecl` or `__fastcall` declarations. + */ +#ifdef __cplusplus +#define FT_CALLBACK_DEF( x ) extern "C" x +#else +#define FT_CALLBACK_DEF( x ) static x +#endif + +#if defined( __GNUC__ ) && defined( __i386__ ) +#define FT_COMPARE_DEF( x ) FT_CALLBACK_DEF( x ) __attribute__(( cdecl )) +#elif defined( _MSC_VER ) && defined( _M_IX86 ) +#define FT_COMPARE_DEF( x ) FT_CALLBACK_DEF( x ) __cdecl +#elif defined( __WATCOMC__ ) && __WATCOMC__ >= 1240 +#define FT_COMPARE_DEF( x ) FT_CALLBACK_DEF( x ) __watcall +#else +#define FT_COMPARE_DEF( x ) FT_CALLBACK_DEF( x ) +#endif + +#define FT_BASE_CALLBACK( x ) FT_FUNCTION_DECLARATION( x ) +#define FT_BASE_CALLBACK_DEF( x ) FT_FUNCTION_DEFINITION( x ) + +#ifndef FT_CALLBACK_TABLE +#ifdef __cplusplus +#define FT_CALLBACK_TABLE extern "C" +#define FT_CALLBACK_TABLE_DEF extern "C" +#else +#define FT_CALLBACK_TABLE extern +#define FT_CALLBACK_TABLE_DEF /* nothing */ +#endif +#endif /* FT_CALLBACK_TABLE */ + +FT_END_HEADER + +#endif /* INTERNAL_COMPILER_MACROS_H_ */ diff --git a/src/font/freetype-2.10.2/include/freetype/internal/ftcalc.h b/3rdparty/freetype-2.13.2/include/freetype/internal/ftcalc.h similarity index 84% rename from src/font/freetype-2.10.2/include/freetype/internal/ftcalc.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/ftcalc.h index 3054a4c49..d9aea2360 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/ftcalc.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/ftcalc.h @@ -4,7 +4,7 @@ * * Arithmetic computations (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,9 +20,9 @@ #define FTCALC_H_ -#include -#include FT_FREETYPE_H +#include +#include "compiler-macros.h" FT_BEGIN_HEADER @@ -278,6 +278,40 @@ FT_BEGIN_HEADER FT_Long c ); + /************************************************************************** + * + * @function: + * FT_MulAddFix + * + * @description: + * Compute `(s[0] * f[0] + s[1] * f[1] + ...) / 0x10000`, where `s[n]` is + * usually a 16.16 scalar. + * + * @input: + * s :: + * The array of scalars. + * f :: + * The array of factors. + * count :: + * The number of entries in the array. + * + * @return: + * The result of `(s[0] * f[0] + s[1] * f[1] + ...) / 0x10000`. + * + * @note: + * This function is currently used for the scaled delta computation of + * variation stores. It internally uses 64-bit data types when + * available, otherwise it emulates 64-bit math by using 32-bit + * operations, which produce a correct result but most likely at a slower + * performance in comparison to the implementation base on `int64_t`. + * + */ + FT_BASE( FT_Int32 ) + FT_MulAddFix( FT_Fixed* s, + FT_Int32* f, + FT_UInt count ); + + /* * A variant of FT_Matrix_Multiply which scales its result afterwards. The * idea is that both `a' and `b' are scaled by factors of 10 so that the @@ -298,9 +332,9 @@ FT_BEGIN_HEADER * Based on geometric considerations we use the following inequality to * identify a degenerate matrix. * - * 50 * abs(xx*yy - xy*yx) < xx^2 + xy^2 + yx^2 + yy^2 + * 32 * abs(xx*yy - xy*yx) < xx^2 + xy^2 + yx^2 + yy^2 * - * Value 50 is heuristic. + * Value 32 is heuristic. */ FT_BASE( FT_Bool ) FT_Matrix_Check( const FT_Matrix* matrix ); @@ -359,8 +393,8 @@ FT_BEGIN_HEADER #ifndef FT_CONFIG_OPTION_NO_ASSEMBLER -#if defined( __GNUC__ ) && \ - ( __GNUC__ > 3 || ( __GNUC__ == 3 && __GNUC_MINOR__ >= 4 ) ) +#if defined( __clang__ ) || ( defined( __GNUC__ ) && \ + ( __GNUC__ > 3 || ( __GNUC__ == 3 && __GNUC_MINOR__ >= 4 ) ) ) #if FT_SIZEOF_INT == 4 @@ -370,12 +404,25 @@ FT_BEGIN_HEADER #define FT_MSB( x ) ( 31 - __builtin_clzl( x ) ) -#endif /* __GNUC__ */ +#endif +#elif defined( _MSC_VER ) && _MSC_VER >= 1400 -#elif defined( _MSC_VER ) && ( _MSC_VER >= 1400 ) +#if defined( _WIN32_WCE ) -#if FT_SIZEOF_INT == 4 +#include +#pragma intrinsic( _CountLeadingZeros ) + +#define FT_MSB( x ) ( 31 - _CountLeadingZeros( x ) ) + +#elif defined( _M_ARM64 ) || defined( _M_ARM ) + +#include +#pragma intrinsic( _CountLeadingZeros ) + +#define FT_MSB( x ) ( 31 - _CountLeadingZeros( x ) ) + +#elif defined( _M_IX86 ) || defined( _M_AMD64 ) || defined( _M_IA64 ) #include #pragma intrinsic( _BitScanReverse ) @@ -391,15 +438,40 @@ FT_BEGIN_HEADER return (FT_Int32)where; } -#define FT_MSB( x ) ( FT_MSB_i386( x ) ) +#define FT_MSB( x ) FT_MSB_i386( x ) #endif -#endif /* _MSC_VER */ +#elif defined( __WATCOMC__ ) && defined( __386__ ) + + extern __inline FT_Int32 + FT_MSB_i386( FT_UInt32 x ); +#pragma aux FT_MSB_i386 = \ + "bsr eax, eax" \ + __parm [__eax] __nomemory \ + __value [__eax] \ + __modify __exact [__eax] __nomemory; + +#define FT_MSB( x ) FT_MSB_i386( x ) + +#elif defined( __DECC ) || defined( __DECCXX ) + +#include + +#define FT_MSB( x ) (FT_Int)( 63 - _leadz( x ) ) + +#elif defined( _CRAYC ) + +#include + +#define FT_MSB( x ) (FT_Int)( 31 - _leadz32( x ) ) + +#endif /* FT_MSB macro definitions */ #endif /* !FT_CONFIG_OPTION_NO_ASSEMBLER */ + #ifndef FT_MSB FT_BASE( FT_Int ) @@ -449,8 +521,7 @@ FT_BEGIN_HEADER #define F2DOT14_TO_FIXED( x ) ( (FT_Long)(x) * 4 ) /* << 2 */ #define FIXED_TO_INT( x ) ( FT_RoundFix( x ) >> 16 ) -#define ROUND_F26DOT6( x ) ( x >= 0 ? ( ( (x) + 32 ) & -64 ) \ - : ( -( ( 32 - (x) ) & -64 ) ) ) +#define ROUND_F26DOT6( x ) ( ( (x) + 32 - ( x < 0 ) ) & -64 ) /* * The following macros have two purposes. @@ -488,7 +559,7 @@ FT_BEGIN_HEADER #define NEG_INT32( a ) \ (FT_Int32)( (FT_UInt32)0 - (FT_UInt32)(a) ) -#ifdef FT_LONG64 +#ifdef FT_INT64 #define ADD_INT64( a, b ) \ (FT_Int64)( (FT_UInt64)(a) + (FT_UInt64)(b) ) @@ -499,7 +570,7 @@ FT_BEGIN_HEADER #define NEG_INT64( a ) \ (FT_Int64)( (FT_UInt64)0 - (FT_UInt64)(a) ) -#endif /* FT_LONG64 */ +#endif /* FT_INT64 */ FT_END_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/ftdebug.h b/3rdparty/freetype-2.13.2/include/freetype/internal/ftdebug.h similarity index 55% rename from src/font/freetype-2.10.2/include/freetype/internal/ftdebug.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/ftdebug.h index 00d258e64..4e013ba1e 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/ftdebug.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/ftdebug.h @@ -4,7 +4,7 @@ * * Debugging and logging component (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -27,11 +27,28 @@ #include #include FT_CONFIG_CONFIG_H -#include FT_FREETYPE_H +#include + +#include "compiler-macros.h" + +#ifdef FT_DEBUG_LOGGING +#define DLG_STATIC +#include +#include + +#include +#endif /* FT_DEBUG_LOGGING */ FT_BEGIN_HEADER + /* force the definition of FT_DEBUG_LEVEL_TRACE if FT_DEBUG_LOGGING is */ + /* already defined. */ + /* */ +#ifdef FT_DEBUG_LOGGING +#undef FT_DEBUG_LEVEL_TRACE +#define FT_DEBUG_LEVEL_TRACE +#endif /* force the definition of FT_DEBUG_LEVEL_ERROR if FT_DEBUG_LEVEL_TRACE */ /* is already defined; this simplifies the following #ifdefs */ @@ -56,7 +73,7 @@ FT_BEGIN_HEADER /* defining the enumeration */ typedef enum FT_Trace_ { -#include FT_INTERNAL_TRACE_H +#include trace_count } FT_Trace; @@ -80,21 +97,67 @@ FT_BEGIN_HEADER * Each component must define the macro FT_COMPONENT to a valid FT_Trace * value before using any TRACE macro. * + * To get consistent logging output, there should be no newline character + * (i.e., '\n') or a single trailing one in the message string of + * `FT_TRACEx` and `FT_ERROR`. */ -#ifdef FT_DEBUG_LEVEL_TRACE - /* we need two macros here to make cpp expand `FT_COMPONENT' */ -#define FT_TRACE_COMP( x ) FT_TRACE_COMP_( x ) -#define FT_TRACE_COMP_( x ) trace_ ## x + /************************************************************************* + * + * If FT_DEBUG_LOGGING is enabled, tracing messages are sent to dlg's API. + * If FT_DEBUG_LOGGING is disabled, tracing messages are sent to + * `FT_Message` (defined in ftdebug.c). + */ +#ifdef FT_DEBUG_LOGGING -#define FT_TRACE( level, varformat ) \ + /* we need two macros to convert the names of `FT_COMPONENT` to a string */ +#define FT_LOGGING_TAG( x ) FT_LOGGING_TAG_( x ) +#define FT_LOGGING_TAG_( x ) #x + + /* we need two macros to convert the component and the trace level */ + /* to a string that combines them */ +#define FT_LOGGING_TAGX( x, y ) FT_LOGGING_TAGX_( x, y ) +#define FT_LOGGING_TAGX_( x, y ) #x ":" #y + + +#define FT_LOG( level, varformat ) \ + do \ + { \ + const char* dlg_tag = FT_LOGGING_TAGX( FT_COMPONENT, level ); \ + \ + \ + ft_add_tag( dlg_tag ); \ + if ( ft_trace_levels[FT_TRACE_COMP( FT_COMPONENT )] >= level ) \ + { \ + if ( custom_output_handler != NULL ) \ + FT_Logging_Callback varformat; \ + else \ + dlg_trace varformat; \ + } \ + ft_remove_tag( dlg_tag ); \ + } while( 0 ) + +#else /* !FT_DEBUG_LOGGING */ + +#define FT_LOG( level, varformat ) \ do \ { \ if ( ft_trace_levels[FT_TRACE_COMP( FT_COMPONENT )] >= level ) \ FT_Message varformat; \ } while ( 0 ) +#endif /* !FT_DEBUG_LOGGING */ + + +#ifdef FT_DEBUG_LEVEL_TRACE + + /* we need two macros here to make cpp expand `FT_COMPONENT' */ +#define FT_TRACE_COMP( x ) FT_TRACE_COMP_( x ) +#define FT_TRACE_COMP_( x ) trace_ ## x + +#define FT_TRACE( level, varformat ) FT_LOG( level, varformat ) + #else /* !FT_DEBUG_LEVEL_TRACE */ #define FT_TRACE( level, varformat ) do { } while ( 0 ) /* nothing */ @@ -202,7 +265,32 @@ FT_BEGIN_HEADER #ifdef FT_DEBUG_LEVEL_ERROR -#define FT_ERROR( varformat ) FT_Message varformat + /************************************************************************** + * + * If FT_DEBUG_LOGGING is enabled, error messages are sent to dlg's API. + * If FT_DEBUG_LOGGING is disabled, error messages are sent to `FT_Message` + * (defined in ftdebug.c). + * + */ +#ifdef FT_DEBUG_LOGGING + +#define FT_ERROR( varformat ) \ + do \ + { \ + const char* dlg_tag = FT_LOGGING_TAG( FT_COMPONENT ); \ + \ + \ + ft_add_tag( dlg_tag ); \ + dlg_trace varformat; \ + ft_remove_tag( dlg_tag ); \ + } while ( 0 ) + +#else /* !FT_DEBUG_LOGGING */ + +#define FT_ERROR( varformat ) FT_Message varformat + +#endif /* !FT_DEBUG_LOGGING */ + #else /* !FT_DEBUG_LEVEL_ERROR */ @@ -275,6 +363,77 @@ FT_BEGIN_HEADER FT_BASE( void ) ft_debug_init( void ); + +#ifdef FT_DEBUG_LOGGING + + /************************************************************************** + * + * 'dlg' uses output handlers to control how and where log messages are + * printed. Therefore we need to define a default output handler for + * FreeType. + */ + FT_BASE( void ) + ft_log_handler( const struct dlg_origin* origin, + const char* string, + void* data ); + + + /************************************************************************** + * + * 1. `ft_default_log_handler` stores the function pointer that is used + * internally by FreeType to print logs to a file. + * + * 2. `custom_output_handler` stores the function pointer to the callback + * function provided by the user. + * + * It is defined in `ftdebug.c`. + */ + extern dlg_handler ft_default_log_handler; + extern FT_Custom_Log_Handler custom_output_handler; + + + /************************************************************************** + * + * If FT_DEBUG_LOGGING macro is enabled, FreeType needs to initialize and + * un-initialize `FILE*`. + * + * These functions are defined in `ftdebug.c`. + */ + FT_BASE( void ) + ft_logging_init( void ); + + FT_BASE( void ) + ft_logging_deinit( void ); + + + /************************************************************************** + * + * For printing the name of `FT_COMPONENT` along with the actual log we + * need to add a tag with the name of `FT_COMPONENT`. + * + * These functions are defined in `ftdebug.c`. + */ + FT_BASE( void ) + ft_add_tag( const char* tag ); + + FT_BASE( void ) + ft_remove_tag( const char* tag ); + + + /************************************************************************** + * + * A function to print log data using a custom callback logging function + * (which is set using `FT_Set_Log_Handler`). + * + * This function is defined in `ftdebug.c`. + */ + FT_BASE( void ) + FT_Logging_Callback( const char* fmt, + ... ); + +#endif /* FT_DEBUG_LOGGING */ + + FT_END_HEADER #endif /* FTDEBUG_H_ */ diff --git a/src/font/freetype-2.10.2/include/freetype/internal/ftdrv.h b/3rdparty/freetype-2.13.2/include/freetype/internal/ftdrv.h similarity index 98% rename from src/font/freetype-2.10.2/include/freetype/internal/ftdrv.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/ftdrv.h index 1dd9206c8..9001c07ad 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/ftdrv.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/ftdrv.h @@ -4,7 +4,7 @@ * * FreeType internal font driver interface (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,9 +20,9 @@ #define FTDRV_H_ -#include -#include FT_MODULE_H +#include +#include "compiler-macros.h" FT_BEGIN_HEADER @@ -157,6 +157,7 @@ FT_BEGIN_HEADER * A handle to a function used to select a new fixed size. It is used * only if @FT_FACE_FLAG_FIXED_SIZES is set. Can be set to 0 if the * scaling done in the base layer suffices. + * * @note: * Most function pointers, with the exception of `load_glyph`, can be set * to 0 to indicate a default behaviour. diff --git a/src/font/freetype-2.10.2/include/freetype/internal/ftgloadr.h b/3rdparty/freetype-2.13.2/include/freetype/internal/ftgloadr.h similarity index 98% rename from src/font/freetype-2.10.2/include/freetype/internal/ftgloadr.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/ftgloadr.h index 6f3793b1c..36e5509f9 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/ftgloadr.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/ftgloadr.h @@ -4,7 +4,7 @@ * * The FreeType glyph loader (specification). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg * * This file is part of the FreeType project, and may only be used, @@ -20,9 +20,9 @@ #define FTGLOADR_H_ -#include -#include FT_FREETYPE_H +#include +#include "compiler-macros.h" FT_BEGIN_HEADER @@ -138,8 +138,6 @@ FT_BEGIN_HEADER FT_BASE( void ) FT_GlyphLoader_Add( FT_GlyphLoader loader ); - /* */ - FT_END_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/fthash.h b/3rdparty/freetype-2.13.2/include/freetype/internal/fthash.h similarity index 98% rename from src/font/freetype-2.10.2/include/freetype/internal/fthash.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/fthash.h index 249188040..622ec76bb 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/fthash.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/fthash.h @@ -43,8 +43,7 @@ #define FTHASH_H_ -#include -#include FT_FREETYPE_H +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/ftmemory.h b/3rdparty/freetype-2.13.2/include/freetype/internal/ftmemory.h similarity index 95% rename from src/font/freetype-2.10.2/include/freetype/internal/ftmemory.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/ftmemory.h index e0758c127..5eb1d21ff 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/ftmemory.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/ftmemory.h @@ -4,7 +4,7 @@ * * The FreeType memory management macros (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg * * This file is part of the FreeType project, and may only be used, @@ -22,8 +22,9 @@ #include #include FT_CONFIG_CONFIG_H -#include FT_TYPES_H +#include +#include "compiler-macros.h" FT_BEGIN_HEADER @@ -95,15 +96,15 @@ extern "C++" #ifdef FT_DEBUG_MEMORY - FT_BASE( const char* ) _ft_debug_file; - FT_BASE( long ) _ft_debug_lineno; + FT_BASE( const char* ) ft_debug_file_; + FT_BASE( long ) ft_debug_lineno_; -#define FT_DEBUG_INNER( exp ) ( _ft_debug_file = __FILE__, \ - _ft_debug_lineno = __LINE__, \ +#define FT_DEBUG_INNER( exp ) ( ft_debug_file_ = __FILE__, \ + ft_debug_lineno_ = __LINE__, \ (exp) ) -#define FT_ASSIGNP_INNER( p, exp ) ( _ft_debug_file = __FILE__, \ - _ft_debug_lineno = __LINE__, \ +#define FT_ASSIGNP_INNER( p, exp ) ( ft_debug_file_ = __FILE__, \ + ft_debug_lineno_ = __LINE__, \ FT_ASSIGNP( p, exp ) ) #else /* !FT_DEBUG_MEMORY */ @@ -343,14 +344,13 @@ extern "C++" #define FT_RENEW_ARRAY( ptr, curcnt, newcnt ) \ FT_MEM_SET_ERROR( FT_MEM_RENEW_ARRAY( ptr, curcnt, newcnt ) ) -#define FT_QNEW( ptr ) \ - FT_MEM_SET_ERROR( FT_MEM_QNEW( ptr ) ) +#define FT_QNEW( ptr ) FT_MEM_SET_ERROR( FT_MEM_QNEW( ptr ) ) -#define FT_QNEW_ARRAY( ptr, count ) \ - FT_MEM_SET_ERROR( FT_MEM_NEW_ARRAY( ptr, count ) ) +#define FT_QNEW_ARRAY( ptr, count ) \ + FT_MEM_SET_ERROR( FT_MEM_QNEW_ARRAY( ptr, count ) ) -#define FT_QRENEW_ARRAY( ptr, curcnt, newcnt ) \ - FT_MEM_SET_ERROR( FT_MEM_RENEW_ARRAY( ptr, curcnt, newcnt ) ) +#define FT_QRENEW_ARRAY( ptr, curcnt, newcnt ) \ + FT_MEM_SET_ERROR( FT_MEM_QRENEW_ARRAY( ptr, curcnt, newcnt ) ) FT_BASE( FT_Pointer ) @@ -389,8 +389,6 @@ extern "C++" #define FT_STRCPYN( dst, src, size ) \ ft_mem_strcpyn( (char*)dst, (const char*)(src), (FT_ULong)(size) ) - /* */ - FT_END_HEADER diff --git a/3rdparty/freetype-2.13.2/include/freetype/internal/ftmmtypes.h b/3rdparty/freetype-2.13.2/include/freetype/internal/ftmmtypes.h new file mode 100644 index 000000000..c4b21d614 --- /dev/null +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/ftmmtypes.h @@ -0,0 +1,91 @@ +/**************************************************************************** + * + * ftmmtypes.h + * + * OpenType Variations type definitions for internal use + * with the multi-masters service (specification). + * + * Copyright (C) 2022-2023 by + * David Turner, Robert Wilhelm, Werner Lemberg, George Williams, and + * Dominik Röttsches. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + +#ifndef FTMMTYPES_H_ +#define FTMMTYPES_H_ + +FT_BEGIN_HEADER + + + typedef FT_Int32 FT_ItemVarDelta; + + typedef struct GX_ItemVarDataRec_ + { + FT_UInt itemCount; /* Number of delta sets per item. */ + FT_UInt regionIdxCount; /* Number of region indices. */ + FT_UInt* regionIndices; /* Array of `regionCount` indices; */ + /* these index `varRegionList`. */ + FT_Byte* deltaSet; /* Array of `itemCount` deltas; */ + /* use `innerIndex` for this array. */ + FT_UShort wordDeltaCount; /* Number of the first 32-bit ints */ + /* or 16-bit ints of `deltaSet` */ + /* depending on `longWords`. */ + FT_Bool longWords; /* If true, `deltaSet` is a 32-bit */ + /* array followed by a 16-bit */ + /* array, otherwise a 16-bit array */ + /* followed by an 8-bit array. */ + } GX_ItemVarDataRec, *GX_ItemVarData; + + + /* contribution of one axis to a region */ + typedef struct GX_AxisCoordsRec_ + { + FT_Fixed startCoord; + FT_Fixed peakCoord; /* zero means no effect (factor = 1) */ + FT_Fixed endCoord; + + } GX_AxisCoordsRec, *GX_AxisCoords; + + + typedef struct GX_VarRegionRec_ + { + GX_AxisCoords axisList; /* array of axisCount records */ + + } GX_VarRegionRec, *GX_VarRegion; + + + /* item variation store */ + typedef struct GX_ItemVarStoreRec_ + { + FT_UInt dataCount; + GX_ItemVarData varData; /* array of dataCount records; */ + /* use `outerIndex' for this array */ + FT_UShort axisCount; + FT_UInt regionCount; /* total number of regions defined */ + GX_VarRegion varRegionList; + + } GX_ItemVarStoreRec, *GX_ItemVarStore; + + + typedef struct GX_DeltaSetIdxMapRec_ + { + FT_ULong mapCount; + FT_UInt* outerIndex; /* indices to item var data */ + FT_UInt* innerIndex; /* indices to delta set */ + + } GX_DeltaSetIdxMapRec, *GX_DeltaSetIdxMap; + + +FT_END_HEADER + +#endif /* FTMMTYPES_H_ */ + + +/* END */ diff --git a/src/font/freetype-2.10.2/include/freetype/internal/ftobjs.h b/3rdparty/freetype-2.13.2/include/freetype/internal/ftobjs.h similarity index 98% rename from src/font/freetype-2.10.2/include/freetype/internal/ftobjs.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/ftobjs.h index 140eebc7c..28bc9b65f 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/ftobjs.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/ftobjs.h @@ -4,7 +4,7 @@ * * The FreeType private base classes (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -26,21 +26,21 @@ #ifndef FTOBJS_H_ #define FTOBJS_H_ -#include -#include FT_RENDER_H -#include FT_SIZES_H -#include FT_LCD_FILTER_H -#include FT_INTERNAL_MEMORY_H -#include FT_INTERNAL_GLYPH_LOADER_H -#include FT_INTERNAL_DRIVER_H -#include FT_INTERNAL_AUTOHINT_H -#include FT_INTERNAL_SERVICE_H -#include FT_INTERNAL_CALC_H +#include +#include +#include +#include +#include +#include +#include +#include +#include #ifdef FT_CONFIG_OPTION_INCREMENTAL -#include FT_INCREMENTAL_H +#include #endif +#include "compiler-macros.h" FT_BEGIN_HEADER @@ -226,8 +226,8 @@ FT_BEGIN_HEADER } FT_CMap_ClassRec; -#define FT_DECLARE_CMAP_CLASS( class_ ) \ - FT_CALLBACK_TABLE const FT_CMap_ClassRec class_; +#define FT_DECLARE_CMAP_CLASS( class_ ) \ + FT_CALLBACK_TABLE const FT_CMap_ClassRec class_; #define FT_DEFINE_CMAP_CLASS( \ class_, \ @@ -418,7 +418,8 @@ FT_BEGIN_HEADER * initializing the glyph slot. */ -#define FT_GLYPH_OWN_BITMAP 0x1U +#define FT_GLYPH_OWN_BITMAP 0x1U +#define FT_GLYPH_OWN_GZIP_SVG 0x2U typedef struct FT_Slot_InternalRec_ { @@ -653,7 +654,7 @@ FT_BEGIN_HEADER FT_BASE( void ) FT_Done_GlyphSlot( FT_GlyphSlot slot ); - /* */ + /* */ #define FT_REQUEST_WIDTH( req ) \ ( (req)->horiResolution \ @@ -673,7 +674,7 @@ FT_BEGIN_HEADER /* Set the metrics according to a size request. */ - FT_BASE( void ) + FT_BASE( FT_Error ) FT_Request_Metrics( FT_Face face, FT_Size_Request req ); @@ -1057,6 +1058,9 @@ FT_BEGIN_HEADER * The struct will be allocated in the global scope (or the scope where * the macro is used). */ +#define FT_DECLARE_GLYPH( class_ ) \ + FT_CALLBACK_TABLE const FT_Glyph_Class class_; + #define FT_DEFINE_GLYPH( \ class_, \ size_, \ diff --git a/src/font/freetype-2.10.2/include/freetype/internal/ftpsprop.h b/3rdparty/freetype-2.13.2/include/freetype/internal/ftpsprop.h similarity index 93% rename from src/font/freetype-2.10.2/include/freetype/internal/ftpsprop.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/ftpsprop.h index 72907c4c3..1d5b287ad 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/ftpsprop.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/ftpsprop.h @@ -4,7 +4,7 @@ * * Get and set properties of PostScript drivers (specification). * - * Copyright (C) 2017-2020 by + * Copyright (C) 2017-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,8 +20,7 @@ #define FTPSPROP_H_ -#include -#include FT_FREETYPE_H +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/ftrfork.h b/3rdparty/freetype-2.13.2/include/freetype/internal/ftrfork.h similarity index 98% rename from src/font/freetype-2.10.2/include/freetype/internal/ftrfork.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/ftrfork.h index 9a275a515..e96459921 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/ftrfork.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/ftrfork.h @@ -4,7 +4,7 @@ * * Embedded resource forks accessor (specification). * - * Copyright (C) 2004-2020 by + * Copyright (C) 2004-2023 by * Masatake YAMATO and Redhat K.K. * * This file is part of the FreeType project, and may only be used, @@ -25,8 +25,7 @@ #define FTRFORK_H_ -#include -#include FT_INTERNAL_OBJECTS_H +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/ftserv.h b/3rdparty/freetype-2.13.2/include/freetype/internal/ftserv.h similarity index 93% rename from src/font/freetype-2.10.2/include/freetype/internal/ftserv.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/ftserv.h index bcaf4720d..1e85d6d38 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/ftserv.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/ftserv.h @@ -4,7 +4,7 @@ * * The FreeType services (specification only). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -31,6 +31,7 @@ #ifndef FTSERV_H_ #define FTSERV_H_ +#include "compiler-macros.h" FT_BEGIN_HEADER @@ -486,33 +487,6 @@ FT_BEGIN_HEADER /* */ - /* - * The header files containing the services. - */ - -#define FT_SERVICE_BDF_H -#define FT_SERVICE_CFF_TABLE_LOAD_H -#define FT_SERVICE_CID_H -#define FT_SERVICE_FONT_FORMAT_H -#define FT_SERVICE_GLYPH_DICT_H -#define FT_SERVICE_GX_VALIDATE_H -#define FT_SERVICE_KERNING_H -#define FT_SERVICE_METRICS_VARIATIONS_H -#define FT_SERVICE_MULTIPLE_MASTERS_H -#define FT_SERVICE_OPENTYPE_VALIDATE_H -#define FT_SERVICE_PFR_H -#define FT_SERVICE_POSTSCRIPT_CMAPS_H -#define FT_SERVICE_POSTSCRIPT_INFO_H -#define FT_SERVICE_POSTSCRIPT_NAME_H -#define FT_SERVICE_PROPERTIES_H -#define FT_SERVICE_SFNT_H -#define FT_SERVICE_TRUETYPE_ENGINE_H -#define FT_SERVICE_TRUETYPE_GLYF_H -#define FT_SERVICE_TT_CMAP_H -#define FT_SERVICE_WINFNT_H - - /* */ - FT_END_HEADER #endif /* FTSERV_H_ */ diff --git a/src/font/freetype-2.10.2/include/freetype/internal/ftstream.h b/3rdparty/freetype-2.13.2/include/freetype/internal/ftstream.h similarity index 86% rename from src/font/freetype-2.10.2/include/freetype/internal/ftstream.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/ftstream.h index f3b3ef0d0..88e19287c 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/ftstream.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/ftstream.h @@ -4,7 +4,7 @@ * * Stream handling (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -21,8 +21,8 @@ #include -#include FT_SYSTEM_H -#include FT_INTERNAL_OBJECTS_H +#include +#include FT_BEGIN_HEADER @@ -196,9 +196,9 @@ FT_BEGIN_HEADER FT_BYTE_U32( p, 2, 8 ) | \ FT_BYTE_U32( p, 3, 0 ) ) -#define FT_PEEK_OFF3( p ) FT_INT32( FT_BYTE_U32( p, 0, 16 ) | \ - FT_BYTE_U32( p, 1, 8 ) | \ - FT_BYTE_U32( p, 2, 0 ) ) +#define FT_PEEK_OFF3( p ) ( FT_INT32( FT_BYTE_U32( p, 0, 24 ) | \ + FT_BYTE_U32( p, 1, 16 ) | \ + FT_BYTE_U32( p, 2, 8 ) ) >> 8 ) #define FT_PEEK_UOFF3( p ) FT_UINT32( FT_BYTE_U32( p, 0, 16 ) | \ FT_BYTE_U32( p, 1, 8 ) | \ @@ -220,9 +220,9 @@ FT_BEGIN_HEADER FT_BYTE_U32( p, 1, 8 ) | \ FT_BYTE_U32( p, 0, 0 ) ) -#define FT_PEEK_OFF3_LE( p ) FT_INT32( FT_BYTE_U32( p, 2, 16 ) | \ - FT_BYTE_U32( p, 1, 8 ) | \ - FT_BYTE_U32( p, 0, 0 ) ) +#define FT_PEEK_OFF3_LE( p ) ( FT_INT32( FT_BYTE_U32( p, 2, 24 ) | \ + FT_BYTE_U32( p, 1, 16 ) | \ + FT_BYTE_U32( p, 0, 8 ) ) >> 8 ) #define FT_PEEK_UOFF3_LE( p ) FT_UINT32( FT_BYTE_U32( p, 2, 16 ) | \ FT_BYTE_U32( p, 1, 8 ) | \ @@ -238,42 +238,42 @@ FT_BEGIN_HEADER #define FT_NEXT_BYTE( buffer ) \ ( (unsigned char)*buffer++ ) -#define FT_NEXT_SHORT( buffer ) \ - ( (short)( buffer += 2, FT_PEEK_SHORT( buffer - 2 ) ) ) +#define FT_NEXT_SHORT( buffer ) \ + ( buffer += 2, FT_PEEK_SHORT( buffer - 2 ) ) -#define FT_NEXT_USHORT( buffer ) \ - ( (unsigned short)( buffer += 2, FT_PEEK_USHORT( buffer - 2 ) ) ) +#define FT_NEXT_USHORT( buffer ) \ + ( buffer += 2, FT_PEEK_USHORT( buffer - 2 ) ) -#define FT_NEXT_OFF3( buffer ) \ - ( (long)( buffer += 3, FT_PEEK_OFF3( buffer - 3 ) ) ) +#define FT_NEXT_OFF3( buffer ) \ + ( buffer += 3, FT_PEEK_OFF3( buffer - 3 ) ) -#define FT_NEXT_UOFF3( buffer ) \ - ( (unsigned long)( buffer += 3, FT_PEEK_UOFF3( buffer - 3 ) ) ) +#define FT_NEXT_UOFF3( buffer ) \ + ( buffer += 3, FT_PEEK_UOFF3( buffer - 3 ) ) -#define FT_NEXT_LONG( buffer ) \ - ( (long)( buffer += 4, FT_PEEK_LONG( buffer - 4 ) ) ) +#define FT_NEXT_LONG( buffer ) \ + ( buffer += 4, FT_PEEK_LONG( buffer - 4 ) ) -#define FT_NEXT_ULONG( buffer ) \ - ( (unsigned long)( buffer += 4, FT_PEEK_ULONG( buffer - 4 ) ) ) +#define FT_NEXT_ULONG( buffer ) \ + ( buffer += 4, FT_PEEK_ULONG( buffer - 4 ) ) -#define FT_NEXT_SHORT_LE( buffer ) \ - ( (short)( buffer += 2, FT_PEEK_SHORT_LE( buffer - 2 ) ) ) +#define FT_NEXT_SHORT_LE( buffer ) \ + ( buffer += 2, FT_PEEK_SHORT_LE( buffer - 2 ) ) -#define FT_NEXT_USHORT_LE( buffer ) \ - ( (unsigned short)( buffer += 2, FT_PEEK_USHORT_LE( buffer - 2 ) ) ) +#define FT_NEXT_USHORT_LE( buffer ) \ + ( buffer += 2, FT_PEEK_USHORT_LE( buffer - 2 ) ) -#define FT_NEXT_OFF3_LE( buffer ) \ - ( (long)( buffer += 3, FT_PEEK_OFF3_LE( buffer - 3 ) ) ) +#define FT_NEXT_OFF3_LE( buffer ) \ + ( buffer += 3, FT_PEEK_OFF3_LE( buffer - 3 ) ) -#define FT_NEXT_UOFF3_LE( buffer ) \ - ( (unsigned long)( buffer += 3, FT_PEEK_UOFF3_LE( buffer - 3 ) ) ) +#define FT_NEXT_UOFF3_LE( buffer ) \ + ( buffer += 3, FT_PEEK_UOFF3_LE( buffer - 3 ) ) -#define FT_NEXT_LONG_LE( buffer ) \ - ( (long)( buffer += 4, FT_PEEK_LONG_LE( buffer - 4 ) ) ) +#define FT_NEXT_LONG_LE( buffer ) \ + ( buffer += 4, FT_PEEK_LONG_LE( buffer - 4 ) ) -#define FT_NEXT_ULONG_LE( buffer ) \ - ( (unsigned long)( buffer += 4, FT_PEEK_ULONG_LE( buffer - 4 ) ) ) +#define FT_NEXT_ULONG_LE( buffer ) \ + ( buffer += 4, FT_PEEK_ULONG_LE( buffer - 4 ) ) /************************************************************************** @@ -305,20 +305,19 @@ FT_BEGIN_HEADER #else #define FT_GET_MACRO( func, type ) ( (type)func( stream ) ) -#define FT_GET_CHAR() FT_GET_MACRO( FT_Stream_GetChar, FT_Char ) -#define FT_GET_BYTE() FT_GET_MACRO( FT_Stream_GetChar, FT_Byte ) -#define FT_GET_SHORT() FT_GET_MACRO( FT_Stream_GetUShort, FT_Short ) -#define FT_GET_USHORT() FT_GET_MACRO( FT_Stream_GetUShort, FT_UShort ) -#define FT_GET_OFF3() FT_GET_MACRO( FT_Stream_GetUOffset, FT_Long ) -#define FT_GET_UOFF3() FT_GET_MACRO( FT_Stream_GetUOffset, FT_ULong ) -#define FT_GET_LONG() FT_GET_MACRO( FT_Stream_GetULong, FT_Long ) -#define FT_GET_ULONG() FT_GET_MACRO( FT_Stream_GetULong, FT_ULong ) -#define FT_GET_TAG4() FT_GET_MACRO( FT_Stream_GetULong, FT_ULong ) - -#define FT_GET_SHORT_LE() FT_GET_MACRO( FT_Stream_GetUShortLE, FT_Short ) -#define FT_GET_USHORT_LE() FT_GET_MACRO( FT_Stream_GetUShortLE, FT_UShort ) -#define FT_GET_LONG_LE() FT_GET_MACRO( FT_Stream_GetULongLE, FT_Long ) -#define FT_GET_ULONG_LE() FT_GET_MACRO( FT_Stream_GetULongLE, FT_ULong ) +#define FT_GET_CHAR() FT_GET_MACRO( FT_Stream_GetByte, FT_Char ) +#define FT_GET_BYTE() FT_GET_MACRO( FT_Stream_GetByte, FT_Byte ) +#define FT_GET_SHORT() FT_GET_MACRO( FT_Stream_GetUShort, FT_Int16 ) +#define FT_GET_USHORT() FT_GET_MACRO( FT_Stream_GetUShort, FT_UInt16 ) +#define FT_GET_UOFF3() FT_GET_MACRO( FT_Stream_GetUOffset, FT_UInt32 ) +#define FT_GET_LONG() FT_GET_MACRO( FT_Stream_GetULong, FT_Int32 ) +#define FT_GET_ULONG() FT_GET_MACRO( FT_Stream_GetULong, FT_UInt32 ) +#define FT_GET_TAG4() FT_GET_MACRO( FT_Stream_GetULong, FT_UInt32 ) + +#define FT_GET_SHORT_LE() FT_GET_MACRO( FT_Stream_GetUShortLE, FT_Int16 ) +#define FT_GET_USHORT_LE() FT_GET_MACRO( FT_Stream_GetUShortLE, FT_UInt16 ) +#define FT_GET_LONG_LE() FT_GET_MACRO( FT_Stream_GetULongLE, FT_Int32 ) +#define FT_GET_ULONG_LE() FT_GET_MACRO( FT_Stream_GetULongLE, FT_UInt32 ) #endif @@ -333,19 +332,18 @@ FT_BEGIN_HEADER * `FT_STREAM_POS'. They use the full machinery to check whether a read is * valid. */ -#define FT_READ_BYTE( var ) FT_READ_MACRO( FT_Stream_ReadChar, FT_Byte, var ) -#define FT_READ_CHAR( var ) FT_READ_MACRO( FT_Stream_ReadChar, FT_Char, var ) -#define FT_READ_SHORT( var ) FT_READ_MACRO( FT_Stream_ReadUShort, FT_Short, var ) -#define FT_READ_USHORT( var ) FT_READ_MACRO( FT_Stream_ReadUShort, FT_UShort, var ) -#define FT_READ_OFF3( var ) FT_READ_MACRO( FT_Stream_ReadUOffset, FT_Long, var ) -#define FT_READ_UOFF3( var ) FT_READ_MACRO( FT_Stream_ReadUOffset, FT_ULong, var ) -#define FT_READ_LONG( var ) FT_READ_MACRO( FT_Stream_ReadULong, FT_Long, var ) -#define FT_READ_ULONG( var ) FT_READ_MACRO( FT_Stream_ReadULong, FT_ULong, var ) +#define FT_READ_BYTE( var ) FT_READ_MACRO( FT_Stream_ReadByte, FT_Byte, var ) +#define FT_READ_CHAR( var ) FT_READ_MACRO( FT_Stream_ReadByte, FT_Char, var ) +#define FT_READ_SHORT( var ) FT_READ_MACRO( FT_Stream_ReadUShort, FT_Int16, var ) +#define FT_READ_USHORT( var ) FT_READ_MACRO( FT_Stream_ReadUShort, FT_UInt16, var ) +#define FT_READ_UOFF3( var ) FT_READ_MACRO( FT_Stream_ReadUOffset, FT_UInt32, var ) +#define FT_READ_LONG( var ) FT_READ_MACRO( FT_Stream_ReadULong, FT_Int32, var ) +#define FT_READ_ULONG( var ) FT_READ_MACRO( FT_Stream_ReadULong, FT_UInt32, var ) -#define FT_READ_SHORT_LE( var ) FT_READ_MACRO( FT_Stream_ReadUShortLE, FT_Short, var ) -#define FT_READ_USHORT_LE( var ) FT_READ_MACRO( FT_Stream_ReadUShortLE, FT_UShort, var ) -#define FT_READ_LONG_LE( var ) FT_READ_MACRO( FT_Stream_ReadULongLE, FT_Long, var ) -#define FT_READ_ULONG_LE( var ) FT_READ_MACRO( FT_Stream_ReadULongLE, FT_ULong, var ) +#define FT_READ_SHORT_LE( var ) FT_READ_MACRO( FT_Stream_ReadUShortLE, FT_Int16, var ) +#define FT_READ_USHORT_LE( var ) FT_READ_MACRO( FT_Stream_ReadUShortLE, FT_UInt16, var ) +#define FT_READ_LONG_LE( var ) FT_READ_MACRO( FT_Stream_ReadULongLE, FT_Int32, var ) +#define FT_READ_ULONG_LE( var ) FT_READ_MACRO( FT_Stream_ReadULongLE, FT_UInt32, var ) #ifndef FT_CONFIG_OPTION_NO_DEFAULT_SYSTEM @@ -457,37 +455,37 @@ FT_BEGIN_HEADER /* read a byte from an entered frame */ - FT_BASE( FT_Char ) - FT_Stream_GetChar( FT_Stream stream ); + FT_BASE( FT_Byte ) + FT_Stream_GetByte( FT_Stream stream ); /* read a 16-bit big-endian unsigned integer from an entered frame */ - FT_BASE( FT_UShort ) + FT_BASE( FT_UInt16 ) FT_Stream_GetUShort( FT_Stream stream ); /* read a 24-bit big-endian unsigned integer from an entered frame */ - FT_BASE( FT_ULong ) + FT_BASE( FT_UInt32 ) FT_Stream_GetUOffset( FT_Stream stream ); /* read a 32-bit big-endian unsigned integer from an entered frame */ - FT_BASE( FT_ULong ) + FT_BASE( FT_UInt32 ) FT_Stream_GetULong( FT_Stream stream ); /* read a 16-bit little-endian unsigned integer from an entered frame */ - FT_BASE( FT_UShort ) + FT_BASE( FT_UInt16 ) FT_Stream_GetUShortLE( FT_Stream stream ); /* read a 32-bit little-endian unsigned integer from an entered frame */ - FT_BASE( FT_ULong ) + FT_BASE( FT_UInt32 ) FT_Stream_GetULongLE( FT_Stream stream ); /* read a byte from a stream */ - FT_BASE( FT_Char ) - FT_Stream_ReadChar( FT_Stream stream, + FT_BASE( FT_Byte ) + FT_Stream_ReadByte( FT_Stream stream, FT_Error* error ); /* read a 16-bit big-endian unsigned integer from a stream */ - FT_BASE( FT_UShort ) + FT_BASE( FT_UInt16 ) FT_Stream_ReadUShort( FT_Stream stream, FT_Error* error ); @@ -497,17 +495,17 @@ FT_BEGIN_HEADER FT_Error* error ); /* read a 32-bit big-endian integer from a stream */ - FT_BASE( FT_ULong ) + FT_BASE( FT_UInt32 ) FT_Stream_ReadULong( FT_Stream stream, FT_Error* error ); /* read a 16-bit little-endian unsigned integer from a stream */ - FT_BASE( FT_UShort ) + FT_BASE( FT_UInt16 ) FT_Stream_ReadUShortLE( FT_Stream stream, FT_Error* error ); /* read a 32-bit little-endian unsigned integer from a stream */ - FT_BASE( FT_ULong ) + FT_BASE( FT_UInt32 ) FT_Stream_ReadULongLE( FT_Stream stream, FT_Error* error ); diff --git a/src/font/freetype-2.10.2/include/freetype/internal/fttrace.h b/3rdparty/freetype-2.13.2/include/freetype/internal/fttrace.h similarity index 87% rename from src/font/freetype-2.10.2/include/freetype/internal/fttrace.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/fttrace.h index 58bd77413..319fe56fd 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/fttrace.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/fttrace.h @@ -4,7 +4,7 @@ * * Tracing handling (specification only). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -18,6 +18,11 @@ /* definitions of trace levels for FreeType 2 */ + /* the maximum string length (if the argument to `FT_TRACE_DEF` */ + /* gets used as a string) plus one charachter for ':' plus */ + /* another one for the trace level */ +#define FT_MAX_TRACE_LEVEL_LENGTH (9 + 1 + 1) + /* the first level must always be `trace_any' */ FT_TRACE_DEF( any ) @@ -38,12 +43,17 @@ FT_TRACE_DEF( checksum ) /* bitmap checksum (ftobjs.c) */ FT_TRACE_DEF( mm ) /* MM interface (ftmm.c) */ FT_TRACE_DEF( psprops ) /* PS driver properties (ftpsprop.c) */ FT_TRACE_DEF( raccess ) /* resource fork accessor (ftrfork.c) */ +FT_TRACE_DEF( synth ) /* bold/slant synthesizer (ftsynth.c) */ + + /* rasterizers */ FT_TRACE_DEF( raster ) /* monochrome rasterizer (ftraster.c) */ FT_TRACE_DEF( smooth ) /* anti-aliasing raster (ftgrays.c) */ -FT_TRACE_DEF( synth ) /* bold/slant synthesizer (ftsynth.c) */ - /* Cache sub-system */ -FT_TRACE_DEF( cache ) /* cache sub-system (ftcache.c, etc.) */ + /* ot-svg module */ +FT_TRACE_DEF( otsvg ) /* OT-SVG renderer (ftsvg.c) */ + + /* cache sub-system */ +FT_TRACE_DEF( cache ) /* cache sub-system (ftcache.c, etc.) */ /* SFNT driver components */ FT_TRACE_DEF( sfdriver ) /* SFNT font driver (sfdriver.c) */ @@ -54,6 +64,7 @@ FT_TRACE_DEF( ttbdf ) /* TrueType embedded BDF (ttbdf.c) */ FT_TRACE_DEF( ttcmap ) /* charmap handler (ttcmap.c) */ FT_TRACE_DEF( ttcolr ) /* glyph layer table (ttcolr.c) */ FT_TRACE_DEF( ttcpal ) /* color palette table (ttcpal.c) */ +FT_TRACE_DEF( ttsvg ) /* OpenType SVG table (ttsvg.c) */ FT_TRACE_DEF( ttkern ) /* kerning handler (ttkern.c) */ FT_TRACE_DEF( ttload ) /* basic TrueType tables (ttload.c) */ FT_TRACE_DEF( ttmtx ) /* metrics-related tables (ttmtx.c) */ @@ -77,6 +88,7 @@ FT_TRACE_DEF( t1objs ) FT_TRACE_DEF( t1parse ) /* PostScript helper module `psaux' */ +FT_TRACE_DEF( afmparse ) FT_TRACE_DEF( cffdecode ) FT_TRACE_DEF( psconv ) FT_TRACE_DEF( psobjs ) @@ -151,8 +163,10 @@ FT_TRACE_DEF( afglobal ) FT_TRACE_DEF( afhints ) FT_TRACE_DEF( afmodule ) FT_TRACE_DEF( aflatin ) -FT_TRACE_DEF( aflatin2 ) FT_TRACE_DEF( afshaper ) -FT_TRACE_DEF( afwarp ) + + /* SDF components */ +FT_TRACE_DEF( sdf ) /* signed distance raster for outlines (ftsdf.c) */ +FT_TRACE_DEF( bsdf ) /* signed distance raster for bitmaps (ftbsdf.c) */ /* END */ diff --git a/src/font/freetype-2.10.2/include/freetype/internal/ftvalid.h b/3rdparty/freetype-2.13.2/include/freetype/internal/ftvalid.h similarity index 97% rename from src/font/freetype-2.10.2/include/freetype/internal/ftvalid.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/ftvalid.h index 62aea4dc6..e98ee4e47 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/ftvalid.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/ftvalid.h @@ -4,7 +4,7 @@ * * FreeType validation support (specification). * - * Copyright (C) 2004-2020 by + * Copyright (C) 2004-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,8 +20,9 @@ #define FTVALID_H_ #include -#include FT_CONFIG_STANDARD_LIBRARY_H /* for ft_setjmp and ft_longjmp */ +#include FT_CONFIG_STANDARD_LIBRARY_H /* for ft_jmpbuf */ +#include "compiler-macros.h" FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/psaux.h b/3rdparty/freetype-2.13.2/include/freetype/internal/psaux.h similarity index 99% rename from src/font/freetype-2.10.2/include/freetype/internal/psaux.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/psaux.h index 8248a0ecd..dfb1987f8 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/psaux.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/psaux.h @@ -5,7 +5,7 @@ * Auxiliary functions and data structures related to PostScript fonts * (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -21,14 +21,13 @@ #define PSAUX_H_ -#include -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_TYPE1_TYPES_H -#include FT_INTERNAL_HASH_H -#include FT_INTERNAL_TRUETYPE_TYPES_H -#include FT_SERVICE_POSTSCRIPT_CMAPS_H -#include FT_INTERNAL_CFF_TYPES_H -#include FT_INTERNAL_CFF_OBJECTS_TYPES_H +#include +#include +#include +#include +#include +#include +#include @@ -133,9 +132,6 @@ FT_BEGIN_HEADER * max_elems :: * The maximum number of elements in table. * - * num_elems :: - * The current number of elements in table. - * * elements :: * A table of element addresses within the block. * @@ -156,7 +152,6 @@ FT_BEGIN_HEADER FT_ULong init; FT_Int max_elems; - FT_Int num_elems; FT_Byte** elements; /* addresses of table elements */ FT_UInt* lengths; /* lengths of table elements */ diff --git a/src/font/freetype-2.10.2/include/freetype/internal/pshints.h b/3rdparty/freetype-2.13.2/include/freetype/internal/pshints.h similarity index 99% rename from src/font/freetype-2.10.2/include/freetype/internal/pshints.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/pshints.h index cf0c65298..ededc4c72 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/pshints.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/pshints.h @@ -6,7 +6,7 @@ * recorders (specification only). These are used to support native * T1/T2 hints in the 'type1', 'cid', and 'cff' font drivers. * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -22,9 +22,8 @@ #define PSHINTS_H_ -#include -#include FT_FREETYPE_H -#include FT_TYPE1_TABLES_H +#include +#include FT_BEGIN_HEADER @@ -295,7 +294,7 @@ FT_BEGIN_HEADER * * @note: * On input, all points within the outline are in font coordinates. On - * output, they are in 1/64th of pixels. + * output, they are in 1/64 of pixels. * * The scaling transformation is taken from the 'globals' object which * must correspond to the same font as the glyph. @@ -608,7 +607,7 @@ FT_BEGIN_HEADER * * @note: * On input, all points within the outline are in font coordinates. On - * output, they are in 1/64th of pixels. + * output, they are in 1/64 of pixels. * * The scaling transformation is taken from the 'globals' object which * must correspond to the same font than the glyph. diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svbdf.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svbdf.h similarity index 94% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svbdf.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svbdf.h index 0ec9c7ccb..bf0c1dcc7 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svbdf.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svbdf.h @@ -4,7 +4,7 @@ * * The FreeType BDF services (specification). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,8 @@ #ifndef SVBDF_H_ #define SVBDF_H_ -#include FT_BDF_H -#include FT_INTERNAL_SERVICE_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svcfftl.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svcfftl.h similarity index 96% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svcfftl.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svcfftl.h index c2f42c1d1..4a20498ee 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svcfftl.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svcfftl.h @@ -4,7 +4,7 @@ * * The FreeType CFF tables loader service (specification). * - * Copyright (C) 2017-2020 by + * Copyright (C) 2017-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,8 @@ #ifndef SVCFFTL_H_ #define SVCFFTL_H_ -#include FT_INTERNAL_SERVICE_H -#include FT_INTERNAL_CFF_TYPES_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svcid.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svcid.h similarity index 96% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svcid.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svcid.h index b8efd8147..06d0cb8fd 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svcid.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svcid.h @@ -4,7 +4,7 @@ * * The FreeType CID font services (specification). * - * Copyright (C) 2007-2020 by + * Copyright (C) 2007-2023 by * Derek Clegg and Michael Toftdal. * * This file is part of the FreeType project, and may only be used, @@ -19,7 +19,7 @@ #ifndef SVCID_H_ #define SVCID_H_ -#include FT_INTERNAL_SERVICE_H +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svfntfmt.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svfntfmt.h similarity index 94% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svfntfmt.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svfntfmt.h index 5ec84c933..bc45e8056 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svfntfmt.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svfntfmt.h @@ -4,7 +4,7 @@ * * The FreeType font format service (specification only). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,7 +19,7 @@ #ifndef SVFNTFMT_H_ #define SVFNTFMT_H_ -#include FT_INTERNAL_SERVICE_H +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svgldict.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svgldict.h similarity index 96% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svgldict.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svgldict.h index 5a63883c9..6437abfbf 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svgldict.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svgldict.h @@ -4,7 +4,7 @@ * * The FreeType glyph dictionary services (specification). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,7 +19,7 @@ #ifndef SVGLDICT_H_ #define SVGLDICT_H_ -#include FT_INTERNAL_SERVICE_H +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svgxval.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svgxval.h similarity index 94% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svgxval.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svgxval.h index d0cb10a42..31016afe0 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svgxval.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svgxval.h @@ -4,7 +4,7 @@ * * FreeType API for validating TrueTypeGX/AAT tables (specification). * - * Copyright (C) 2004-2020 by + * Copyright (C) 2004-2023 by * Masatake YAMATO, Red Hat K.K., * David Turner, Robert Wilhelm, and Werner Lemberg. * @@ -28,8 +28,8 @@ #ifndef SVGXVAL_H_ #define SVGXVAL_H_ -#include FT_GX_VALIDATE_H -#include FT_INTERNAL_VALIDATE_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svkern.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svkern.h similarity index 90% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svkern.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svkern.h index 891c61a75..bcabbc3e6 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svkern.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svkern.h @@ -4,7 +4,7 @@ * * The FreeType Kerning service (specification). * - * Copyright (C) 2006-2020 by + * Copyright (C) 2006-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,8 @@ #ifndef SVKERN_H_ #define SVKERN_H_ -#include FT_INTERNAL_SERVICE_H -#include FT_TRUETYPE_TABLES_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svmetric.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svmetric.h similarity index 89% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svmetric.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svmetric.h index 06faa4b4f..167617ebb 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svmetric.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svmetric.h @@ -4,7 +4,7 @@ * * The FreeType services for metrics variations (specification). * - * Copyright (C) 2016-2020 by + * Copyright (C) 2016-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,7 +19,7 @@ #ifndef SVMETRIC_H_ #define SVMETRIC_H_ -#include FT_INTERNAL_SERVICE_H +#include FT_BEGIN_HEADER @@ -77,6 +77,9 @@ FT_BEGIN_HEADER typedef void (*FT_Metrics_Adjust_Func)( FT_Face face ); + typedef FT_Error + (*FT_Size_Reset_Func)( FT_Size size ); + FT_DEFINE_SERVICE( MetricsVariations ) { @@ -90,6 +93,7 @@ FT_BEGIN_HEADER FT_VOrg_Adjust_Func vorg_adjust; FT_Metrics_Adjust_Func metrics_adjust; + FT_Size_Reset_Func size_reset; }; @@ -101,7 +105,8 @@ FT_BEGIN_HEADER tsb_adjust_, \ bsb_adjust_, \ vorg_adjust_, \ - metrics_adjust_ ) \ + metrics_adjust_, \ + size_reset_ ) \ static const FT_Service_MetricsVariationsRec class_ = \ { \ hadvance_adjust_, \ @@ -111,7 +116,8 @@ FT_BEGIN_HEADER tsb_adjust_, \ bsb_adjust_, \ vorg_adjust_, \ - metrics_adjust_ \ + metrics_adjust_, \ + size_reset_ \ }; /* */ diff --git a/3rdparty/freetype-2.13.2/include/freetype/internal/services/svmm.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svmm.h new file mode 100644 index 000000000..7e76ab832 --- /dev/null +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svmm.h @@ -0,0 +1,214 @@ +/**************************************************************************** + * + * svmm.h + * + * The FreeType Multiple Masters and GX var services (specification). + * + * Copyright (C) 2003-2023 by + * David Turner, Robert Wilhelm, Werner Lemberg, and Dominik Röttsches. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + +#ifndef SVMM_H_ +#define SVMM_H_ + +#include +#include +#include + + +FT_BEGIN_HEADER + + + /* + * A service used to manage multiple-masters data in a given face. + * + * See the related APIs in `ftmm.h' (FT_MULTIPLE_MASTERS_H). + * + */ + +#define FT_SERVICE_ID_MULTI_MASTERS "multi-masters" + + + typedef FT_Error + (*FT_Get_MM_Func)( FT_Face face, + FT_Multi_Master* master ); + + typedef FT_Error + (*FT_Get_MM_Var_Func)( FT_Face face, + FT_MM_Var* *master ); + + typedef FT_Error + (*FT_Set_MM_Design_Func)( FT_Face face, + FT_UInt num_coords, + FT_Long* coords ); + + /* use return value -1 to indicate that the new coordinates */ + /* are equal to the current ones; no changes are thus needed */ + typedef FT_Error + (*FT_Set_Var_Design_Func)( FT_Face face, + FT_UInt num_coords, + FT_Fixed* coords ); + + /* use return value -1 to indicate that the new coordinates */ + /* are equal to the current ones; no changes are thus needed */ + typedef FT_Error + (*FT_Set_MM_Blend_Func)( FT_Face face, + FT_UInt num_coords, + FT_Fixed* coords ); + + typedef FT_Error + (*FT_Get_Var_Design_Func)( FT_Face face, + FT_UInt num_coords, + FT_Fixed* coords ); + + typedef FT_Error + (*FT_Set_Named_Instance_Func)( FT_Face face, + FT_UInt instance_index ); + + typedef FT_Error + (*FT_Get_Default_Named_Instance_Func)( FT_Face face, + FT_UInt *instance_index ); + + typedef FT_Error + (*FT_Get_MM_Blend_Func)( FT_Face face, + FT_UInt num_coords, + FT_Fixed* coords ); + + typedef FT_Error + (*FT_Get_Var_Blend_Func)( FT_Face face, + FT_UInt *num_coords, + FT_Fixed* *coords, + FT_Fixed* *normalizedcoords, + FT_MM_Var* *mm_var ); + + typedef void + (*FT_Done_Blend_Func)( FT_Face face ); + + typedef FT_Error + (*FT_Set_MM_WeightVector_Func)( FT_Face face, + FT_UInt len, + FT_Fixed* weight_vector ); + + typedef FT_Error + (*FT_Get_MM_WeightVector_Func)( FT_Face face, + FT_UInt* len, + FT_Fixed* weight_vector ); + + typedef void + (*FT_Construct_PS_Name_Func)( FT_Face face ); + + typedef FT_Error + (*FT_Var_Load_Delta_Set_Idx_Map_Func)( FT_Face face, + FT_ULong offset, + GX_DeltaSetIdxMap map, + GX_ItemVarStore itemStore, + FT_ULong table_len ); + + typedef FT_Error + (*FT_Var_Load_Item_Var_Store_Func)( FT_Face face, + FT_ULong offset, + GX_ItemVarStore itemStore ); + + typedef FT_ItemVarDelta + (*FT_Var_Get_Item_Delta_Func)( FT_Face face, + GX_ItemVarStore itemStore, + FT_UInt outerIndex, + FT_UInt innerIndex ); + + typedef void + (*FT_Var_Done_Item_Var_Store_Func)( FT_Face face, + GX_ItemVarStore itemStore ); + + typedef void + (*FT_Var_Done_Delta_Set_Idx_Map_Func)( FT_Face face, + GX_DeltaSetIdxMap deltaSetIdxMap ); + + + FT_DEFINE_SERVICE( MultiMasters ) + { + FT_Get_MM_Func get_mm; + FT_Set_MM_Design_Func set_mm_design; + FT_Set_MM_Blend_Func set_mm_blend; + FT_Get_MM_Blend_Func get_mm_blend; + FT_Get_MM_Var_Func get_mm_var; + FT_Set_Var_Design_Func set_var_design; + FT_Get_Var_Design_Func get_var_design; + FT_Set_Named_Instance_Func set_named_instance; + FT_Get_Default_Named_Instance_Func get_default_named_instance; + FT_Set_MM_WeightVector_Func set_mm_weightvector; + FT_Get_MM_WeightVector_Func get_mm_weightvector; + + /* for internal use; only needed for code sharing between modules */ + FT_Construct_PS_Name_Func construct_ps_name; + FT_Var_Load_Delta_Set_Idx_Map_Func load_delta_set_idx_map; + FT_Var_Load_Item_Var_Store_Func load_item_var_store; + FT_Var_Get_Item_Delta_Func get_item_delta; + FT_Var_Done_Item_Var_Store_Func done_item_var_store; + FT_Var_Done_Delta_Set_Idx_Map_Func done_delta_set_idx_map; + FT_Get_Var_Blend_Func get_var_blend; + FT_Done_Blend_Func done_blend; + }; + + +#define FT_DEFINE_SERVICE_MULTIMASTERSREC( class_, \ + get_mm_, \ + set_mm_design_, \ + set_mm_blend_, \ + get_mm_blend_, \ + get_mm_var_, \ + set_var_design_, \ + get_var_design_, \ + set_named_instance_, \ + get_default_named_instance_, \ + set_mm_weightvector_, \ + get_mm_weightvector_, \ + \ + construct_ps_name_, \ + load_delta_set_idx_map_, \ + load_item_var_store_, \ + get_item_delta_, \ + done_item_var_store_, \ + done_delta_set_idx_map_, \ + get_var_blend_, \ + done_blend_ ) \ + static const FT_Service_MultiMastersRec class_ = \ + { \ + get_mm_, \ + set_mm_design_, \ + set_mm_blend_, \ + get_mm_blend_, \ + get_mm_var_, \ + set_var_design_, \ + get_var_design_, \ + set_named_instance_, \ + get_default_named_instance_, \ + set_mm_weightvector_, \ + get_mm_weightvector_, \ + \ + construct_ps_name_, \ + load_delta_set_idx_map_, \ + load_item_var_store_, \ + get_item_delta_, \ + done_item_var_store_, \ + done_delta_set_idx_map_, \ + get_var_blend_, \ + done_blend_ \ + }; + + /* */ + + +FT_END_HEADER + +#endif /* SVMM_H_ */ + + +/* END */ diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svotval.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svotval.h similarity index 92% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svotval.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svotval.h index 34ad7ca9f..a4683cd5f 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svotval.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svotval.h @@ -4,7 +4,7 @@ * * The FreeType OpenType validation service (specification). * - * Copyright (C) 2004-2020 by + * Copyright (C) 2004-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,8 @@ #ifndef SVOTVAL_H_ #define SVOTVAL_H_ -#include FT_OPENTYPE_VALIDATE_H -#include FT_INTERNAL_VALIDATE_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svpfr.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svpfr.h similarity index 93% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svpfr.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svpfr.h index 2dd075c5d..fd189c7de 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svpfr.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svpfr.h @@ -4,7 +4,7 @@ * * Internal PFR service functions (specification). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,8 @@ #ifndef SVPFR_H_ #define SVPFR_H_ -#include FT_PFR_H -#include FT_INTERNAL_SERVICE_H +#include +#include FT_BEGIN_HEADER @@ -56,7 +56,6 @@ FT_BEGIN_HEADER }; - /* */ FT_END_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svpostnm.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svpostnm.h similarity index 95% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svpostnm.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svpostnm.h index 86ab61138..2b8f6dfec 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svpostnm.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svpostnm.h @@ -4,7 +4,7 @@ * * The FreeType PostScript name services (specification). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,7 +19,7 @@ #ifndef SVPOSTNM_H_ #define SVPOSTNM_H_ -#include FT_INTERNAL_SERVICE_H +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svprop.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svprop.h similarity index 98% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svprop.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svprop.h index 8f755436a..932ce32e0 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svprop.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svprop.h @@ -4,7 +4,7 @@ * * The FreeType property service (specification). * - * Copyright (C) 2012-2020 by + * Copyright (C) 2012-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svpscmap.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svpscmap.h similarity index 97% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svpscmap.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svpscmap.h index 6c2ffe2e2..6e599f3aa 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svpscmap.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svpscmap.h @@ -4,7 +4,7 @@ * * The FreeType PostScript charmap service (specification). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,7 +19,7 @@ #ifndef SVPSCMAP_H_ #define SVPSCMAP_H_ -#include FT_INTERNAL_OBJECTS_H +#include FT_BEGIN_HEADER @@ -97,7 +97,7 @@ FT_BEGIN_HEADER (*PS_Unicodes_CharIndexFunc)( PS_Unicodes unicodes, FT_UInt32 unicode ); - typedef FT_UInt32 + typedef FT_UInt (*PS_Unicodes_CharNextFunc)( PS_Unicodes unicodes, FT_UInt32 *unicode ); diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svpsinfo.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svpsinfo.h similarity index 95% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svpsinfo.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svpsinfo.h index ade24dc2b..09c4cdccc 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svpsinfo.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svpsinfo.h @@ -4,7 +4,7 @@ * * The FreeType PostScript info service (specification). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,8 @@ #ifndef SVPSINFO_H_ #define SVPSINFO_H_ -#include FT_INTERNAL_SERVICE_H -#include FT_INTERNAL_TYPE1_TYPES_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svsfnt.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svsfnt.h similarity index 95% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svsfnt.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svsfnt.h index f3e81ca84..f98df2ef5 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svsfnt.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svsfnt.h @@ -4,7 +4,7 @@ * * The FreeType SFNT table loading service (specification). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,8 @@ #ifndef SVSFNT_H_ #define SVSFNT_H_ -#include FT_INTERNAL_SERVICE_H -#include FT_TRUETYPE_TABLES_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svttcmap.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svttcmap.h similarity index 95% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svttcmap.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svttcmap.h index fbb3115ed..5f9eb02d6 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svttcmap.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svttcmap.h @@ -4,7 +4,7 @@ * * The FreeType TrueType/sfnt cmap extra information service. * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * Masatake YAMATO, Redhat K.K., * David Turner, Robert Wilhelm, and Werner Lemberg. * @@ -22,8 +22,8 @@ #ifndef SVTTCMAP_H_ #define SVTTCMAP_H_ -#include FT_INTERNAL_SERVICE_H -#include FT_TRUETYPE_TABLES_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svtteng.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svtteng.h similarity index 90% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svtteng.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svtteng.h index 6218d9efe..ad577cb29 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svtteng.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svtteng.h @@ -4,7 +4,7 @@ * * The FreeType TrueType engine query service (specification). * - * Copyright (C) 2006-2020 by + * Copyright (C) 2006-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,8 @@ #ifndef SVTTENG_H_ #define SVTTENG_H_ -#include FT_INTERNAL_SERVICE_H -#include FT_MODULE_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svttglyf.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svttglyf.h similarity index 92% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svttglyf.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svttglyf.h index d9894e362..ca6fff744 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svttglyf.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svttglyf.h @@ -4,7 +4,7 @@ * * The FreeType TrueType glyph service. * - * Copyright (C) 2007-2020 by + * Copyright (C) 2007-2023 by * David Turner. * * This file is part of the FreeType project, and may only be used, @@ -18,8 +18,8 @@ #ifndef SVTTGLYF_H_ #define SVTTGLYF_H_ -#include FT_INTERNAL_SERVICE_H -#include FT_TRUETYPE_TABLES_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/services/svwinfnt.h b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svwinfnt.h similarity index 90% rename from src/font/freetype-2.10.2/include/freetype/internal/services/svwinfnt.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/services/svwinfnt.h index 377f73d45..002923f8c 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/services/svwinfnt.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/services/svwinfnt.h @@ -4,7 +4,7 @@ * * The FreeType Windows FNT/FONT service (specification). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,8 +19,8 @@ #ifndef SVWINFNT_H_ #define SVWINFNT_H_ -#include FT_INTERNAL_SERVICE_H -#include FT_WINFONTS_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/include/freetype/internal/sfnt.h b/3rdparty/freetype-2.13.2/include/freetype/internal/sfnt.h similarity index 73% rename from src/font/freetype-2.10.2/include/freetype/internal/sfnt.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/sfnt.h index b9c81a8f3..a2d4e15ba 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/sfnt.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/sfnt.h @@ -4,7 +4,7 @@ * * High-level 'sfnt' driver interface (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,10 +20,9 @@ #define SFNT_H_ -#include -#include FT_INTERNAL_DRIVER_H -#include FT_INTERNAL_TRUETYPE_TYPES_H -#include FT_INTERNAL_WOFF_TYPES_H +#include +#include +#include FT_BEGIN_HEADER @@ -312,6 +311,33 @@ FT_BEGIN_HEADER TT_SBit_MetricsRec *ametrics ); + /************************************************************************** + * + * @functype: + * TT_Load_Svg_Doc_Func + * + * @description: + * Scan the SVG document list to find the document containing the glyph + * that has the ID 'glyph*XXX*', where *XXX* is the value of + * `glyph_index` as a decimal integer. + * + * @inout: + * glyph :: + * The glyph slot from which pointers to the SVG document list is to be + * grabbed. The results are stored back in the slot. + * + * @input: + * glyph_index :: + * The index of the glyph that is to be looked up. + * + * @return: + * FreeType error code. 0 means success. + */ + typedef FT_Error + (*TT_Load_Svg_Doc_Func)( FT_GlyphSlot glyph, + FT_UInt glyph_index ); + + /************************************************************************** * * @functype: @@ -525,6 +551,170 @@ FT_BEGIN_HEADER FT_LayerIterator* iterator ); + /************************************************************************** + * + * @functype: + * TT_Get_Color_Glyph_Paint_Func + * + * @description: + * Find the root @FT_OpaquePaint object for a given glyph ID. + * + * @input: + * face :: + * The target face object. + * + * base_glyph :: + * The glyph index the colored glyph layers are associated with. + * + * @output: + * paint :: + * The root @FT_OpaquePaint object. + * + * @return: + * Value~1 if everything is OK. If no color glyph is found, or the root + * paint could not be retrieved, value~0 gets returned. In case of an + * error, value~0 is returned also. + */ + typedef FT_Bool + ( *TT_Get_Color_Glyph_Paint_Func )( TT_Face face, + FT_UInt base_glyph, + FT_Color_Root_Transform root_transform, + FT_OpaquePaint *paint ); + + + /************************************************************************** + * + * @functype: + * TT_Get_Color_Glyph_ClipBox_Func + * + * @description: + * Search for a 'COLR' v1 clip box for the specified `base_glyph` and + * fill the `clip_box` parameter with the 'COLR' v1 'ClipBox' information + * if one is found. + * + * @input: + * face :: + * A handle to the parent face object. + * + * base_glyph :: + * The glyph index for which to retrieve the clip box. + * + * @output: + * clip_box :: + * The clip box for the requested `base_glyph` if one is found. The + * clip box is computed taking scale and transformations configured on + * the @FT_Face into account. @FT_ClipBox contains @FT_Vector values + * in 26.6 format. + * + * @note: + * To retrieve the clip box in font units, reset scale to units-per-em + * and remove transforms configured using @FT_Set_Transform. + * + * @return: + * Value~1 if a ClipBox is found. If no clip box is found or an + * error occured, value~0 is returned. + */ + typedef FT_Bool + ( *TT_Get_Color_Glyph_ClipBox_Func )( TT_Face face, + FT_UInt base_glyph, + FT_ClipBox* clip_box ); + + + /************************************************************************** + * + * @functype: + * TT_Get_Paint_Layers_Func + * + * @description: + * Access the layers of a `PaintColrLayers` table. + * + * @input: + * face :: + * The target face object. + * + * @inout: + * iterator :: + * The @FT_LayerIterator from an @FT_PaintColrLayers object, for which + * the layers are to be retrieved. The internal state of the iterator + * is incremented after one call to this function for retrieving one + * layer. + * + * @output: + * paint :: + * The root @FT_OpaquePaint object referencing the actual paint table. + * + * @return: + * Value~1 if everything is OK. Value~0 gets returned when the paint + * object can not be retrieved or any other error occurs. + */ + typedef FT_Bool + ( *TT_Get_Paint_Layers_Func )( TT_Face face, + FT_LayerIterator* iterator, + FT_OpaquePaint *paint ); + + + /************************************************************************** + * + * @functype: + * TT_Get_Colorline_Stops_Func + * + * @description: + * Get the gradient and solid fill information for a given glyph. + * + * @input: + * face :: + * The target face object. + * + * @inout: + * iterator :: + * An @FT_ColorStopIterator object. For the first call you should set + * `iterator->p` to `NULL`. For all following calls, simply use the + * same object again. + * + * @output: + * color_stop :: + * Color index and alpha value for the retrieved color stop. + * + * @return: + * Value~1 if everything is OK. If there are no more color stops, + * value~0 gets returned. In case of an error, value~0 is returned + * also. + */ + typedef FT_Bool + ( *TT_Get_Colorline_Stops_Func )( TT_Face face, + FT_ColorStop *color_stop, + FT_ColorStopIterator* iterator ); + + + /************************************************************************** + * + * @functype: + * TT_Get_Paint_Func + * + * @description: + * Get the paint details for a given @FT_OpaquePaint object. + * + * @input: + * face :: + * The target face object. + * + * opaque_paint :: + * The @FT_OpaquePaint object. + * + * @output: + * paint :: + * An @FT_COLR_Paint object holding the details on `opaque_paint`. + * + * @return: + * Value~1 if everything is OK. Value~0 if no details can be found for + * this paint or any other error occured. + */ + typedef FT_Bool + ( *TT_Get_Paint_Func )( TT_Face face, + FT_OpaquePaint opaque_paint, + FT_COLR_Paint *paint ); + + /************************************************************************** * * @functype: @@ -710,73 +900,83 @@ FT_BEGIN_HEADER */ typedef struct SFNT_Interface_ { - TT_Loader_GotoTableFunc goto_table; + TT_Loader_GotoTableFunc goto_table; - TT_Init_Face_Func init_face; - TT_Load_Face_Func load_face; - TT_Done_Face_Func done_face; - FT_Module_Requester get_interface; + TT_Init_Face_Func init_face; + TT_Load_Face_Func load_face; + TT_Done_Face_Func done_face; + FT_Module_Requester get_interface; - TT_Load_Any_Func load_any; + TT_Load_Any_Func load_any; /* these functions are called by `load_face' but they can also */ /* be called from external modules, if there is a need to do so */ - TT_Load_Table_Func load_head; - TT_Load_Metrics_Func load_hhea; - TT_Load_Table_Func load_cmap; - TT_Load_Table_Func load_maxp; - TT_Load_Table_Func load_os2; - TT_Load_Table_Func load_post; + TT_Load_Table_Func load_head; + TT_Load_Metrics_Func load_hhea; + TT_Load_Table_Func load_cmap; + TT_Load_Table_Func load_maxp; + TT_Load_Table_Func load_os2; + TT_Load_Table_Func load_post; - TT_Load_Table_Func load_name; - TT_Free_Table_Func free_name; + TT_Load_Table_Func load_name; + TT_Free_Table_Func free_name; /* this field was called `load_kerning' up to version 2.1.10 */ - TT_Load_Table_Func load_kern; + TT_Load_Table_Func load_kern; - TT_Load_Table_Func load_gasp; - TT_Load_Table_Func load_pclt; + TT_Load_Table_Func load_gasp; + TT_Load_Table_Func load_pclt; /* see `ttload.h'; this field was called `load_bitmap_header' up to */ /* version 2.1.10 */ - TT_Load_Table_Func load_bhed; + TT_Load_Table_Func load_bhed; - TT_Load_SBit_Image_Func load_sbit_image; + TT_Load_SBit_Image_Func load_sbit_image; /* see `ttpost.h' */ - TT_Get_PS_Name_Func get_psname; - TT_Free_Table_Func free_psnames; + TT_Get_PS_Name_Func get_psname; + TT_Free_Table_Func free_psnames; /* starting here, the structure differs from version 2.1.7 */ /* this field was introduced in version 2.1.8, named `get_psname' */ - TT_Face_GetKerningFunc get_kerning; + TT_Face_GetKerningFunc get_kerning; /* new elements introduced after version 2.1.10 */ /* load the font directory, i.e., the offset table and */ /* the table directory */ - TT_Load_Table_Func load_font_dir; - TT_Load_Metrics_Func load_hmtx; + TT_Load_Table_Func load_font_dir; + TT_Load_Metrics_Func load_hmtx; - TT_Load_Table_Func load_eblc; - TT_Free_Table_Func free_eblc; + TT_Load_Table_Func load_eblc; + TT_Free_Table_Func free_eblc; TT_Set_SBit_Strike_Func set_sbit_strike; TT_Load_Strike_Metrics_Func load_strike_metrics; - TT_Load_Table_Func load_cpal; - TT_Load_Table_Func load_colr; - TT_Free_Table_Func free_cpal; - TT_Free_Table_Func free_colr; - TT_Set_Palette_Func set_palette; - TT_Get_Colr_Layer_Func get_colr_layer; - TT_Blend_Colr_Func colr_blend; - - TT_Get_Metrics_Func get_metrics; - - TT_Get_Name_Func get_name; - TT_Get_Name_ID_Func get_name_id; + TT_Load_Table_Func load_cpal; + TT_Load_Table_Func load_colr; + TT_Free_Table_Func free_cpal; + TT_Free_Table_Func free_colr; + TT_Set_Palette_Func set_palette; + TT_Get_Colr_Layer_Func get_colr_layer; + TT_Get_Color_Glyph_Paint_Func get_colr_glyph_paint; + TT_Get_Color_Glyph_ClipBox_Func get_color_glyph_clipbox; + TT_Get_Paint_Layers_Func get_paint_layers; + TT_Get_Colorline_Stops_Func get_colorline_stops; + TT_Get_Paint_Func get_paint; + TT_Blend_Colr_Func colr_blend; + + TT_Get_Metrics_Func get_metrics; + + TT_Get_Name_Func get_name; + TT_Get_Name_ID_Func get_name_id; + + /* OpenType SVG Support */ + TT_Load_Table_Func load_svg; + TT_Free_Table_Func free_svg; + TT_Load_Svg_Doc_Func load_svg_doc; } SFNT_Interface; @@ -821,10 +1021,18 @@ FT_BEGIN_HEADER free_colr_, \ set_palette_, \ get_colr_layer_, \ + get_colr_glyph_paint_, \ + get_color_glyph_clipbox, \ + get_paint_layers_, \ + get_colorline_stops_, \ + get_paint_, \ colr_blend_, \ get_metrics_, \ get_name_, \ - get_name_id_ ) \ + get_name_id_, \ + load_svg_, \ + free_svg_, \ + load_svg_doc_ ) \ static const SFNT_Interface class_ = \ { \ goto_table_, \ @@ -861,10 +1069,18 @@ FT_BEGIN_HEADER free_colr_, \ set_palette_, \ get_colr_layer_, \ + get_colr_glyph_paint_, \ + get_color_glyph_clipbox, \ + get_paint_layers_, \ + get_colorline_stops_, \ + get_paint_, \ colr_blend_, \ get_metrics_, \ get_name_, \ - get_name_id_ \ + get_name_id_, \ + load_svg_, \ + free_svg_, \ + load_svg_doc_ \ }; diff --git a/3rdparty/freetype-2.13.2/include/freetype/internal/svginterface.h b/3rdparty/freetype-2.13.2/include/freetype/internal/svginterface.h new file mode 100644 index 000000000..f464b2c05 --- /dev/null +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/svginterface.h @@ -0,0 +1,46 @@ +/**************************************************************************** + * + * svginterface.h + * + * Interface of ot-svg module (specification only). + * + * Copyright (C) 2022-2023 by + * David Turner, Robert Wilhelm, Werner Lemberg, and Moazin Khatti. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + +#ifndef SVGINTERFACE_H_ +#define SVGINTERFACE_H_ + +#include +#include + + +FT_BEGIN_HEADER + + typedef FT_Error + (*Preset_Bitmap_Func)( FT_Module module, + FT_GlyphSlot slot, + FT_Bool cache ); + + typedef struct SVG_Interface_ + { + Preset_Bitmap_Func preset_slot; + + } SVG_Interface; + + typedef SVG_Interface* SVG_Service; + +FT_END_HEADER + +#endif /* SVGINTERFACE_H_ */ + + +/* END */ diff --git a/src/font/freetype-2.10.2/include/freetype/internal/t1types.h b/3rdparty/freetype-2.13.2/include/freetype/internal/t1types.h similarity index 91% rename from src/font/freetype-2.10.2/include/freetype/internal/t1types.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/t1types.h index 799c2939f..b9c94398f 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/t1types.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/t1types.h @@ -5,7 +5,7 @@ * Basic Type1/Type2 type definitions and interface (specification * only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -21,12 +21,11 @@ #define T1TYPES_H_ -#include -#include FT_TYPE1_TABLES_H -#include FT_INTERNAL_POSTSCRIPT_HINTS_H -#include FT_INTERNAL_SERVICE_H -#include FT_INTERNAL_HASH_H -#include FT_SERVICE_POSTSCRIPT_CMAPS_H +#include +#include +#include +#include +#include FT_BEGIN_HEADER @@ -173,8 +172,8 @@ FT_BEGIN_HEADER { FT_Bool IsCIDFont; FT_BBox FontBBox; - FT_Fixed Ascender; - FT_Fixed Descender; + FT_Fixed Ascender; /* optional, mind the zero */ + FT_Fixed Descender; /* optional, mind the zero */ AFM_TrackKern TrackKerns; /* free if non-NULL */ FT_UInt NumTrackKern; AFM_KernPair KernPairs; /* free if non-NULL */ @@ -202,30 +201,30 @@ FT_BEGIN_HEADER typedef struct T1_FaceRec_ { - FT_FaceRec root; - T1_FontRec type1; - const void* psnames; - const void* psaux; - const void* afm_data; - FT_CharMapRec charmaprecs[2]; - FT_CharMap charmaps[2]; + FT_FaceRec root; + T1_FontRec type1; + const void* psnames; + const void* psaux; + const void* afm_data; + FT_CharMapRec charmaprecs[2]; + FT_CharMap charmaps[2]; /* support for Multiple Masters fonts */ - PS_Blend blend; + PS_Blend blend; /* undocumented, optional: indices of subroutines that express */ /* the NormalizeDesignVector and the ConvertDesignVector procedure, */ /* respectively, as Type 2 charstrings; -1 if keywords not present */ - FT_Int ndv_idx; - FT_Int cdv_idx; + FT_Int ndv_idx; + FT_Int cdv_idx; /* undocumented, optional: has the same meaning as len_buildchar */ /* for Type 2 fonts; manipulated by othersubrs 19, 24, and 25 */ - FT_UInt len_buildchar; - FT_Long* buildchar; + FT_UInt len_buildchar; + FT_Long* buildchar; /* since version 2.1 - interface to PostScript hinter */ - const void* pshinter; + const void* pshinter; } T1_FaceRec; diff --git a/src/font/freetype-2.10.2/include/freetype/internal/tttypes.h b/3rdparty/freetype-2.13.2/include/freetype/internal/tttypes.h similarity index 95% rename from src/font/freetype-2.10.2/include/freetype/internal/tttypes.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/tttypes.h index 1bddf102b..b9788c783 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/tttypes.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/tttypes.h @@ -5,7 +5,7 @@ * Basic SFNT/TrueType type definitions and interface (specification * only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -21,13 +21,12 @@ #define TTTYPES_H_ -#include -#include FT_TRUETYPE_TABLES_H -#include FT_INTERNAL_OBJECTS_H -#include FT_COLOR_H +#include +#include +#include #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT -#include FT_MULTIPLE_MASTERS_H +#include #endif @@ -780,13 +779,15 @@ FT_BEGIN_HEADER /************************************************************************** * * @struct: - * TT_Post_20Rec + * TT_Post_NamesRec * * @description: - * Postscript names sub-table, format 2.0. Stores the PS name of each - * glyph in the font face. + * Postscript names table, either format 2.0 or 2.5. * * @fields: + * loaded :: + * A flag to indicate whether the PS names are loaded. + * * num_glyphs :: * The number of named glyphs in the table. * @@ -799,68 +800,13 @@ FT_BEGIN_HEADER * glyph_names :: * The PS names not in Mac Encoding. */ - typedef struct TT_Post_20Rec_ + typedef struct TT_Post_NamesRec_ { + FT_Bool loaded; FT_UShort num_glyphs; FT_UShort num_names; FT_UShort* glyph_indices; - FT_Char** glyph_names; - - } TT_Post_20Rec, *TT_Post_20; - - - /************************************************************************** - * - * @struct: - * TT_Post_25Rec - * - * @description: - * Postscript names sub-table, format 2.5. Stores the PS name of each - * glyph in the font face. - * - * @fields: - * num_glyphs :: - * The number of glyphs in the table. - * - * offsets :: - * An array of signed offsets in a normal Mac Postscript name encoding. - */ - typedef struct TT_Post_25_ - { - FT_UShort num_glyphs; - FT_Char* offsets; - - } TT_Post_25Rec, *TT_Post_25; - - - /************************************************************************** - * - * @struct: - * TT_Post_NamesRec - * - * @description: - * Postscript names table, either format 2.0 or 2.5. - * - * @fields: - * loaded :: - * A flag to indicate whether the PS names are loaded. - * - * format_20 :: - * The sub-table used for format 2.0. - * - * format_25 :: - * The sub-table used for format 2.5. - */ - typedef struct TT_Post_NamesRec_ - { - FT_Bool loaded; - - union - { - TT_Post_20Rec format_20; - TT_Post_25Rec format_25; - - } names; + FT_Byte** glyph_names; } TT_Post_NamesRec, *TT_Post_Names; @@ -1254,12 +1200,16 @@ FT_BEGIN_HEADER * mm :: * A pointer to the Multiple Masters service. * - * var :: - * A pointer to the Metrics Variations service. + * tt_var :: + * A pointer to the Metrics Variations service for the "truetype" + * driver. + * + * face_var :: + * A pointer to the Metrics Variations service for this `TT_Face`'s + * driver. * - * hdmx :: - * The face's horizontal device metrics ('hdmx' table). This table is - * optional in TrueType/OpenType fonts. + * psaux :: + * A pointer to the PostScript Auxiliary service. * * gasp :: * The grid-fitting and scaling properties table ('gasp'). This table @@ -1365,6 +1315,12 @@ FT_BEGIN_HEADER * var_postscript_prefix_len :: * The length of the `var_postscript_prefix` string. * + * var_default_named_instance :: + * The index of the default named instance. + * + * non_var_style_name :: + * The non-variation style name, used as a backup. + * * horz_metrics_size :: * The size of the 'hmtx' table. * @@ -1373,7 +1329,7 @@ FT_BEGIN_HEADER * * num_locations :: * The number of glyph locations in this TrueType file. This should be - * identical to the number of glyphs. Ignored for Type 2 fonts. + * one more than the number of glyphs. Ignored for Type 2 fonts. * * glyph_locations :: * An array of longs. These are offsets to glyph data within the @@ -1391,8 +1347,8 @@ FT_BEGIN_HEADER * hdmx_record_size :: * The size of a single hdmx record. * - * hdmx_record_sizes :: - * An array holding the ppem sizes available in the 'hdmx' table. + * hdmx_records :: + * A array of pointers to the 'hdmx' table records sorted by ppem. * * sbit_table :: * A pointer to the font's embedded bitmap location table. @@ -1411,14 +1367,6 @@ FT_BEGIN_HEADER * A mapping between the strike indices exposed by the API and the * indices used in the font's sbit table. * - * cpal :: - * A pointer to data related to the 'CPAL' table. `NULL` if the table - * is not available. - * - * colr :: - * A pointer to data related to the 'COLR' table. `NULL` if the table - * is not available. - * * kern_table :: * A pointer to the 'kern' table. * @@ -1446,19 +1394,23 @@ FT_BEGIN_HEADER * vert_metrics_offset :: * The file offset of the 'vmtx' table. * - * sph_found_func_flags :: - * Flags identifying special bytecode functions (used by the v38 - * implementation of the bytecode interpreter). - * - * sph_compatibility_mode :: - * This flag is set if we are in ClearType backward compatibility mode - * (used by the v38 implementation of the bytecode interpreter). - * * ebdt_start :: * The file offset of the sbit data table (CBDT, bdat, etc.). * * ebdt_size :: * The size of the sbit data table. + * + * cpal :: + * A pointer to data related to the 'CPAL' table. `NULL` if the table + * is not available. + * + * colr :: + * A pointer to data related to the 'COLR' table. `NULL` if the table + * is not available. + * + * svg :: + * A pointer to data related to the 'SVG' table. `NULL` if the table + * is not available. */ typedef struct TT_FaceRec_ { @@ -1509,8 +1461,14 @@ FT_BEGIN_HEADER void* mm; /* a typeless pointer to the FT_Service_MetricsVariationsRec table */ - /* used to handle the HVAR, VVAR, and MVAR OpenType tables */ - void* var; + /* used to handle the HVAR, VVAR, and MVAR OpenType tables by the */ + /* "truetype" driver */ + void* tt_var; + + /* a typeless pointer to the FT_Service_MetricsVariationsRec table */ + /* used to handle the HVAR, VVAR, and MVAR OpenType tables by this */ + /* TT_Face's driver */ + void* face_var; /* since 2.13.1 */ #endif /* a typeless pointer to the PostScript Aux service */ @@ -1592,6 +1550,9 @@ FT_BEGIN_HEADER const char* var_postscript_prefix; /* since 2.7.2 */ FT_UInt var_postscript_prefix_len; /* since 2.7.2 */ + FT_UInt var_default_named_instance; /* since 2.13.1 */ + + const char* non_var_style_name; /* since 2.13.1 */ #endif /* since version 2.2 */ @@ -1599,14 +1560,14 @@ FT_BEGIN_HEADER FT_ULong horz_metrics_size; FT_ULong vert_metrics_size; - FT_ULong num_locations; /* in broken TTF, gid > 0xFFFF */ + FT_ULong num_locations; /* up to 0xFFFF + 1 */ FT_Byte* glyph_locations; FT_Byte* hdmx_table; FT_ULong hdmx_table_size; FT_UInt hdmx_record_count; FT_ULong hdmx_record_size; - FT_Byte* hdmx_record_sizes; + FT_Byte** hdmx_records; FT_Byte* sbit_table; FT_ULong sbit_table_size; @@ -1628,13 +1589,6 @@ FT_BEGIN_HEADER FT_ULong horz_metrics_offset; FT_ULong vert_metrics_offset; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - /* since 2.4.12 */ - FT_ULong sph_found_func_flags; /* special functions found */ - /* for this face */ - FT_Bool sph_compatibility_mode; -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - #ifdef TT_CONFIG_OPTION_EMBEDDED_BITMAPS /* since 2.7 */ FT_ULong ebdt_start; /* either `CBDT', `EBDT', or `bdat' */ @@ -1645,6 +1599,9 @@ FT_BEGIN_HEADER void* cpal; void* colr; + /* since 2.12 */ + void* svg; + } TT_FaceRec; @@ -1735,7 +1692,7 @@ FT_BEGIN_HEADER FT_UInt glyph_index; FT_Stream stream; - FT_Int byte_len; + FT_UInt byte_len; FT_Short n_contours; FT_BBox bbox; @@ -1770,6 +1727,9 @@ FT_BEGIN_HEADER /* since version 2.6.2 */ FT_ListRec composites; + /* since version 2.11.2 */ + FT_Byte* widthp; + } TT_LoaderRec; diff --git a/src/font/freetype-2.10.2/include/freetype/internal/wofftypes.h b/3rdparty/freetype-2.13.2/include/freetype/internal/wofftypes.h similarity index 97% rename from src/font/freetype-2.10.2/include/freetype/internal/wofftypes.h rename to 3rdparty/freetype-2.13.2/include/freetype/internal/wofftypes.h index 26159b9d3..0c1d8eeaf 100644 --- a/src/font/freetype-2.10.2/include/freetype/internal/wofftypes.h +++ b/3rdparty/freetype-2.13.2/include/freetype/internal/wofftypes.h @@ -5,7 +5,7 @@ * Basic WOFF/WOFF2 type definitions and interface (specification * only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -21,9 +21,8 @@ #define WOFFTYPES_H_ -#include -#include FT_TRUETYPE_TABLES_H -#include FT_INTERNAL_OBJECTS_H +#include +#include FT_BEGIN_HEADER @@ -93,7 +92,7 @@ FT_BEGIN_HEADER */ typedef struct WOFF_TableRec_ { - FT_ULong Tag; /* table ID */ + FT_Tag Tag; /* table ID */ FT_ULong Offset; /* table file offset */ FT_ULong CompLength; /* compressed table length */ FT_ULong OrigLength; /* uncompressed table length */ @@ -192,7 +191,7 @@ FT_BEGIN_HEADER typedef struct WOFF2_TableRec_ { FT_Byte FlagByte; /* table type and flags */ - FT_ULong Tag; /* table file offset */ + FT_Tag Tag; /* table file offset */ FT_ULong dst_length; /* uncompressed table length */ FT_ULong TransformLength; /* transformed length */ diff --git a/3rdparty/freetype-2.13.2/include/freetype/otsvg.h b/3rdparty/freetype-2.13.2/include/freetype/otsvg.h new file mode 100644 index 000000000..bfe9a6ab7 --- /dev/null +++ b/3rdparty/freetype-2.13.2/include/freetype/otsvg.h @@ -0,0 +1,336 @@ +/**************************************************************************** + * + * otsvg.h + * + * Interface for OT-SVG support related things (specification). + * + * Copyright (C) 2022-2023 by + * David Turner, Robert Wilhelm, Werner Lemberg, and Moazin Khatti. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + +#ifndef OTSVG_H_ +#define OTSVG_H_ + +#include + +#ifdef FREETYPE_H +#error "freetype.h of FreeType 1 has been loaded!" +#error "Please fix the directory search order for header files" +#error "so that freetype.h of FreeType 2 is found first." +#endif + + +FT_BEGIN_HEADER + + + /************************************************************************** + * + * @section: + * svg_fonts + * + * @title: + * OpenType SVG Fonts + * + * @abstract: + * OT-SVG API between FreeType and an external SVG rendering library. + * + * @description: + * This section describes the four hooks necessary to render SVG + * 'documents' that are contained in an OpenType font's 'SVG~' table. + * + * For more information on the implementation, see our standard hooks + * based on 'librsvg' in the [FreeType Demo + * Programs](https://gitlab.freedesktop.org/freetype/freetype-demos) + * repository. + * + */ + + + /************************************************************************** + * + * @functype: + * SVG_Lib_Init_Func + * + * @description: + * A callback that is called when the first OT-SVG glyph is rendered in + * the lifetime of an @FT_Library object. In a typical implementation, + * one would want to allocate a structure and point the `data_pointer` + * to it and perform any library initializations that might be needed. + * + * @inout: + * data_pointer :: + * The SVG rendering module stores a pointer variable that can be used + * by clients to store any data that needs to be shared across + * different hooks. `data_pointer` is essentially a pointer to that + * pointer such that it can be written to as well as read from. + * + * @return: + * FreeType error code. 0 means success. + * + * @since: + * 2.12 + */ + typedef FT_Error + (*SVG_Lib_Init_Func)( FT_Pointer *data_pointer ); + + + /************************************************************************** + * + * @functype: + * SVG_Lib_Free_Func + * + * @description: + * A callback that is called when the `ot-svg` module is being freed. + * It is only called if the init hook was called earlier. This means + * that neither the init nor the free hook is called if no OT-SVG glyph + * is rendered. + * + * In a typical implementation, one would want to free any state + * structure that was allocated in the init hook and perform any + * library-related closure that might be needed. + * + * @inout: + * data_pointer :: + * The SVG rendering module stores a pointer variable that can be used + * by clients to store any data that needs to be shared across + * different hooks. `data_pointer` is essentially a pointer to that + * pointer such that it can be written to as well as read from. + * + * @since: + * 2.12 + */ + typedef void + (*SVG_Lib_Free_Func)( FT_Pointer *data_pointer ); + + + /************************************************************************** + * + * @functype: + * SVG_Lib_Render_Func + * + * @description: + * A callback that is called to render an OT-SVG glyph. This callback + * hook is called right after the preset hook @SVG_Lib_Preset_Slot_Func + * has been called with `cache` set to `TRUE`. The data necessary to + * render is available through the handle @FT_SVG_Document, which is set + * in the `other` field of @FT_GlyphSlotRec. + * + * The render hook is expected to render the SVG glyph to the bitmap + * buffer that is allocated already at `slot->bitmap.buffer`. It also + * sets the `num_grays` value as well as `slot->format`. + * + * @input: + * slot :: + * The slot to render. + * + * @inout: + * data_pointer :: + * The SVG rendering module stores a pointer variable that can be used + * by clients to store any data that needs to be shared across + * different hooks. `data_pointer` is essentially a pointer to that + * pointer such that it can be written to as well as read from. + * + * @return: + * FreeType error code. 0 means success. + * + * @since: + * 2.12 + */ + typedef FT_Error + (*SVG_Lib_Render_Func)( FT_GlyphSlot slot, + FT_Pointer *data_pointer ); + + + /************************************************************************** + * + * @functype: + * SVG_Lib_Preset_Slot_Func + * + * @description: + * A callback that is called to preset the glyph slot. It is called from + * two places. + * + * 1. When `FT_Load_Glyph` needs to preset the glyph slot. + * + * 2. Right before the `svg` module calls the render callback hook. + * + * When it is the former, the argument `cache` is set to `FALSE`. When + * it is the latter, the argument `cache` is set to `TRUE`. This + * distinction has been made because many calculations that are necessary + * for presetting a glyph slot are the same needed later for the render + * callback hook. Thus, if `cache` is `TRUE`, the hook can _cache_ those + * calculations in a memory block referenced by the state pointer. + * + * This hook is expected to preset the slot by setting parameters such as + * `bitmap_left`, `bitmap_top`, `width`, `rows`, `pitch`, and + * `pixel_mode`. It is also expected to set all the metrics for the slot + * including the vertical advance if it is not already set. Typically, + * fonts have horizontal advances but not vertical ones. If those are + * available, they had already been set, otherwise they have to be + * estimated and set manually. The hook must take into account the + * transformations that have been set, and translate the transformation + * matrices into the SVG coordinate system, as the original matrix is + * intended for the TTF/CFF coordinate system. + * + * @input: + * slot :: + * The glyph slot that has the SVG document loaded. + * + * cache :: + * See description. + * + * @inout: + * data_pointer :: + * The SVG rendering module stores a pointer variable that can be used + * by clients to store any data that needs to be shared across + * different hooks. `data_pointer` is essentially a pointer to that + * pointer such that it can be written to as well as read from. + * + * @return: + * FreeType error code. 0 means success. + * + * @since: + * 2.12 + */ + typedef FT_Error + (*SVG_Lib_Preset_Slot_Func)( FT_GlyphSlot slot, + FT_Bool cache, + FT_Pointer *state ); + + + /************************************************************************** + * + * @struct: + * SVG_RendererHooks + * + * @description: + * A structure that stores the four hooks needed to render OT-SVG glyphs + * properly. The structure is publicly used to set the hooks via the + * @svg-hooks driver property. + * + * The behavior of each hook is described in its documentation. One + * thing to note is that the preset hook and the render hook often need + * to do the same operations; therefore, it's better to cache the + * intermediate data in a state structure to avoid calculating it twice. + * For example, in the preset hook one can draw the glyph on a recorder + * surface and later create a bitmap surface from it in the render hook. + * + * All four hooks must be non-NULL. + * + * @fields: + * init_svg :: + * The initialization hook. + * + * free_svg :: + * The cleanup hook. + * + * render_hook :: + * The render hook. + * + * preset_slot :: + * The preset hook. + * + * @since: + * 2.12 + */ + typedef struct SVG_RendererHooks_ + { + SVG_Lib_Init_Func init_svg; + SVG_Lib_Free_Func free_svg; + SVG_Lib_Render_Func render_svg; + + SVG_Lib_Preset_Slot_Func preset_slot; + + } SVG_RendererHooks; + + + /************************************************************************** + * + * @struct: + * FT_SVG_DocumentRec + * + * @description: + * A structure that models one SVG document. + * + * @fields: + * svg_document :: + * A pointer to the SVG document. + * + * svg_document_length :: + * The length of `svg_document`. + * + * metrics :: + * A metrics object storing the size information. + * + * units_per_EM :: + * The size of the EM square. + * + * start_glyph_id :: + * The first glyph ID in the glyph range covered by this document. + * + * end_glyph_id :: + * The last glyph ID in the glyph range covered by this document. + * + * transform :: + * A 2x2 transformation matrix to apply to the glyph while rendering + * it. + * + * delta :: + * The translation to apply to the glyph while rendering. + * + * @note: + * When an @FT_GlyphSlot object `slot` is passed down to a renderer, the + * renderer can only access the `metrics` and `units_per_EM` fields via + * `slot->face`. However, when @FT_Glyph_To_Bitmap sets up a dummy + * object, it has no way to set a `face` object. Thus, metrics + * information and `units_per_EM` (which is necessary for OT-SVG) has to + * be stored separately. + * + * @since: + * 2.12 + */ + typedef struct FT_SVG_DocumentRec_ + { + FT_Byte* svg_document; + FT_ULong svg_document_length; + + FT_Size_Metrics metrics; + FT_UShort units_per_EM; + + FT_UShort start_glyph_id; + FT_UShort end_glyph_id; + + FT_Matrix transform; + FT_Vector delta; + + } FT_SVG_DocumentRec; + + + /************************************************************************** + * + * @type: + * FT_SVG_Document + * + * @description: + * A handle to an @FT_SVG_DocumentRec object. + * + * @since: + * 2.12 + */ + typedef struct FT_SVG_DocumentRec_* FT_SVG_Document; + + +FT_END_HEADER + +#endif /* OTSVG_H_ */ + + +/* END */ diff --git a/src/font/freetype-2.10.2/include/freetype/t1tables.h b/3rdparty/freetype-2.13.2/include/freetype/t1tables.h similarity index 81% rename from src/font/freetype-2.10.2/include/freetype/t1tables.h rename to 3rdparty/freetype-2.13.2/include/freetype/t1tables.h index 522d6ae6a..1aecfbbd9 100644 --- a/src/font/freetype-2.10.2/include/freetype/t1tables.h +++ b/3rdparty/freetype-2.13.2/include/freetype/t1tables.h @@ -5,7 +5,7 @@ * Basic Type 1/Type 2 tables definitions and interface (specification * only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -21,8 +21,7 @@ #define T1TABLES_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" @@ -361,7 +360,7 @@ FT_BEGIN_HEADER FT_UInt num_subrs; FT_ULong subrmap_offset; - FT_Int sd_bytes; + FT_UInt sd_bytes; } CID_FaceDictRec; @@ -416,11 +415,11 @@ FT_BEGIN_HEADER FT_ULong xuid[16]; FT_ULong cidmap_offset; - FT_Int fd_bytes; - FT_Int gd_bytes; + FT_UInt fd_bytes; + FT_UInt gd_bytes; FT_ULong cid_count; - FT_Int num_dicts; + FT_UInt num_dicts; CID_FaceDict font_dicts; FT_ULong data_offset; @@ -454,22 +453,22 @@ FT_BEGIN_HEADER /************************************************************************** * * @function: - * FT_Has_PS_Glyph_Names + * FT_Has_PS_Glyph_Names * * @description: - * Return true if a given face provides reliable PostScript glyph names. - * This is similar to using the @FT_HAS_GLYPH_NAMES macro, except that - * certain fonts (mostly TrueType) contain incorrect glyph name tables. + * Return true if a given face provides reliable PostScript glyph names. + * This is similar to using the @FT_HAS_GLYPH_NAMES macro, except that + * certain fonts (mostly TrueType) contain incorrect glyph name tables. * - * When this function returns true, the caller is sure that the glyph - * names returned by @FT_Get_Glyph_Name are reliable. + * When this function returns true, the caller is sure that the glyph + * names returned by @FT_Get_Glyph_Name are reliable. * * @input: - * face :: - * face handle + * face :: + * face handle * * @return: - * Boolean. True if glyph names are reliable. + * Boolean. True if glyph names are reliable. * */ FT_EXPORT( FT_Int ) @@ -479,30 +478,40 @@ FT_BEGIN_HEADER /************************************************************************** * * @function: - * FT_Get_PS_Font_Info + * FT_Get_PS_Font_Info * * @description: - * Retrieve the @PS_FontInfoRec structure corresponding to a given - * PostScript font. + * Retrieve the @PS_FontInfoRec structure corresponding to a given + * PostScript font. * * @input: - * face :: - * PostScript face handle. + * face :: + * PostScript face handle. * * @output: - * afont_info :: - * Output font info structure pointer. + * afont_info :: + * A pointer to a @PS_FontInfoRec object. * * @return: - * FreeType error code. 0~means success. + * FreeType error code. 0~means success. * * @note: - * String pointers within the @PS_FontInfoRec structure are owned by the - * face and don't need to be freed by the caller. Missing entries in - * the font's FontInfo dictionary are represented by `NULL` pointers. + * String pointers within the @PS_FontInfoRec structure are owned by the + * face and don't need to be freed by the caller. Missing entries in the + * font's FontInfo dictionary are represented by `NULL` pointers. + * + * The following font formats support this feature: 'Type~1', 'Type~42', + * 'CFF', 'CID~Type~1'. For other font formats this function returns the + * `FT_Err_Invalid_Argument` error code. * - * If the font's format is not PostScript-based, this function will - * return the `FT_Err_Invalid_Argument` error code. + * @example: + * ``` + * PS_FontInfoRec font_info; + * + * + * error = FT_Get_PS_Font_Info( face, &font_info ); + * ... + * ``` * */ FT_EXPORT( FT_Error ) @@ -513,29 +522,39 @@ FT_BEGIN_HEADER /************************************************************************** * * @function: - * FT_Get_PS_Font_Private + * FT_Get_PS_Font_Private * * @description: - * Retrieve the @PS_PrivateRec structure corresponding to a given - * PostScript font. + * Retrieve the @PS_PrivateRec structure corresponding to a given + * PostScript font. * * @input: - * face :: - * PostScript face handle. + * face :: + * PostScript face handle. * * @output: - * afont_private :: - * Output private dictionary structure pointer. + * afont_private :: + * A pointer to a @PS_PrivateRec object. * * @return: - * FreeType error code. 0~means success. + * FreeType error code. 0~means success. * * @note: - * The string pointers within the @PS_PrivateRec structure are owned by - * the face and don't need to be freed by the caller. + * The string pointers within the @PS_PrivateRec structure are owned by + * the face and don't need to be freed by the caller. * - * If the font's format is not PostScript-based, this function returns - * the `FT_Err_Invalid_Argument` error code. + * Only the 'Type~1' font format supports this feature. For other font + * formats this function returns the `FT_Err_Invalid_Argument` error + * code. + * + * @example: + * ``` + * PS_PrivateRec font_private; + * + * + * error = FT_Get_PS_Font_Private( face, &font_private ); + * ... + * ``` * */ FT_EXPORT( FT_Error ) @@ -694,67 +713,67 @@ FT_BEGIN_HEADER /************************************************************************** * * @function: - * FT_Get_PS_Font_Value + * FT_Get_PS_Font_Value * * @description: - * Retrieve the value for the supplied key from a PostScript font. + * Retrieve the value for the supplied key from a PostScript font. * * @input: - * face :: - * PostScript face handle. + * face :: + * PostScript face handle. * - * key :: - * An enumeration value representing the dictionary key to retrieve. + * key :: + * An enumeration value representing the dictionary key to retrieve. * - * idx :: - * For array values, this specifies the index to be returned. + * idx :: + * For array values, this specifies the index to be returned. * - * value :: - * A pointer to memory into which to write the value. + * value :: + * A pointer to memory into which to write the value. * - * valen_len :: - * The size, in bytes, of the memory supplied for the value. + * valen_len :: + * The size, in bytes, of the memory supplied for the value. * * @output: - * value :: - * The value matching the above key, if it exists. + * value :: + * The value matching the above key, if it exists. * * @return: - * The amount of memory (in bytes) required to hold the requested value - * (if it exists, -1 otherwise). + * The amount of memory (in bytes) required to hold the requested value + * (if it exists, -1 otherwise). * * @note: - * The values returned are not pointers into the internal structures of - * the face, but are 'fresh' copies, so that the memory containing them - * belongs to the calling application. This also enforces the - * 'read-only' nature of these values, i.e., this function cannot be - * used to manipulate the face. + * The values returned are not pointers into the internal structures of + * the face, but are 'fresh' copies, so that the memory containing them + * belongs to the calling application. This also enforces the + * 'read-only' nature of these values, i.e., this function cannot be + * used to manipulate the face. * - * `value` is a void pointer because the values returned can be of - * various types. + * `value` is a void pointer because the values returned can be of + * various types. * - * If either `value` is `NULL` or `value_len` is too small, just the - * required memory size for the requested entry is returned. + * If either `value` is `NULL` or `value_len` is too small, just the + * required memory size for the requested entry is returned. * - * The `idx` parameter is used, not only to retrieve elements of, for - * example, the FontMatrix or FontBBox, but also to retrieve name keys - * from the CharStrings dictionary, and the charstrings themselves. It - * is ignored for atomic values. + * The `idx` parameter is used, not only to retrieve elements of, for + * example, the FontMatrix or FontBBox, but also to retrieve name keys + * from the CharStrings dictionary, and the charstrings themselves. It + * is ignored for atomic values. * - * `PS_DICT_BLUE_SCALE` returns a value that is scaled up by 1000. To - * get the value as in the font stream, you need to divide by 65536000.0 - * (to remove the FT_Fixed scale, and the x1000 scale). + * `PS_DICT_BLUE_SCALE` returns a value that is scaled up by 1000. To + * get the value as in the font stream, you need to divide by 65536000.0 + * (to remove the FT_Fixed scale, and the x1000 scale). * - * IMPORTANT: Only key/value pairs read by the FreeType interpreter can - * be retrieved. So, for example, PostScript procedures such as NP, ND, - * and RD are not available. Arbitrary keys are, obviously, not be - * available either. + * IMPORTANT: Only key/value pairs read by the FreeType interpreter can + * be retrieved. So, for example, PostScript procedures such as NP, ND, + * and RD are not available. Arbitrary keys are, obviously, not be + * available either. * - * If the font's format is not PostScript-based, this function returns - * the `FT_Err_Invalid_Argument` error code. + * If the font's format is not PostScript-based, this function returns + * the `FT_Err_Invalid_Argument` error code. * * @since: - * 2.4.8 + * 2.4.8 * */ FT_EXPORT( FT_Long ) diff --git a/src/font/freetype-2.10.2/include/freetype/ttnameid.h b/3rdparty/freetype-2.13.2/include/freetype/ttnameid.h similarity index 99% rename from src/font/freetype-2.10.2/include/freetype/ttnameid.h rename to 3rdparty/freetype-2.13.2/include/freetype/ttnameid.h index 9a00913ee..e31c68b9b 100644 --- a/src/font/freetype-2.10.2/include/freetype/ttnameid.h +++ b/3rdparty/freetype-2.13.2/include/freetype/ttnameid.h @@ -4,7 +4,7 @@ * * TrueType name ID definitions (specification only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,7 +20,6 @@ #define TTNAMEID_H_ -#include FT_BEGIN_HEADER @@ -592,7 +591,7 @@ FT_BEGIN_HEADER #define TT_MS_LANGID_MALAY_MALAYSIA 0x043E #define TT_MS_LANGID_MALAY_BRUNEI_DARUSSALAM 0x083E #define TT_MS_LANGID_KAZAKH_KAZAKHSTAN 0x043F -#define TT_MS_LANGID_KYRGYZ_KYRGYZSTAN /* Cyrillic*/ 0x0440 +#define TT_MS_LANGID_KYRGYZ_KYRGYZSTAN /* Cyrillic */ 0x0440 #define TT_MS_LANGID_KISWAHILI_KENYA 0x0441 #define TT_MS_LANGID_TURKMEN_TURKMENISTAN 0x0442 #define TT_MS_LANGID_UZBEK_UZBEKISTAN_LATIN 0x0443 diff --git a/src/font/freetype-2.10.2/include/freetype/tttables.h b/3rdparty/freetype-2.13.2/include/freetype/tttables.h similarity index 99% rename from src/font/freetype-2.10.2/include/freetype/tttables.h rename to 3rdparty/freetype-2.13.2/include/freetype/tttables.h index 8108db717..a9f60e762 100644 --- a/src/font/freetype-2.10.2/include/freetype/tttables.h +++ b/3rdparty/freetype-2.13.2/include/freetype/tttables.h @@ -5,7 +5,7 @@ * Basic SFNT/TrueType tables definitions and interface * (specification only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -21,8 +21,7 @@ #define TTTABLES_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" @@ -425,8 +424,8 @@ FT_BEGIN_HEADER /* only version 5 and higher: */ - FT_UShort usLowerOpticalPointSize; /* in twips (1/20th points) */ - FT_UShort usUpperOpticalPointSize; /* in twips (1/20th points) */ + FT_UShort usLowerOpticalPointSize; /* in twips (1/20 points) */ + FT_UShort usUpperOpticalPointSize; /* in twips (1/20 points) */ } TT_OS2; diff --git a/src/font/freetype-2.10.2/include/freetype/tttags.h b/3rdparty/freetype-2.13.2/include/freetype/tttags.h similarity index 97% rename from src/font/freetype-2.10.2/include/freetype/tttags.h rename to 3rdparty/freetype-2.13.2/include/freetype/tttags.h index f2b2a4526..9bf4fca23 100644 --- a/src/font/freetype-2.10.2/include/freetype/tttags.h +++ b/3rdparty/freetype-2.13.2/include/freetype/tttags.h @@ -4,7 +4,7 @@ * * Tags for TrueType and OpenType tables (specification only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,8 +20,7 @@ #define TTAGS_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" @@ -96,6 +95,7 @@ FT_BEGIN_HEADER #define TTAG_sbix FT_MAKE_TAG( 's', 'b', 'i', 'x' ) #define TTAG_sfnt FT_MAKE_TAG( 's', 'f', 'n', 't' ) #define TTAG_SING FT_MAKE_TAG( 'S', 'I', 'N', 'G' ) +#define TTAG_SVG FT_MAKE_TAG( 'S', 'V', 'G', ' ' ) #define TTAG_trak FT_MAKE_TAG( 't', 'r', 'a', 'k' ) #define TTAG_true FT_MAKE_TAG( 't', 'r', 'u', 'e' ) #define TTAG_ttc FT_MAKE_TAG( 't', 't', 'c', ' ' ) diff --git a/src/font/freetype-2.10.2/include/ft2build.h b/3rdparty/freetype-2.13.2/include/ft2build.h similarity index 78% rename from src/font/freetype-2.10.2/include/ft2build.h rename to 3rdparty/freetype-2.13.2/include/ft2build.h index 195e91833..58491ceea 100644 --- a/src/font/freetype-2.10.2/include/ft2build.h +++ b/3rdparty/freetype-2.13.2/include/ft2build.h @@ -4,7 +4,7 @@ * * FreeType 2 build and setup macros. * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -18,16 +18,14 @@ /************************************************************************** * - * This is the 'entry point' for FreeType header file inclusions. It is - * the only header file which should be included directly; all other - * FreeType header files should be accessed with macro names (after - * including `ft2build.h`). + * This is the 'entry point' for FreeType header file inclusions, to be + * loaded before all other header files. * * A typical example is * * ``` * #include - * #include FT_FREETYPE_H + * #include * ``` * */ diff --git a/src/font/freetype-2.10.2/src/autofit/afblue.c b/3rdparty/freetype-2.13.2/src/autofit/afblue.c similarity index 95% rename from src/font/freetype-2.10.2/src/autofit/afblue.c rename to 3rdparty/freetype-2.13.2/src/autofit/afblue.c index 63f9ed458..d7655b9b9 100644 --- a/src/font/freetype-2.10.2/src/autofit/afblue.c +++ b/3rdparty/freetype-2.13.2/src/autofit/afblue.c @@ -7,7 +7,7 @@ * * Auto-fitter data for blue strings (body). * - * Copyright (C) 2013-2020 by + * Copyright (C) 2013-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -134,7 +134,7 @@ '\0', '\xF0', '\x90', '\x90', '\xA8', ' ', '\xF0', '\x90', '\x90', '\xAA', ' ', '\xF0', '\x90', '\x90', '\xAC', ' ', '\xF0', '\x90', '\x90', '\xBF', ' ', '\xF0', '\x90', '\x91', '\x83', /* 𐐨 𐐪 𐐬 𐐿 𐑃 */ '\0', - '\xE0', '\xA4', '\x95', ' ', '\xE0', '\xA4', '\xAE', ' ', '\xE0', '\xA4', '\x85', ' ', '\xE0', '\xA4', '\x86', ' ', '\xE0', '\xA4', '\xA5', ' ', '\xE0', '\xA4', '\xA7', ' ', '\xE0', '\xA4', '\xAD', ' ', '\xE0', '\xA4', '\xB6', /* क म अ आ थ ध भ श */ + '\xE0', '\xA4', '\x95', ' ', '\xE0', '\xA4', '\xA8', ' ', '\xE0', '\xA4', '\xAE', ' ', '\xE0', '\xA4', '\x89', ' ', '\xE0', '\xA4', '\x9B', ' ', '\xE0', '\xA4', '\x9F', ' ', '\xE0', '\xA4', '\xA0', ' ', '\xE0', '\xA4', '\xA1', /* क न म उ छ ट ठ ड */ '\0', '\xE0', '\xA4', '\x88', ' ', '\xE0', '\xA4', '\x90', ' ', '\xE0', '\xA4', '\x93', ' ', '\xE0', '\xA4', '\x94', ' ', '\xE0', '\xA4', '\xBF', ' ', '\xE0', '\xA5', '\x80', ' ', '\xE0', '\xA5', '\x8B', ' ', '\xE0', '\xA5', '\x8C', /* ई ऐ ओ औ ि ी ो ौ */ '\0', @@ -296,6 +296,20 @@ '\0', '\xE0', '\xB4', '\x9F', ' ', '\xE0', '\xB4', '\xA0', ' ', '\xE0', '\xB4', '\xA7', ' ', '\xE0', '\xB4', '\xB6', ' ', '\xE0', '\xB4', '\x98', ' ', '\xE0', '\xB4', '\x9A', ' ', '\xE0', '\xB4', '\xA5', ' ', '\xE0', '\xB4', '\xB2', /* ട ഠ ധ ശ ഘ ച ഥ ല */ '\0', + '\xF0', '\x96', '\xB9', '\x80', ' ', '\xF0', '\x96', '\xB9', '\x81', ' ', '\xF0', '\x96', '\xB9', '\x82', ' ', '\xF0', '\x96', '\xB9', '\x83', ' ', '\xF0', '\x96', '\xB9', '\x8F', ' ', '\xF0', '\x96', '\xB9', '\x9A', ' ', '\xF0', '\x96', '\xB9', '\x9F', /* 𖹀 𖹁 𖹂 𖹃 𖹏 𖹚 𖹟 */ + '\0', + '\xF0', '\x96', '\xB9', '\x80', ' ', '\xF0', '\x96', '\xB9', '\x81', ' ', '\xF0', '\x96', '\xB9', '\x82', ' ', '\xF0', '\x96', '\xB9', '\x83', ' ', '\xF0', '\x96', '\xB9', '\x8F', ' ', '\xF0', '\x96', '\xB9', '\x9A', ' ', '\xF0', '\x96', '\xB9', '\x92', ' ', '\xF0', '\x96', '\xB9', '\x93', /* 𖹀 𖹁 𖹂 𖹃 𖹏 𖹚 𖹒 𖹓 */ + '\0', + '\xF0', '\x96', '\xB9', '\xA4', ' ', '\xF0', '\x96', '\xB9', '\xAC', ' ', '\xF0', '\x96', '\xB9', '\xA7', ' ', '\xF0', '\x96', '\xB9', '\xB4', ' ', '\xF0', '\x96', '\xB9', '\xB6', ' ', '\xF0', '\x96', '\xB9', '\xBE', /* 𖹤 𖹬 𖹧 𖹴 𖹶 𖹾 */ + '\0', + '\xF0', '\x96', '\xB9', '\xA0', ' ', '\xF0', '\x96', '\xB9', '\xA1', ' ', '\xF0', '\x96', '\xB9', '\xA2', ' ', '\xF0', '\x96', '\xB9', '\xB9', ' ', '\xF0', '\x96', '\xB9', '\xB3', ' ', '\xF0', '\x96', '\xB9', '\xAE', /* 𖹠 𖹡 𖹢 𖹹 𖹳 𖹮 */ + '\0', + '\xF0', '\x96', '\xB9', '\xA0', ' ', '\xF0', '\x96', '\xB9', '\xA1', ' ', '\xF0', '\x96', '\xB9', '\xA2', ' ', '\xF0', '\x96', '\xB9', '\xB3', ' ', '\xF0', '\x96', '\xB9', '\xAD', ' ', '\xF0', '\x96', '\xB9', '\xBD', /* 𖹠 𖹡 𖹢 𖹳 𖹭 𖹽 */ + '\0', + '\xF0', '\x96', '\xB9', '\xA5', ' ', '\xF0', '\x96', '\xB9', '\xA8', ' ', '\xF0', '\x96', '\xB9', '\xA9', /* 𖹥 𖹨 𖹩 */ + '\0', + '\xF0', '\x96', '\xBA', '\x80', ' ', '\xF0', '\x96', '\xBA', '\x85', ' ', '\xF0', '\x96', '\xBA', '\x88', ' ', '\xF0', '\x96', '\xBA', '\x84', ' ', '\xF0', '\x96', '\xBA', '\x8D', /* 𖺀 𖺅 𖺈 𖺄 𖺍 */ + '\0', '\xE1', '\xA0', '\xB3', ' ', '\xE1', '\xA0', '\xB4', ' ', '\xE1', '\xA0', '\xB6', ' ', '\xE1', '\xA0', '\xBD', ' ', '\xE1', '\xA1', '\x82', ' ', '\xE1', '\xA1', '\x8A', ' ', '\xE2', '\x80', '\x8D', '\xE1', '\xA1', '\xA1', '\xE2', '\x80', '\x8D', ' ', '\xE2', '\x80', '\x8D', '\xE1', '\xA1', '\xB3', '\xE2', '\x80', '\x8D', /* ᠳ ᠴ ᠶ ᠽ ᡂ ᡊ ‍ᡡ‍ ‍ᡳ‍ */ '\0', '\xE1', '\xA1', '\x83', /* ᡃ */ @@ -494,14 +508,14 @@ { AF_BLUE_STRING_CHAKMA_BOTTOM, 0 }, { AF_BLUE_STRING_CHAKMA_DESCENDER, 0 }, { AF_BLUE_STRING_MAX, 0 }, - { AF_BLUE_STRING_CANADIAN_SYLLABICS_TOP, AF_BLUE_PROPERTY_LATIN_TOP }, - { AF_BLUE_STRING_CANADIAN_SYLLABICS_BOTTOM, 0 }, - { AF_BLUE_STRING_CANADIAN_SYLLABICS_SMALL_TOP, AF_BLUE_PROPERTY_LATIN_TOP | - AF_BLUE_PROPERTY_LATIN_X_HEIGHT }, - { AF_BLUE_STRING_CANADIAN_SYLLABICS_SMALL_BOTTOM, 0 }, - { AF_BLUE_STRING_CANADIAN_SYLLABICS_SUPS_TOP, AF_BLUE_PROPERTY_LATIN_TOP }, - { AF_BLUE_STRING_CANADIAN_SYLLABICS_SUPS_BOTTOM, 0 }, - { AF_BLUE_STRING_MAX, 0 }, + { AF_BLUE_STRING_CANADIAN_SYLLABICS_TOP, AF_BLUE_PROPERTY_LATIN_TOP }, + { AF_BLUE_STRING_CANADIAN_SYLLABICS_BOTTOM, 0 }, + { AF_BLUE_STRING_CANADIAN_SYLLABICS_SMALL_TOP, AF_BLUE_PROPERTY_LATIN_TOP | + AF_BLUE_PROPERTY_LATIN_X_HEIGHT }, + { AF_BLUE_STRING_CANADIAN_SYLLABICS_SMALL_BOTTOM, 0 }, + { AF_BLUE_STRING_CANADIAN_SYLLABICS_SUPS_TOP, AF_BLUE_PROPERTY_LATIN_TOP }, + { AF_BLUE_STRING_CANADIAN_SYLLABICS_SUPS_BOTTOM, 0 }, + { AF_BLUE_STRING_MAX, 0 }, { AF_BLUE_STRING_CARIAN_TOP, AF_BLUE_PROPERTY_LATIN_TOP }, { AF_BLUE_STRING_CARIAN_BOTTOM, 0 }, { AF_BLUE_STRING_MAX, 0 }, @@ -601,6 +615,9 @@ { AF_BLUE_STRING_HEBREW_BOTTOM, 0 }, { AF_BLUE_STRING_HEBREW_DESCENDER, 0 }, { AF_BLUE_STRING_MAX, 0 }, + { AF_BLUE_STRING_KANNADA_TOP, AF_BLUE_PROPERTY_LATIN_TOP }, + { AF_BLUE_STRING_KANNADA_BOTTOM, 0 }, + { AF_BLUE_STRING_MAX, 0 }, { AF_BLUE_STRING_KAYAH_LI_TOP, AF_BLUE_PROPERTY_LATIN_TOP | AF_BLUE_PROPERTY_LATIN_X_HEIGHT }, { AF_BLUE_STRING_KAYAH_LI_BOTTOM, 0 }, @@ -619,9 +636,6 @@ AF_BLUE_PROPERTY_LATIN_X_HEIGHT }, { AF_BLUE_STRING_KHMER_SYMBOLS_WANING_BOTTOM, 0 }, { AF_BLUE_STRING_MAX, 0 }, - { AF_BLUE_STRING_KANNADA_TOP, AF_BLUE_PROPERTY_LATIN_TOP }, - { AF_BLUE_STRING_KANNADA_BOTTOM, 0 }, - { AF_BLUE_STRING_MAX, 0 }, { AF_BLUE_STRING_LAO_TOP, AF_BLUE_PROPERTY_LATIN_TOP | AF_BLUE_PROPERTY_LATIN_X_HEIGHT }, { AF_BLUE_STRING_LAO_BOTTOM, 0 }, @@ -659,6 +673,15 @@ { AF_BLUE_STRING_MALAYALAM_TOP, AF_BLUE_PROPERTY_LATIN_TOP }, { AF_BLUE_STRING_MALAYALAM_BOTTOM, 0 }, { AF_BLUE_STRING_MAX, 0 }, + { AF_BLUE_STRING_MEDEFAIDRIN_CAPITAL_TOP, AF_BLUE_PROPERTY_LATIN_TOP }, + { AF_BLUE_STRING_MEDEFAIDRIN_CAPITAL_BOTTOM, 0 }, + { AF_BLUE_STRING_MEDEFAIDRIN_SMALL_F_TOP, AF_BLUE_PROPERTY_LATIN_TOP }, + { AF_BLUE_STRING_MEDEFAIDRIN_SMALL_TOP, AF_BLUE_PROPERTY_LATIN_TOP | + AF_BLUE_PROPERTY_LATIN_X_HEIGHT }, + { AF_BLUE_STRING_MEDEFAIDRIN_SMALL_BOTTOM, 0 }, + { AF_BLUE_STRING_MEDEFAIDRIN_SMALL_DESCENDER, 0 }, + { AF_BLUE_STRING_MEDEFAIDRIN_DIGIT_TOP, AF_BLUE_PROPERTY_LATIN_TOP }, + { AF_BLUE_STRING_MAX, 0 }, { AF_BLUE_STRING_MONGOLIAN_TOP_BASE, AF_BLUE_PROPERTY_LATIN_TOP }, { AF_BLUE_STRING_MONGOLIAN_BOTTOM_BASE, 0 }, { AF_BLUE_STRING_MAX, 0 }, @@ -724,9 +747,6 @@ { AF_BLUE_STRING_TELUGU_TOP, AF_BLUE_PROPERTY_LATIN_TOP }, { AF_BLUE_STRING_TELUGU_BOTTOM, 0 }, { AF_BLUE_STRING_MAX, 0 }, - { AF_BLUE_STRING_TIFINAGH, AF_BLUE_PROPERTY_LATIN_TOP }, - { AF_BLUE_STRING_TIFINAGH, 0 }, - { AF_BLUE_STRING_MAX, 0 }, { AF_BLUE_STRING_THAI_TOP, AF_BLUE_PROPERTY_LATIN_TOP | AF_BLUE_PROPERTY_LATIN_X_HEIGHT }, { AF_BLUE_STRING_THAI_BOTTOM, 0 }, @@ -736,6 +756,9 @@ { AF_BLUE_STRING_THAI_LARGE_DESCENDER, 0 }, { AF_BLUE_STRING_THAI_DIGIT_TOP, 0 }, { AF_BLUE_STRING_MAX, 0 }, + { AF_BLUE_STRING_TIFINAGH, AF_BLUE_PROPERTY_LATIN_TOP }, + { AF_BLUE_STRING_TIFINAGH, 0 }, + { AF_BLUE_STRING_MAX, 0 }, { AF_BLUE_STRING_VAI_TOP, AF_BLUE_PROPERTY_LATIN_TOP }, { AF_BLUE_STRING_VAI_BOTTOM, 0 }, { AF_BLUE_STRING_MAX, 0 }, diff --git a/src/font/freetype-2.10.2/src/autofit/afblue.cin b/3rdparty/freetype-2.13.2/src/autofit/afblue.cin similarity index 96% rename from src/font/freetype-2.10.2/src/autofit/afblue.cin rename to 3rdparty/freetype-2.13.2/src/autofit/afblue.cin index c6a697fee..d561c5093 100644 --- a/src/font/freetype-2.10.2/src/autofit/afblue.cin +++ b/3rdparty/freetype-2.13.2/src/autofit/afblue.cin @@ -4,7 +4,7 @@ * * Auto-fitter data for blue strings (body). * - * Copyright (C) 2013-2020 by + * Copyright (C) 2013-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, diff --git a/src/font/freetype-2.10.2/src/autofit/afblue.dat b/3rdparty/freetype-2.13.2/src/autofit/afblue.dat similarity index 95% rename from src/font/freetype-2.10.2/src/autofit/afblue.dat rename to 3rdparty/freetype-2.13.2/src/autofit/afblue.dat index f8356ba3a..8299baa25 100644 --- a/src/font/freetype-2.10.2/src/autofit/afblue.dat +++ b/3rdparty/freetype-2.13.2/src/autofit/afblue.dat @@ -2,7 +2,7 @@ // // Auto-fitter data for blue strings. // -// Copyright (C) 2013-2020 by +// Copyright (C) 2013-2023 by // David Turner, Robert Wilhelm, and Werner Lemberg. // // This file is part of the FreeType project, and may only be used, @@ -89,7 +89,7 @@ AF_BLUE_STRING_ENUM AF_BLUE_STRINGS_ARRAY AF_BLUE_STRING_MAX_LEN: "ت ث ط ظ ك" // We don't necessarily have access to medial forms via Unicode in case // Arabic presentational forms are missing. The only character that is - // guaranteed to have the same vertical position with joining (this is, + // guaranteed to have the same vertical position with joining (that is, // non-isolated) forms is U+0640, ARABIC TATWEEL, which must join both // round and flat curves. AF_BLUE_STRING_ARABIC_JOIN @@ -203,7 +203,7 @@ AF_BLUE_STRING_ENUM AF_BLUE_STRINGS_ARRAY AF_BLUE_STRING_MAX_LEN: "𐐨 𐐪 𐐬 𐐿 𐑃" AF_BLUE_STRING_DEVANAGARI_BASE - "क म अ आ थ ध भ श" + "क न म उ छ ट ठ ड" AF_BLUE_STRING_DEVANAGARI_TOP "ई ऐ ओ औ ि ी ो ौ" // note that some fonts have extreme variation in the height of the @@ -392,6 +392,21 @@ AF_BLUE_STRING_ENUM AF_BLUE_STRINGS_ARRAY AF_BLUE_STRING_MAX_LEN: AF_BLUE_STRING_MALAYALAM_BOTTOM "ട ഠ ധ ശ ഘ ച ഥ ല" + AF_BLUE_STRING_MEDEFAIDRIN_CAPITAL_TOP + "𖹀 𖹁 𖹂 𖹃 𖹏 𖹚 𖹟" + AF_BLUE_STRING_MEDEFAIDRIN_CAPITAL_BOTTOM + "𖹀 𖹁 𖹂 𖹃 𖹏 𖹚 𖹒 𖹓" + AF_BLUE_STRING_MEDEFAIDRIN_SMALL_F_TOP + "𖹤 𖹬 𖹧 𖹴 𖹶 𖹾" + AF_BLUE_STRING_MEDEFAIDRIN_SMALL_TOP + "𖹠 𖹡 𖹢 𖹹 𖹳 𖹮" + AF_BLUE_STRING_MEDEFAIDRIN_SMALL_BOTTOM + "𖹠 𖹡 𖹢 𖹳 𖹭 𖹽" + AF_BLUE_STRING_MEDEFAIDRIN_SMALL_DESCENDER + "𖹥 𖹨 𖹩" + AF_BLUE_STRING_MEDEFAIDRIN_DIGIT_TOP + "𖺀 𖺅 𖺈 𖺄 𖺍" + AF_BLUE_STRING_MONGOLIAN_TOP_BASE "ᠳ ᠴ ᠶ ᠽ ᡂ ᡊ ‍ᡡ‍ ‍ᡳ‍" AF_BLUE_STRING_MONGOLIAN_BOTTOM_BASE @@ -741,14 +756,14 @@ AF_BLUE_STRINGSET_ENUM AF_BLUE_STRINGSETS_ARRAY AF_BLUE_STRINGSET_MAX_LEN: { AF_BLUE_STRING_MAX, 0 } AF_BLUE_STRINGSET_CANS - { AF_BLUE_STRING_CANADIAN_SYLLABICS_TOP, AF_BLUE_PROPERTY_LATIN_TOP } - { AF_BLUE_STRING_CANADIAN_SYLLABICS_BOTTOM, 0 } - { AF_BLUE_STRING_CANADIAN_SYLLABICS_SMALL_TOP, AF_BLUE_PROPERTY_LATIN_TOP | - AF_BLUE_PROPERTY_LATIN_X_HEIGHT } - { AF_BLUE_STRING_CANADIAN_SYLLABICS_SMALL_BOTTOM, 0 } - { AF_BLUE_STRING_CANADIAN_SYLLABICS_SUPS_TOP, AF_BLUE_PROPERTY_LATIN_TOP } - { AF_BLUE_STRING_CANADIAN_SYLLABICS_SUPS_BOTTOM, 0 } - { AF_BLUE_STRING_MAX, 0 } + { AF_BLUE_STRING_CANADIAN_SYLLABICS_TOP, AF_BLUE_PROPERTY_LATIN_TOP } + { AF_BLUE_STRING_CANADIAN_SYLLABICS_BOTTOM, 0 } + { AF_BLUE_STRING_CANADIAN_SYLLABICS_SMALL_TOP, AF_BLUE_PROPERTY_LATIN_TOP | + AF_BLUE_PROPERTY_LATIN_X_HEIGHT } + { AF_BLUE_STRING_CANADIAN_SYLLABICS_SMALL_BOTTOM, 0 } + { AF_BLUE_STRING_CANADIAN_SYLLABICS_SUPS_TOP, AF_BLUE_PROPERTY_LATIN_TOP } + { AF_BLUE_STRING_CANADIAN_SYLLABICS_SUPS_BOTTOM, 0 } + { AF_BLUE_STRING_MAX, 0 } AF_BLUE_STRINGSET_CARI { AF_BLUE_STRING_CARIAN_TOP, AF_BLUE_PROPERTY_LATIN_TOP } @@ -881,6 +896,11 @@ AF_BLUE_STRINGSET_ENUM AF_BLUE_STRINGSETS_ARRAY AF_BLUE_STRINGSET_MAX_LEN: { AF_BLUE_STRING_HEBREW_DESCENDER, 0 } { AF_BLUE_STRING_MAX, 0 } + AF_BLUE_STRINGSET_KNDA + { AF_BLUE_STRING_KANNADA_TOP, AF_BLUE_PROPERTY_LATIN_TOP } + { AF_BLUE_STRING_KANNADA_BOTTOM, 0 } + { AF_BLUE_STRING_MAX, 0 } + AF_BLUE_STRINGSET_KALI { AF_BLUE_STRING_KAYAH_LI_TOP, AF_BLUE_PROPERTY_LATIN_TOP | AF_BLUE_PROPERTY_LATIN_X_HEIGHT } @@ -905,11 +925,6 @@ AF_BLUE_STRINGSET_ENUM AF_BLUE_STRINGSETS_ARRAY AF_BLUE_STRINGSET_MAX_LEN: { AF_BLUE_STRING_KHMER_SYMBOLS_WANING_BOTTOM, 0 } { AF_BLUE_STRING_MAX, 0 } - AF_BLUE_STRINGSET_KNDA - { AF_BLUE_STRING_KANNADA_TOP, AF_BLUE_PROPERTY_LATIN_TOP } - { AF_BLUE_STRING_KANNADA_BOTTOM, 0 } - { AF_BLUE_STRING_MAX, 0 } - AF_BLUE_STRINGSET_LAO { AF_BLUE_STRING_LAO_TOP, AF_BLUE_PROPERTY_LATIN_TOP | AF_BLUE_PROPERTY_LATIN_X_HEIGHT } @@ -959,6 +974,17 @@ AF_BLUE_STRINGSET_ENUM AF_BLUE_STRINGSETS_ARRAY AF_BLUE_STRINGSET_MAX_LEN: { AF_BLUE_STRING_MALAYALAM_BOTTOM, 0 } { AF_BLUE_STRING_MAX, 0 } + AF_BLUE_STRINGSET_MEDF + { AF_BLUE_STRING_MEDEFAIDRIN_CAPITAL_TOP, AF_BLUE_PROPERTY_LATIN_TOP } + { AF_BLUE_STRING_MEDEFAIDRIN_CAPITAL_BOTTOM, 0 } + { AF_BLUE_STRING_MEDEFAIDRIN_SMALL_F_TOP, AF_BLUE_PROPERTY_LATIN_TOP } + { AF_BLUE_STRING_MEDEFAIDRIN_SMALL_TOP, AF_BLUE_PROPERTY_LATIN_TOP | + AF_BLUE_PROPERTY_LATIN_X_HEIGHT } + { AF_BLUE_STRING_MEDEFAIDRIN_SMALL_BOTTOM, 0 } + { AF_BLUE_STRING_MEDEFAIDRIN_SMALL_DESCENDER, 0 } + { AF_BLUE_STRING_MEDEFAIDRIN_DIGIT_TOP, AF_BLUE_PROPERTY_LATIN_TOP } + { AF_BLUE_STRING_MAX, 0 } + AF_BLUE_STRINGSET_MONG { AF_BLUE_STRING_MONGOLIAN_TOP_BASE, AF_BLUE_PROPERTY_LATIN_TOP } { AF_BLUE_STRING_MONGOLIAN_BOTTOM_BASE, 0 } @@ -1056,11 +1082,6 @@ AF_BLUE_STRINGSET_ENUM AF_BLUE_STRINGSETS_ARRAY AF_BLUE_STRINGSET_MAX_LEN: { AF_BLUE_STRING_TELUGU_BOTTOM, 0 } { AF_BLUE_STRING_MAX, 0 } - AF_BLUE_STRINGSET_TFNG - { AF_BLUE_STRING_TIFINAGH, AF_BLUE_PROPERTY_LATIN_TOP } - { AF_BLUE_STRING_TIFINAGH, 0 } - { AF_BLUE_STRING_MAX, 0 } - AF_BLUE_STRINGSET_THAI { AF_BLUE_STRING_THAI_TOP, AF_BLUE_PROPERTY_LATIN_TOP | AF_BLUE_PROPERTY_LATIN_X_HEIGHT } @@ -1072,6 +1093,11 @@ AF_BLUE_STRINGSET_ENUM AF_BLUE_STRINGSETS_ARRAY AF_BLUE_STRINGSET_MAX_LEN: { AF_BLUE_STRING_THAI_DIGIT_TOP, 0 } { AF_BLUE_STRING_MAX, 0 } + AF_BLUE_STRINGSET_TFNG + { AF_BLUE_STRING_TIFINAGH, AF_BLUE_PROPERTY_LATIN_TOP } + { AF_BLUE_STRING_TIFINAGH, 0 } + { AF_BLUE_STRING_MAX, 0 } + AF_BLUE_STRINGSET_VAII { AF_BLUE_STRING_VAI_TOP, AF_BLUE_PROPERTY_LATIN_TOP } { AF_BLUE_STRING_VAI_BOTTOM, 0 } diff --git a/src/font/freetype-2.10.2/src/autofit/afblue.h b/3rdparty/freetype-2.13.2/src/autofit/afblue.h similarity index 79% rename from src/font/freetype-2.10.2/src/autofit/afblue.h rename to 3rdparty/freetype-2.13.2/src/autofit/afblue.h index 2b6a5cdda..76f2f47cb 100644 --- a/src/font/freetype-2.10.2/src/autofit/afblue.h +++ b/3rdparty/freetype-2.13.2/src/autofit/afblue.h @@ -7,7 +7,7 @@ * * Auto-fitter data for blue strings (specification). * - * Copyright (C) 2013-2020 by + * Copyright (C) 2013-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -212,61 +212,68 @@ FT_BEGIN_HEADER AF_BLUE_STRING_LISU_BOTTOM = 3506, AF_BLUE_STRING_MALAYALAM_TOP = 3538, AF_BLUE_STRING_MALAYALAM_BOTTOM = 3582, - AF_BLUE_STRING_MONGOLIAN_TOP_BASE = 3614, - AF_BLUE_STRING_MONGOLIAN_BOTTOM_BASE = 3658, - AF_BLUE_STRING_MYANMAR_TOP = 3662, - AF_BLUE_STRING_MYANMAR_BOTTOM = 3694, - AF_BLUE_STRING_MYANMAR_ASCENDER = 3726, - AF_BLUE_STRING_MYANMAR_DESCENDER = 3754, - AF_BLUE_STRING_NKO_TOP = 3786, - AF_BLUE_STRING_NKO_BOTTOM = 3810, - AF_BLUE_STRING_NKO_SMALL_TOP = 3825, - AF_BLUE_STRING_NKO_SMALL_BOTTOM = 3834, - AF_BLUE_STRING_OL_CHIKI = 3846, - AF_BLUE_STRING_OLD_TURKIC_TOP = 3870, - AF_BLUE_STRING_OLD_TURKIC_BOTTOM = 3885, - AF_BLUE_STRING_OSAGE_CAPITAL_TOP = 3905, - AF_BLUE_STRING_OSAGE_CAPITAL_BOTTOM = 3945, - AF_BLUE_STRING_OSAGE_CAPITAL_DESCENDER = 3975, - AF_BLUE_STRING_OSAGE_SMALL_TOP = 3990, - AF_BLUE_STRING_OSAGE_SMALL_BOTTOM = 4030, - AF_BLUE_STRING_OSAGE_SMALL_ASCENDER = 4070, - AF_BLUE_STRING_OSAGE_SMALL_DESCENDER = 4095, - AF_BLUE_STRING_OSMANYA_TOP = 4110, - AF_BLUE_STRING_OSMANYA_BOTTOM = 4150, - AF_BLUE_STRING_ROHINGYA_TOP = 4190, - AF_BLUE_STRING_ROHINGYA_BOTTOM = 4215, - AF_BLUE_STRING_ROHINGYA_JOIN = 4240, - AF_BLUE_STRING_SAURASHTRA_TOP = 4243, - AF_BLUE_STRING_SAURASHTRA_BOTTOM = 4275, - AF_BLUE_STRING_SHAVIAN_TOP = 4295, - AF_BLUE_STRING_SHAVIAN_BOTTOM = 4305, - AF_BLUE_STRING_SHAVIAN_DESCENDER = 4330, - AF_BLUE_STRING_SHAVIAN_SMALL_TOP = 4340, - AF_BLUE_STRING_SHAVIAN_SMALL_BOTTOM = 4375, - AF_BLUE_STRING_SINHALA_TOP = 4390, - AF_BLUE_STRING_SINHALA_BOTTOM = 4422, - AF_BLUE_STRING_SINHALA_DESCENDER = 4454, - AF_BLUE_STRING_SUNDANESE_TOP = 4498, - AF_BLUE_STRING_SUNDANESE_BOTTOM = 4522, - AF_BLUE_STRING_SUNDANESE_DESCENDER = 4554, - AF_BLUE_STRING_TAI_VIET_TOP = 4562, - AF_BLUE_STRING_TAI_VIET_BOTTOM = 4582, - AF_BLUE_STRING_TAMIL_TOP = 4594, - AF_BLUE_STRING_TAMIL_BOTTOM = 4626, - AF_BLUE_STRING_TELUGU_TOP = 4658, - AF_BLUE_STRING_TELUGU_BOTTOM = 4686, - AF_BLUE_STRING_THAI_TOP = 4714, - AF_BLUE_STRING_THAI_BOTTOM = 4738, - AF_BLUE_STRING_THAI_ASCENDER = 4766, - AF_BLUE_STRING_THAI_LARGE_ASCENDER = 4778, - AF_BLUE_STRING_THAI_DESCENDER = 4790, - AF_BLUE_STRING_THAI_LARGE_DESCENDER = 4806, - AF_BLUE_STRING_THAI_DIGIT_TOP = 4814, - AF_BLUE_STRING_TIFINAGH = 4826, - AF_BLUE_STRING_VAI_TOP = 4858, - AF_BLUE_STRING_VAI_BOTTOM = 4890, - af_blue_1_1 = 4921, + AF_BLUE_STRING_MEDEFAIDRIN_CAPITAL_TOP = 3614, + AF_BLUE_STRING_MEDEFAIDRIN_CAPITAL_BOTTOM = 3649, + AF_BLUE_STRING_MEDEFAIDRIN_SMALL_F_TOP = 3689, + AF_BLUE_STRING_MEDEFAIDRIN_SMALL_TOP = 3719, + AF_BLUE_STRING_MEDEFAIDRIN_SMALL_BOTTOM = 3749, + AF_BLUE_STRING_MEDEFAIDRIN_SMALL_DESCENDER = 3779, + AF_BLUE_STRING_MEDEFAIDRIN_DIGIT_TOP = 3794, + AF_BLUE_STRING_MONGOLIAN_TOP_BASE = 3819, + AF_BLUE_STRING_MONGOLIAN_BOTTOM_BASE = 3863, + AF_BLUE_STRING_MYANMAR_TOP = 3867, + AF_BLUE_STRING_MYANMAR_BOTTOM = 3899, + AF_BLUE_STRING_MYANMAR_ASCENDER = 3931, + AF_BLUE_STRING_MYANMAR_DESCENDER = 3959, + AF_BLUE_STRING_NKO_TOP = 3991, + AF_BLUE_STRING_NKO_BOTTOM = 4015, + AF_BLUE_STRING_NKO_SMALL_TOP = 4030, + AF_BLUE_STRING_NKO_SMALL_BOTTOM = 4039, + AF_BLUE_STRING_OL_CHIKI = 4051, + AF_BLUE_STRING_OLD_TURKIC_TOP = 4075, + AF_BLUE_STRING_OLD_TURKIC_BOTTOM = 4090, + AF_BLUE_STRING_OSAGE_CAPITAL_TOP = 4110, + AF_BLUE_STRING_OSAGE_CAPITAL_BOTTOM = 4150, + AF_BLUE_STRING_OSAGE_CAPITAL_DESCENDER = 4180, + AF_BLUE_STRING_OSAGE_SMALL_TOP = 4195, + AF_BLUE_STRING_OSAGE_SMALL_BOTTOM = 4235, + AF_BLUE_STRING_OSAGE_SMALL_ASCENDER = 4275, + AF_BLUE_STRING_OSAGE_SMALL_DESCENDER = 4300, + AF_BLUE_STRING_OSMANYA_TOP = 4315, + AF_BLUE_STRING_OSMANYA_BOTTOM = 4355, + AF_BLUE_STRING_ROHINGYA_TOP = 4395, + AF_BLUE_STRING_ROHINGYA_BOTTOM = 4420, + AF_BLUE_STRING_ROHINGYA_JOIN = 4445, + AF_BLUE_STRING_SAURASHTRA_TOP = 4448, + AF_BLUE_STRING_SAURASHTRA_BOTTOM = 4480, + AF_BLUE_STRING_SHAVIAN_TOP = 4500, + AF_BLUE_STRING_SHAVIAN_BOTTOM = 4510, + AF_BLUE_STRING_SHAVIAN_DESCENDER = 4535, + AF_BLUE_STRING_SHAVIAN_SMALL_TOP = 4545, + AF_BLUE_STRING_SHAVIAN_SMALL_BOTTOM = 4580, + AF_BLUE_STRING_SINHALA_TOP = 4595, + AF_BLUE_STRING_SINHALA_BOTTOM = 4627, + AF_BLUE_STRING_SINHALA_DESCENDER = 4659, + AF_BLUE_STRING_SUNDANESE_TOP = 4703, + AF_BLUE_STRING_SUNDANESE_BOTTOM = 4727, + AF_BLUE_STRING_SUNDANESE_DESCENDER = 4759, + AF_BLUE_STRING_TAI_VIET_TOP = 4767, + AF_BLUE_STRING_TAI_VIET_BOTTOM = 4787, + AF_BLUE_STRING_TAMIL_TOP = 4799, + AF_BLUE_STRING_TAMIL_BOTTOM = 4831, + AF_BLUE_STRING_TELUGU_TOP = 4863, + AF_BLUE_STRING_TELUGU_BOTTOM = 4891, + AF_BLUE_STRING_THAI_TOP = 4919, + AF_BLUE_STRING_THAI_BOTTOM = 4943, + AF_BLUE_STRING_THAI_ASCENDER = 4971, + AF_BLUE_STRING_THAI_LARGE_ASCENDER = 4983, + AF_BLUE_STRING_THAI_DESCENDER = 4995, + AF_BLUE_STRING_THAI_LARGE_DESCENDER = 5011, + AF_BLUE_STRING_THAI_DIGIT_TOP = 5019, + AF_BLUE_STRING_TIFINAGH = 5031, + AF_BLUE_STRING_VAI_TOP = 5063, + AF_BLUE_STRING_VAI_BOTTOM = 5095, + af_blue_1_1 = 5126, #ifdef AF_CONFIG_OPTION_CJK AF_BLUE_STRING_CJK_TOP = af_blue_1_1 + 1, AF_BLUE_STRING_CJK_BOTTOM = af_blue_1_1 + 203, @@ -350,36 +357,37 @@ FT_BEGIN_HEADER AF_BLUE_STRINGSET_GUJR = 112, AF_BLUE_STRINGSET_GURU = 118, AF_BLUE_STRINGSET_HEBR = 124, - AF_BLUE_STRINGSET_KALI = 128, - AF_BLUE_STRINGSET_KHMR = 134, - AF_BLUE_STRINGSET_KHMS = 140, - AF_BLUE_STRINGSET_KNDA = 143, + AF_BLUE_STRINGSET_KNDA = 128, + AF_BLUE_STRINGSET_KALI = 131, + AF_BLUE_STRINGSET_KHMR = 137, + AF_BLUE_STRINGSET_KHMS = 143, AF_BLUE_STRINGSET_LAO = 146, AF_BLUE_STRINGSET_LATN = 152, AF_BLUE_STRINGSET_LATB = 159, AF_BLUE_STRINGSET_LATP = 166, AF_BLUE_STRINGSET_LISU = 173, AF_BLUE_STRINGSET_MLYM = 176, - AF_BLUE_STRINGSET_MONG = 179, - AF_BLUE_STRINGSET_MYMR = 182, - AF_BLUE_STRINGSET_NKOO = 187, - AF_BLUE_STRINGSET_NONE = 192, - AF_BLUE_STRINGSET_OLCK = 193, - AF_BLUE_STRINGSET_ORKH = 196, - AF_BLUE_STRINGSET_OSGE = 199, - AF_BLUE_STRINGSET_OSMA = 207, - AF_BLUE_STRINGSET_ROHG = 210, - AF_BLUE_STRINGSET_SAUR = 214, - AF_BLUE_STRINGSET_SHAW = 217, - AF_BLUE_STRINGSET_SINH = 223, - AF_BLUE_STRINGSET_SUND = 227, - AF_BLUE_STRINGSET_TAML = 231, - AF_BLUE_STRINGSET_TAVT = 234, - AF_BLUE_STRINGSET_TELU = 237, - AF_BLUE_STRINGSET_TFNG = 240, - AF_BLUE_STRINGSET_THAI = 243, - AF_BLUE_STRINGSET_VAII = 251, - af_blue_2_1 = 254, + AF_BLUE_STRINGSET_MEDF = 179, + AF_BLUE_STRINGSET_MONG = 187, + AF_BLUE_STRINGSET_MYMR = 190, + AF_BLUE_STRINGSET_NKOO = 195, + AF_BLUE_STRINGSET_NONE = 200, + AF_BLUE_STRINGSET_OLCK = 201, + AF_BLUE_STRINGSET_ORKH = 204, + AF_BLUE_STRINGSET_OSGE = 207, + AF_BLUE_STRINGSET_OSMA = 215, + AF_BLUE_STRINGSET_ROHG = 218, + AF_BLUE_STRINGSET_SAUR = 222, + AF_BLUE_STRINGSET_SHAW = 225, + AF_BLUE_STRINGSET_SINH = 231, + AF_BLUE_STRINGSET_SUND = 235, + AF_BLUE_STRINGSET_TAML = 239, + AF_BLUE_STRINGSET_TAVT = 242, + AF_BLUE_STRINGSET_TELU = 245, + AF_BLUE_STRINGSET_THAI = 248, + AF_BLUE_STRINGSET_TFNG = 256, + AF_BLUE_STRINGSET_VAII = 259, + af_blue_2_1 = 262, #ifdef AF_CONFIG_OPTION_CJK AF_BLUE_STRINGSET_HANI = af_blue_2_1 + 0, af_blue_2_1_1 = af_blue_2_1 + 2, diff --git a/src/font/freetype-2.10.2/src/autofit/afblue.hin b/3rdparty/freetype-2.13.2/src/autofit/afblue.hin similarity index 99% rename from src/font/freetype-2.10.2/src/autofit/afblue.hin rename to 3rdparty/freetype-2.13.2/src/autofit/afblue.hin index 395702709..6a31298e6 100644 --- a/src/font/freetype-2.10.2/src/autofit/afblue.hin +++ b/3rdparty/freetype-2.13.2/src/autofit/afblue.hin @@ -4,7 +4,7 @@ * * Auto-fitter data for blue strings (specification). * - * Copyright (C) 2013-2020 by + * Copyright (C) 2013-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, diff --git a/src/font/freetype-2.10.2/src/autofit/afcjk.c b/3rdparty/freetype-2.13.2/src/autofit/afcjk.c similarity index 93% rename from src/font/freetype-2.10.2/src/autofit/afcjk.c rename to 3rdparty/freetype-2.13.2/src/autofit/afcjk.c index ca6ce0c60..f414289ad 100644 --- a/src/font/freetype-2.10.2/src/autofit/afcjk.c +++ b/3rdparty/freetype-2.13.2/src/autofit/afcjk.c @@ -4,7 +4,7 @@ * * Auto-fitter hinting routines for CJK writing system (body). * - * Copyright (C) 2006-2020 by + * Copyright (C) 2006-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -22,9 +22,8 @@ * */ -#include -#include FT_ADVANCES_H -#include FT_INTERNAL_DEBUG_H +#include +#include #include "afglobal.h" #include "aflatin.h" @@ -38,11 +37,6 @@ #include "aferrors.h" -#ifdef AF_CONFIG_OPTION_USE_WARPER -#include "afwarp.h" -#endif - - /************************************************************************** * * The macro FT_COMPONENT is used in trace mode. It is an implicit @@ -73,11 +67,11 @@ AF_GlyphHintsRec hints[1]; - FT_TRACE5(( "\n" - "cjk standard widths computation (style `%s')\n" - "===================================================\n" - "\n", + FT_TRACE5(( "\n" )); + FT_TRACE5(( "cjk standard widths computation (style `%s')\n", af_style_names[metrics->root.style_class->style] )); + FT_TRACE5(( "===================================================\n" )); + FT_TRACE5(( "\n" )); af_glyph_hints_init( hints, face->memory ); @@ -158,7 +152,7 @@ if ( !glyph_index ) goto Exit; - FT_TRACE5(( "standard character: U+%04lX (glyph index %d)\n", + FT_TRACE5(( "standard character: U+%04lX (glyph index %ld)\n", ch, glyph_index )); error = FT_Load_Glyph( face, glyph_index, FT_LOAD_NO_SCALE ); @@ -261,9 +255,9 @@ dim == AF_DIMENSION_VERT ? "horizontal" : "vertical" )); - FT_TRACE5(( " %d (standard)", axis->standard_width )); + FT_TRACE5(( " %ld (standard)", axis->standard_width )); for ( i = 1; i < axis->width_count; i++ ) - FT_TRACE5(( " %d", axis->widths[i].org )); + FT_TRACE5(( " %ld", axis->widths[i].org )); FT_TRACE5(( "\n" )); } @@ -315,9 +309,9 @@ /* style's entry in the `af_blue_stringset' array, computing its */ /* extremum points (depending on the string properties) */ - FT_TRACE5(( "cjk blue zones computation\n" - "==========================\n" - "\n" )); + FT_TRACE5(( "cjk blue zones computation\n" )); + FT_TRACE5(( "==========================\n" )); + FT_TRACE5(( "\n" )); #ifdef FT_CONFIG_OPTION_USE_HARFBUZZ shaper_buf = af_shaper_buf_create( face ); @@ -423,16 +417,14 @@ { FT_Int nn; - FT_Int first = 0; - FT_Int last = -1; + FT_Int pp, first, last; - for ( nn = 0; nn < outline.n_contours; first = last + 1, nn++ ) + last = -1; + for ( nn = 0; nn < outline.n_contours; nn++ ) { - FT_Int pp; - - - last = outline.contours[nn]; + first = last + 1; + last = outline.contours[nn]; /* Avoid single-point contours since they are never rasterized. */ /* In some fonts, they correspond to mark attachment points */ @@ -556,9 +548,8 @@ if ( AF_CJK_IS_TOP_BLUE( bs ) ) blue->flags |= AF_CJK_BLUE_TOP; - FT_TRACE5(( " -> reference = %ld\n" - " overshoot = %ld\n", - *blue_ref, *blue_shoot )); + FT_TRACE5(( " -> reference = %ld\n", *blue_ref )); + FT_TRACE5(( " overshoot = %ld\n", *blue_shoot )); } /* end for loop */ @@ -576,8 +567,8 @@ af_cjk_metrics_check_digits( AF_CJKMetrics metrics, FT_Face face ) { - FT_Bool started = 0, same_width = 1; - FT_Fixed advance = 0, old_advance = 0; + FT_Bool started = 0, same_width = 1; + FT_Long advance = 0, old_advance = 0; /* If HarfBuzz is not available, we need a pointer to a single */ /* unsigned long value. */ @@ -642,10 +633,11 @@ /* Initialize global metrics. */ FT_LOCAL_DEF( FT_Error ) - af_cjk_metrics_init( AF_CJKMetrics metrics, - FT_Face face ) + af_cjk_metrics_init( AF_StyleMetrics metrics_, /* AF_CJKMetrics */ + FT_Face face ) { - FT_CharMap oldmap = face->charmap; + AF_CJKMetrics metrics = (AF_CJKMetrics)metrics_; + FT_CharMap oldmap = face->charmap; metrics->units_per_em = face->units_per_EM; @@ -657,7 +649,7 @@ af_cjk_metrics_check_digits( metrics, face ); } - FT_Set_Charmap( face, oldmap ); + face->charmap = oldmap; return FT_Err_Ok; } @@ -728,7 +720,7 @@ delta2 = FT_MulFix( delta2, scale ); - FT_TRACE5(( "delta: %d", delta1 )); + FT_TRACE5(( "delta: %ld", delta1 )); if ( delta2 < 32 ) delta2 = 0; #if 0 @@ -737,20 +729,22 @@ #endif else delta2 = FT_PIX_ROUND( delta2 ); - FT_TRACE5(( "/%d\n", delta2 )); + FT_TRACE5(( "/%ld\n", delta2 )); if ( delta1 < 0 ) delta2 = -delta2; blue->shoot.fit = blue->ref.fit - delta2; - FT_TRACE5(( ">> active cjk blue zone %c%d[%ld/%ld]:\n" - " ref: cur=%.2f fit=%.2f\n" - " shoot: cur=%.2f fit=%.2f\n", + FT_TRACE5(( ">> active cjk blue zone %c%d[%ld/%ld]:\n", ( dim == AF_DIMENSION_HORZ ) ? 'H' : 'V', - nn, blue->ref.org, blue->shoot.org, - blue->ref.cur / 64.0, blue->ref.fit / 64.0, - blue->shoot.cur / 64.0, blue->shoot.fit / 64.0 )); + nn, blue->ref.org, blue->shoot.org )); + FT_TRACE5(( " ref: cur=%.2f fit=%.2f\n", + (double)blue->ref.cur / 64, + (double)blue->ref.fit / 64 )); + FT_TRACE5(( " shoot: cur=%.2f fit=%.2f\n", + (double)blue->shoot.cur / 64, + (double)blue->shoot.fit / 64 )); blue->flags |= AF_CJK_BLUE_ACTIVE; } @@ -761,9 +755,12 @@ /* Scale global values in both directions. */ FT_LOCAL_DEF( void ) - af_cjk_metrics_scale( AF_CJKMetrics metrics, - AF_Scaler scaler ) + af_cjk_metrics_scale( AF_StyleMetrics metrics_, /* AF_CJKMetrics */ + AF_Scaler scaler ) { + AF_CJKMetrics metrics = (AF_CJKMetrics)metrics_; + + /* we copy the whole structure since the x and y scaling values */ /* are not modified, contrary to e.g. the `latin' auto-hinter */ metrics->root.scaler = *scaler; @@ -776,11 +773,14 @@ /* Extract standard_width from writing system/script specific */ /* metrics class. */ - FT_LOCAL_DEF( void ) - af_cjk_get_standard_widths( AF_CJKMetrics metrics, - FT_Pos* stdHW, - FT_Pos* stdVW ) + FT_CALLBACK_DEF( void ) + af_cjk_get_standard_widths( AF_StyleMetrics metrics_, /* AF_CJKMetrics */ + FT_Pos* stdHW, + FT_Pos* stdVW ) { + AF_CJKMetrics metrics = (AF_CJKMetrics)metrics_; + + if ( stdHW ) *stdHW = metrics->axis[AF_DIMENSION_VERT].standard_width; @@ -850,7 +850,7 @@ { AF_AxisHints axis = &hints->axis[dim]; AF_Segment segments = axis->segments; - AF_Segment segment_limit = segments + axis->num_segments; + AF_Segment segment_limit = FT_OFFSET( segments, axis->num_segments ); AF_Direction major_dir = axis->major_dir; AF_Segment seg1, seg2; FT_Pos len_threshold; @@ -1012,7 +1012,7 @@ AF_CJKAxis laxis = &((AF_CJKMetrics)hints->metrics)->axis[dim]; AF_Segment segments = axis->segments; - AF_Segment segment_limit = segments + axis->num_segments; + AF_Segment segment_limit = FT_OFFSET( segments, axis->num_segments ); AF_Segment seg; FT_Fixed scale; @@ -1051,7 +1051,7 @@ { AF_Edge found = NULL; FT_Pos best = 0xFFFFU; - FT_Int ee; + FT_UInt ee; /* look for an edge corresponding to the segment */ @@ -1160,7 +1160,7 @@ */ { AF_Edge edges = axis->edges; - AF_Edge edge_limit = edges + axis->num_edges; + AF_Edge edge_limit = FT_OFFSET( edges, axis->num_edges ); AF_Edge edge; @@ -1298,7 +1298,7 @@ { AF_AxisHints axis = &hints->axis[dim]; AF_Edge edge = axis->edges; - AF_Edge edge_limit = edge + axis->num_edges; + AF_Edge edge_limit = FT_OFFSET( edge, axis->num_edges ); AF_CJKAxis cjk = &metrics->axis[dim]; FT_Fixed scale = cjk->scale; FT_Pos best_dist0; /* initial threshold */ @@ -1381,9 +1381,10 @@ /* Initalize hinting engine. */ FT_LOCAL_DEF( FT_Error ) - af_cjk_hints_init( AF_GlyphHints hints, - AF_CJKMetrics metrics ) + af_cjk_hints_init( AF_GlyphHints hints, + AF_StyleMetrics metrics_ ) /* AF_CJKMetrics */ { + AF_CJKMetrics metrics = (AF_CJKMetrics)metrics_; FT_Render_Mode mode; FT_UInt32 scaler_flags, other_flags; @@ -1402,11 +1403,6 @@ /* compute flags depending on render mode, etc. */ mode = metrics->root.scaler.render_mode; -#if 0 /* AF_CONFIG_OPTION_USE_WARPER */ - if ( mode == FT_RENDER_MODE_LCD || mode == FT_RENDER_MODE_LCD_V ) - metrics->root.scaler.render_mode = mode = FT_RENDER_MODE_NORMAL; -#endif - scaler_flags = hints->scaler_flags; other_flags = 0; @@ -1435,12 +1431,6 @@ scaler_flags |= AF_SCALER_FLAG_NO_ADVANCE; -#ifdef AF_CONFIG_OPTION_USE_WARPER - /* get (global) warper flag */ - if ( !metrics->root.globals->module->warping ) - scaler_flags |= AF_SCALER_FLAG_NO_WARPER; -#endif - hints->scaler_flags = scaler_flags; hints->other_flags = other_flags; @@ -1644,11 +1634,13 @@ stem_edge->pos = base_edge->pos + fitted_width; - FT_TRACE5(( " CJKLINK: edge %d @%d (opos=%.2f) linked to %.2f," + FT_TRACE5(( " CJKLINK: edge %td @%d (opos=%.2f) linked to %.2f," " dist was %.2f, now %.2f\n", stem_edge - hints->axis[dim].edges, stem_edge->fpos, - stem_edge->opos / 64.0, stem_edge->pos / 64.0, - dist / 64.0, fitted_width / 64.0 )); + (double)stem_edge->opos / 64, + (double)stem_edge->pos / 64, + (double)dist / 64, + (double)fitted_width / 64 )); } @@ -1816,7 +1808,7 @@ { AF_AxisHints axis = &hints->axis[dim]; AF_Edge edges = axis->edges; - AF_Edge edge_limit = edges + axis->num_edges; + AF_Edge edge_limit = FT_OFFSET( edges, axis->num_edges ); FT_PtrDist n_edges; AF_Edge edge; AF_Edge anchor = NULL; @@ -1866,10 +1858,10 @@ continue; #ifdef FT_DEBUG_LEVEL_TRACE - FT_TRACE5(( " CJKBLUE: edge %d @%d (opos=%.2f) snapped to %.2f," + FT_TRACE5(( " CJKBLUE: edge %td @%d (opos=%.2f) snapped to %.2f," " was %.2f\n", - edge1 - edges, edge1->fpos, edge1->opos / 64.0, - blue->fit / 64.0, edge1->pos / 64.0 )); + edge1 - edges, edge1->fpos, (double)edge1->opos / 64, + (double)blue->fit / 64, (double)edge1->pos / 64 )); num_actions++; #endif @@ -1930,7 +1922,7 @@ /* this should not happen, but it's better to be safe */ if ( edge2->blue_edge ) { - FT_TRACE5(( "ASSERTION FAILED for edge %d\n", edge2-edges )); + FT_TRACE5(( "ASSERTION FAILED for edge %td\n", edge2 - edges )); af_cjk_align_linked_edge( hints, dim, edge2, edge ); edge->flags |= AF_EDGE_DONE; @@ -2042,8 +2034,8 @@ #if 0 printf( "stem (%d,%d) adjusted (%.1f,%.1f)\n", edge - edges, edge2 - edges, - ( edge->pos - edge->opos ) / 64.0, - ( edge2->pos - edge2->opos ) / 64.0 ); + (double)( edge->pos - edge->opos ) / 64, + (double)( edge2->pos - edge2->opos ) / 64 ); #endif anchor = edge; @@ -2195,7 +2187,7 @@ { AF_AxisHints axis = & hints->axis[dim]; AF_Edge edges = axis->edges; - AF_Edge edge_limit = edges + axis->num_edges; + AF_Edge edge_limit = FT_OFFSET( edges, axis->num_edges ); AF_Edge edge; FT_Bool snapping; @@ -2282,11 +2274,13 @@ /* Apply the complete hinting algorithm to a CJK glyph. */ FT_LOCAL_DEF( FT_Error ) - af_cjk_hints_apply( FT_UInt glyph_index, - AF_GlyphHints hints, - FT_Outline* outline, - AF_CJKMetrics metrics ) + af_cjk_hints_apply( FT_UInt glyph_index, + AF_GlyphHints hints, + FT_Outline* outline, + AF_StyleMetrics metrics_ ) /* AF_CJKMetrics */ { + AF_CJKMetrics metrics = (AF_CJKMetrics)metrics_; + FT_Error error; int dim; @@ -2323,25 +2317,6 @@ if ( ( dim == AF_DIMENSION_HORZ && AF_HINTS_DO_HORIZONTAL( hints ) ) || ( dim == AF_DIMENSION_VERT && AF_HINTS_DO_VERTICAL( hints ) ) ) { - -#ifdef AF_CONFIG_OPTION_USE_WARPER - if ( dim == AF_DIMENSION_HORZ && - metrics->root.scaler.render_mode == FT_RENDER_MODE_NORMAL && - AF_HINTS_DO_WARP( hints ) ) - { - AF_WarperRec warper; - FT_Fixed scale; - FT_Pos delta; - - - af_warper_compute( &warper, hints, (AF_Dimension)dim, - &scale, &delta ); - af_glyph_hints_scale_dim( hints, (AF_Dimension)dim, - scale, delta ); - continue; - } -#endif /* AF_CONFIG_OPTION_USE_WARPER */ - af_cjk_hint_edges( hints, (AF_Dimension)dim ); af_cjk_align_edge_points( hints, (AF_Dimension)dim ); af_glyph_hints_align_strong_points( hints, (AF_Dimension)dim ); diff --git a/src/font/freetype-2.10.2/src/autofit/afcjk.h b/3rdparty/freetype-2.13.2/src/autofit/afcjk.h similarity index 87% rename from src/font/freetype-2.10.2/src/autofit/afcjk.h rename to 3rdparty/freetype-2.13.2/src/autofit/afcjk.h index fd0f451aa..f380ef6e0 100644 --- a/src/font/freetype-2.10.2/src/autofit/afcjk.h +++ b/3rdparty/freetype-2.13.2/src/autofit/afcjk.h @@ -4,7 +4,7 @@ * * Auto-fitter hinting routines for CJK writing system (specification). * - * Copyright (C) 2006-2020 by + * Copyright (C) 2006-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -103,22 +103,22 @@ FT_BEGIN_HEADER #ifdef AF_CONFIG_OPTION_CJK FT_LOCAL( FT_Error ) - af_cjk_metrics_init( AF_CJKMetrics metrics, - FT_Face face ); + af_cjk_metrics_init( AF_StyleMetrics metrics, + FT_Face face ); FT_LOCAL( void ) - af_cjk_metrics_scale( AF_CJKMetrics metrics, - AF_Scaler scaler ); + af_cjk_metrics_scale( AF_StyleMetrics metrics, + AF_Scaler scaler ); FT_LOCAL( FT_Error ) - af_cjk_hints_init( AF_GlyphHints hints, - AF_CJKMetrics metrics ); + af_cjk_hints_init( AF_GlyphHints hints, + AF_StyleMetrics metrics ); FT_LOCAL( FT_Error ) - af_cjk_hints_apply( FT_UInt glyph_index, - AF_GlyphHints hints, - FT_Outline* outline, - AF_CJKMetrics metrics ); + af_cjk_hints_apply( FT_UInt glyph_index, + AF_GlyphHints hints, + FT_Outline* outline, + AF_StyleMetrics metrics ); /* shared; called from afindic.c */ FT_LOCAL( void ) diff --git a/src/font/freetype-2.10.2/src/autofit/afcover.h b/3rdparty/freetype-2.13.2/src/autofit/afcover.h similarity index 99% rename from src/font/freetype-2.10.2/src/autofit/afcover.h rename to 3rdparty/freetype-2.13.2/src/autofit/afcover.h index 03085ad07..102ed4278 100644 --- a/src/font/freetype-2.10.2/src/autofit/afcover.h +++ b/3rdparty/freetype-2.13.2/src/autofit/afcover.h @@ -4,7 +4,7 @@ * * Auto-fitter coverages (specification only). * - * Copyright (C) 2013-2020 by + * Copyright (C) 2013-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, diff --git a/src/font/freetype-2.10.2/src/autofit/afdummy.c b/3rdparty/freetype-2.13.2/src/autofit/afdummy.c similarity index 98% rename from src/font/freetype-2.10.2/src/autofit/afdummy.c rename to 3rdparty/freetype-2.13.2/src/autofit/afdummy.c index 77d31df97..a4629b528 100644 --- a/src/font/freetype-2.10.2/src/autofit/afdummy.c +++ b/3rdparty/freetype-2.13.2/src/autofit/afdummy.c @@ -5,7 +5,7 @@ * Auto-fitter dummy routines to be used if no hinting should be * performed (body). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, diff --git a/src/font/freetype-2.10.2/src/autofit/afdummy.h b/3rdparty/freetype-2.13.2/src/autofit/afdummy.h similarity index 96% rename from src/font/freetype-2.10.2/src/autofit/afdummy.h rename to 3rdparty/freetype-2.13.2/src/autofit/afdummy.h index efd799e84..a7af3f62c 100644 --- a/src/font/freetype-2.10.2/src/autofit/afdummy.h +++ b/3rdparty/freetype-2.13.2/src/autofit/afdummy.h @@ -5,7 +5,7 @@ * Auto-fitter dummy routines to be used if no hinting should be * performed (specification). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, diff --git a/src/font/freetype-2.10.2/src/autofit/aferrors.h b/3rdparty/freetype-2.13.2/src/autofit/aferrors.h similarity index 90% rename from src/font/freetype-2.10.2/src/autofit/aferrors.h rename to 3rdparty/freetype-2.13.2/src/autofit/aferrors.h index 6c7d0e1d7..88faf05c9 100644 --- a/src/font/freetype-2.10.2/src/autofit/aferrors.h +++ b/3rdparty/freetype-2.13.2/src/autofit/aferrors.h @@ -4,7 +4,7 @@ * * Autofitter error codes (specification only). * - * Copyright (C) 2005-2020 by + * Copyright (C) 2005-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -26,7 +26,7 @@ #ifndef AFERRORS_H_ #define AFERRORS_H_ -#include FT_MODULE_ERRORS_H +#include #undef FTERRORS_H_ @@ -34,7 +34,7 @@ #define FT_ERR_PREFIX AF_Err_ #define FT_ERR_BASE FT_Mod_Err_Autofit -#include FT_ERRORS_H +#include #endif /* AFERRORS_H_ */ diff --git a/src/font/freetype-2.10.2/src/autofit/afglobal.c b/3rdparty/freetype-2.13.2/src/autofit/afglobal.c similarity index 87% rename from src/font/freetype-2.10.2/src/autofit/afglobal.c rename to 3rdparty/freetype-2.13.2/src/autofit/afglobal.c index 5ad4ea921..b1957570f 100644 --- a/src/font/freetype-2.10.2/src/autofit/afglobal.c +++ b/3rdparty/freetype-2.13.2/src/autofit/afglobal.c @@ -4,7 +4,7 @@ * * Auto-fitter routines to compute global hinting values (body). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,7 +19,8 @@ #include "afglobal.h" #include "afranges.h" #include "afshaper.h" -#include FT_INTERNAL_DEBUG_H +#include "afws-decl.h" +#include /************************************************************************** @@ -32,11 +33,6 @@ #define FT_COMPONENT afglobal - /* get writing system specific header files */ -#undef WRITING_SYSTEM -#define WRITING_SYSTEM( ws, WS ) /* empty */ -#include "afwrtsys.h" - #include "aferrors.h" @@ -74,7 +70,7 @@ af_writing_system_classes[] = { -#include "afwrtsys.h" +#include "afws-iter.h" NULL /* do not remove */ }; @@ -133,13 +129,13 @@ FT_Face face = globals->face; FT_CharMap old_charmap = face->charmap; FT_UShort* gstyles = globals->glyph_styles; - FT_UInt ss; + FT_UShort ss; + FT_UShort dflt = 0xFFFFU; /* a non-valid value */ FT_UInt i; - FT_UInt dflt = ~0U; /* a non-valid value */ /* the value AF_STYLE_UNASSIGNED means `uncovered glyph' */ - for ( i = 0; i < (FT_UInt)globals->glyph_count; i++ ) + for ( i = 0; i < globals->glyph_count; i++ ) gstyles[i] = AF_STYLE_UNASSIGNED; error = FT_Select_Charmap( face, FT_ENCODING_UNICODE ); @@ -172,8 +168,7 @@ */ if ( style_class->coverage == AF_COVERAGE_DEFAULT ) { - if ( (FT_UInt)style_class->script == - globals->module->default_script ) + if ( style_class->script == globals->module->default_script ) dflt = ss; for ( range = script_class->script_uni_ranges; @@ -187,9 +182,9 @@ gindex = FT_Get_Char_Index( face, charcode ); if ( gindex != 0 && - gindex < (FT_ULong)globals->glyph_count && + gindex < globals->glyph_count && ( gstyles[gindex] & AF_STYLE_MASK ) == AF_STYLE_UNASSIGNED ) - gstyles[gindex] = (FT_UShort)ss; + gstyles[gindex] = ss; for (;;) { @@ -198,9 +193,9 @@ if ( gindex == 0 || charcode > range->last ) break; - if ( gindex < (FT_ULong)globals->glyph_count && + if ( gindex < globals->glyph_count && ( gstyles[gindex] & AF_STYLE_MASK ) == AF_STYLE_UNASSIGNED ) - gstyles[gindex] = (FT_UShort)ss; + gstyles[gindex] = ss; } } @@ -215,9 +210,9 @@ gindex = FT_Get_Char_Index( face, charcode ); - if ( gindex != 0 && - gindex < (FT_ULong)globals->glyph_count && - ( gstyles[gindex] & AF_STYLE_MASK ) == (FT_UShort)ss ) + if ( gindex != 0 && + gindex < globals->glyph_count && + ( gstyles[gindex] & AF_STYLE_MASK ) == ss ) gstyles[gindex] |= AF_NONBASE; for (;;) @@ -227,8 +222,8 @@ if ( gindex == 0 || charcode > range->last ) break; - if ( gindex < (FT_ULong)globals->glyph_count && - ( gstyles[gindex] & AF_STYLE_MASK ) == (FT_UShort)ss ) + if ( gindex < globals->glyph_count && + ( gstyles[gindex] & AF_STYLE_MASK ) == ss ) gstyles[gindex] |= AF_NONBASE; } } @@ -259,7 +254,7 @@ FT_UInt gindex = FT_Get_Char_Index( face, i ); - if ( gindex != 0 && gindex < (FT_ULong)globals->glyph_count ) + if ( gindex != 0 && gindex < globals->glyph_count ) gstyles[gindex] |= AF_DIGIT; } @@ -270,7 +265,7 @@ */ if ( globals->module->fallback_style != AF_STYLE_UNASSIGNED ) { - FT_Long nn; + FT_UInt nn; for ( nn = 0; nn < globals->glyph_count; nn++ ) @@ -285,16 +280,16 @@ #ifdef FT_DEBUG_LEVEL_TRACE - FT_TRACE4(( "\n" - "style coverage\n" - "==============\n" - "\n" )); + FT_TRACE4(( "\n" )); + FT_TRACE4(( "style coverage\n" )); + FT_TRACE4(( "==============\n" )); + FT_TRACE4(( "\n" )); for ( ss = 0; af_style_classes[ss]; ss++ ) { AF_StyleClass style_class = af_style_classes[ss]; FT_UInt count = 0; - FT_Long idx; + FT_UInt idx; FT_TRACE4(( "%s:\n", af_style_names[style_class->style] )); @@ -322,7 +317,7 @@ #endif /* FT_DEBUG_LEVEL_TRACE */ - FT_Set_Charmap( face, old_charmap ); + face->charmap = old_charmap; return error; } @@ -341,13 +336,15 @@ /* we allocate an AF_FaceGlobals structure together */ /* with the glyph_styles array */ - if ( FT_ALLOC( globals, - sizeof ( *globals ) + - (FT_ULong)face->num_glyphs * sizeof ( FT_UShort ) ) ) + if ( FT_QALLOC( globals, + sizeof ( *globals ) + + (FT_ULong)face->num_glyphs * sizeof ( FT_UShort ) ) ) goto Exit; + FT_ZERO( &globals->metrics ); + globals->face = face; - globals->glyph_count = face->num_glyphs; + globals->glyph_count = (FT_UInt)face->num_glyphs; /* right after the globals structure come the glyph styles */ globals->glyph_styles = (FT_UShort*)( globals + 1 ); globals->module = module; @@ -359,7 +356,7 @@ globals->scale_down_factor = 0; #ifdef FT_CONFIG_OPTION_USE_HARFBUZZ - globals->hb_font = hb_ft_font_create( face, NULL ); + globals->hb_font = hb_ft_font_create_( face, NULL ); globals->hb_buf = hb_buffer_create(); #endif @@ -379,8 +376,11 @@ FT_LOCAL_DEF( void ) - af_face_globals_free( AF_FaceGlobals globals ) + af_face_globals_free( void* globals_ ) { + AF_FaceGlobals globals = (AF_FaceGlobals)globals_; + + if ( globals ) { FT_Memory memory = globals->face->memory; @@ -431,7 +431,7 @@ FT_Error error = FT_Err_Ok; - if ( gindex >= (FT_ULong)globals->glyph_count ) + if ( gindex >= globals->glyph_count ) { error = FT_THROW( Invalid_Argument ); goto Exit; @@ -478,6 +478,10 @@ { style = (AF_Style)( globals->glyph_styles[gindex] & AF_STYLE_UNASSIGNED ); + /* IMPORTANT: Clear the error code, see + * https://gitlab.freedesktop.org/freetype/freetype/-/issues/1063 + */ + error = FT_Err_Ok; goto Again; } @@ -499,7 +503,7 @@ af_face_globals_is_digit( AF_FaceGlobals globals, FT_UInt gindex ) { - if ( gindex < (FT_ULong)globals->glyph_count ) + if ( gindex < globals->glyph_count ) return FT_BOOL( globals->glyph_styles[gindex] & AF_DIGIT ); return FT_BOOL( 0 ); diff --git a/src/font/freetype-2.10.2/src/autofit/afglobal.h b/3rdparty/freetype-2.13.2/src/autofit/afglobal.h similarity index 96% rename from src/font/freetype-2.10.2/src/autofit/afglobal.h rename to 3rdparty/freetype-2.13.2/src/autofit/afglobal.h index fecf7af97..66170e419 100644 --- a/src/font/freetype-2.10.2/src/autofit/afglobal.h +++ b/3rdparty/freetype-2.13.2/src/autofit/afglobal.h @@ -5,7 +5,7 @@ * Auto-fitter routines to compute global hinting values * (specification). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -105,7 +105,7 @@ FT_BEGIN_HEADER typedef struct AF_FaceGlobalsRec_ { FT_Face face; - FT_Long glyph_count; /* same as face->num_glyphs */ + FT_UInt glyph_count; /* unsigned face->num_glyphs */ FT_UShort* glyph_styles; #ifdef FT_CONFIG_OPTION_USE_HARFBUZZ @@ -156,9 +156,9 @@ FT_BEGIN_HEADER AF_StyleMetrics *ametrics ); FT_LOCAL( void ) - af_face_globals_free( AF_FaceGlobals globals ); + af_face_globals_free( void* globals ); - FT_LOCAL_DEF( FT_Bool ) + FT_LOCAL( FT_Bool ) af_face_globals_is_digit( AF_FaceGlobals globals, FT_UInt gindex ); diff --git a/src/font/freetype-2.10.2/src/autofit/afhints.c b/3rdparty/freetype-2.13.2/src/autofit/afhints.c similarity index 88% rename from src/font/freetype-2.10.2/src/autofit/afhints.c rename to 3rdparty/freetype-2.13.2/src/autofit/afhints.c index 5a123b2ba..e4a378fbf 100644 --- a/src/font/freetype-2.10.2/src/autofit/afhints.c +++ b/3rdparty/freetype-2.13.2/src/autofit/afhints.c @@ -4,7 +4,7 @@ * * Auto-fitter hinting routines (body). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -18,8 +18,8 @@ #include "afhints.h" #include "aferrors.h" -#include FT_INTERNAL_CALC_H -#include FT_INTERNAL_DEBUG_H +#include +#include /************************************************************************** @@ -32,6 +32,104 @@ #define FT_COMPONENT afhints + FT_LOCAL_DEF( void ) + af_sort_pos( FT_UInt count, + FT_Pos* table ) + { + FT_UInt i, j; + FT_Pos swap; + + + for ( i = 1; i < count; i++ ) + { + for ( j = i; j > 0; j-- ) + { + if ( table[j] >= table[j - 1] ) + break; + + swap = table[j]; + table[j] = table[j - 1]; + table[j - 1] = swap; + } + } + } + + + FT_LOCAL_DEF( void ) + af_sort_and_quantize_widths( FT_UInt* count, + AF_Width table, + FT_Pos threshold ) + { + FT_UInt i, j; + FT_UInt cur_idx; + FT_Pos cur_val; + FT_Pos sum; + AF_WidthRec swap; + + + if ( *count == 1 ) + return; + + /* sort */ + for ( i = 1; i < *count; i++ ) + { + for ( j = i; j > 0; j-- ) + { + if ( table[j].org >= table[j - 1].org ) + break; + + swap = table[j]; + table[j] = table[j - 1]; + table[j - 1] = swap; + } + } + + cur_idx = 0; + cur_val = table[cur_idx].org; + + /* compute and use mean values for clusters not larger than */ + /* `threshold'; this is very primitive and might not yield */ + /* the best result, but normally, using reference character */ + /* `o', `*count' is 2, so the code below is fully sufficient */ + for ( i = 1; i < *count; i++ ) + { + if ( table[i].org - cur_val > threshold || + i == *count - 1 ) + { + sum = 0; + + /* fix loop for end of array */ + if ( table[i].org - cur_val <= threshold && + i == *count - 1 ) + i++; + + for ( j = cur_idx; j < i; j++ ) + { + sum += table[j].org; + table[j].org = 0; + } + table[cur_idx].org = sum / (FT_Pos)j; + + if ( i < *count - 1 ) + { + cur_idx = i + 1; + cur_val = table[cur_idx].org; + } + } + } + + cur_idx = 1; + + /* compress array to remove zero values */ + for ( i = 1; i < *count; i++ ) + { + if ( table[i].org ) + table[cur_idx++] = table[i]; + } + + *count = cur_idx; + } + /* Get new segment for given axis. */ FT_LOCAL_DEF( FT_Error ) @@ -53,9 +151,9 @@ } else if ( axis->num_segments >= axis->max_segments ) { - FT_Int old_max = axis->max_segments; - FT_Int new_max = old_max; - FT_Int big_max = (FT_Int)( FT_INT_MAX / sizeof ( *segment ) ); + FT_UInt old_max = axis->max_segments; + FT_UInt new_max = old_max; + FT_UInt big_max = FT_INT_MAX / sizeof ( *segment ); if ( old_max >= big_max ) @@ -95,7 +193,7 @@ /* Get new edge for given axis, direction, and position, */ /* without initializing the edge itself. */ - FT_LOCAL( FT_Error ) + FT_LOCAL_DEF( FT_Error ) af_axis_hints_new_edge( AF_AxisHints axis, FT_Int fpos, AF_Direction dir, @@ -118,9 +216,9 @@ } else if ( axis->num_edges >= axis->max_edges ) { - FT_Int old_max = axis->max_edges; - FT_Int new_max = old_max; - FT_Int big_max = (FT_Int)( FT_INT_MAX / sizeof ( *edge ) ); + FT_UInt old_max = axis->max_edges; + FT_UInt new_max = old_max; + FT_UInt big_max = FT_INT_MAX / sizeof ( *edge ); if ( old_max >= big_max ) @@ -222,8 +320,9 @@ static char* - af_print_idx( char* p, - int idx ) + af_print_idx( char* p, + size_t n, + int idx ) { if ( idx == -1 ) { @@ -232,7 +331,7 @@ p[2] = '\0'; } else - ft_sprintf( p, "%d", idx ); + ft_snprintf( p, n, "%d", idx ); return p; } @@ -359,12 +458,12 @@ " %5d %5d %7.2f %7.2f %7.2f %7.2f" " %5s %5s %5s %5s\n", point_idx, - af_print_idx( buf1, + af_print_idx( buf1, 16, af_get_edge_index( hints, segment_idx_1, 1 ) ), - af_print_idx( buf2, segment_idx_1 ), - af_print_idx( buf3, + af_print_idx( buf2, 16, segment_idx_1 ), + af_print_idx( buf3, 16, af_get_edge_index( hints, segment_idx_0, 0 ) ), - af_print_idx( buf4, segment_idx_0 ), + af_print_idx( buf4, 16, segment_idx_0 ), ( point->flags & AF_FLAG_NEAR ) ? " near " : ( point->flags & AF_FLAG_WEAK_INTERPOLATION ) @@ -373,23 +472,27 @@ point->fx, point->fy, - point->ox / 64.0, - point->oy / 64.0, - point->x / 64.0, - point->y / 64.0, - - af_print_idx( buf5, af_get_strong_edge_index( hints, - point->before, - 1 ) ), - af_print_idx( buf6, af_get_strong_edge_index( hints, - point->after, - 1 ) ), - af_print_idx( buf7, af_get_strong_edge_index( hints, - point->before, - 0 ) ), - af_print_idx( buf8, af_get_strong_edge_index( hints, - point->after, - 0 ) ) )); + (double)point->ox / 64, + (double)point->oy / 64, + (double)point->x / 64, + (double)point->y / 64, + + af_print_idx( buf5, 16, + af_get_strong_edge_index( hints, + point->before, + 1 ) ), + af_print_idx( buf6, 16, + af_get_strong_edge_index( hints, + point->after, + 1 ) ), + af_print_idx( buf7, 16, + af_get_strong_edge_index( hints, + point->before, + 0 ) ), + af_print_idx( buf8, 16, + af_get_strong_edge_index( hints, + point->after, + 0 ) ) )); } AF_DUMP(( "\n" )); } @@ -476,9 +579,12 @@ AF_INDEX_NUM( seg->first, points ), AF_INDEX_NUM( seg->last, points ), - af_print_idx( buf1, AF_INDEX_NUM( seg->link, segments ) ), - af_print_idx( buf2, AF_INDEX_NUM( seg->serif, segments ) ), - af_print_idx( buf3, AF_INDEX_NUM( seg->edge, edges ) ), + af_print_idx( buf1, 16, + AF_INDEX_NUM( seg->link, segments ) ), + af_print_idx( buf2, 16, + AF_INDEX_NUM( seg->serif, segments ) ), + af_print_idx( buf3, 16, + AF_INDEX_NUM( seg->edge, edges ) ), seg->height, seg->height - ( seg->max_coord - seg->min_coord ), @@ -499,7 +605,7 @@ FT_Error af_glyph_hints_get_num_segments( AF_GlyphHints hints, FT_Int dimension, - FT_Int* num_segments ) + FT_UInt* num_segments ) { AF_Dimension dim; AF_AxisHints axis; @@ -525,7 +631,7 @@ FT_Error af_glyph_hints_get_segment_offset( AF_GlyphHints hints, FT_Int dimension, - FT_Int idx, + FT_UInt idx, FT_Pos *offset, FT_Bool *is_blue, FT_Pos *blue_offset ) @@ -542,7 +648,7 @@ axis = &hints->axis[dim]; - if ( idx < 0 || idx >= axis->num_segments ) + if ( idx >= axis->num_segments ) return FT_THROW( Invalid_Argument ); seg = &axis->segments[idx]; @@ -594,13 +700,13 @@ if ( dimension == AF_DIMENSION_HORZ ) AF_DUMP(( "Table of %s edges (1px=%.2fu, 10u=%.2fpx):\n", "vertical", - 65536.0 * 64.0 / hints->x_scale, - 10.0 * hints->x_scale / 65536.0 / 64.0 )); + 65536 * 64 / (double)hints->x_scale, + 10 * (double)hints->x_scale / 65536 / 64 )); else AF_DUMP(( "Table of %s edges (1px=%.2fu, 10u=%.2fpx):\n", "horizontal", - 65536.0 * 64.0 / hints->y_scale, - 10.0 * hints->y_scale / 65536.0 / 64.0 )); + 65536 * 64 / (double)hints->y_scale, + 10 * (double)hints->y_scale / 65536 / 64 )); if ( axis->num_edges ) { @@ -616,14 +722,16 @@ AF_DUMP(( " %5d %7.2f %5s %4s %5s" " %c %7.2f %7.2f %11s\n", AF_INDEX_NUM( edge, edges ), - (int)edge->opos / 64.0, + (double)(int)edge->opos / 64, af_dir_str( (AF_Direction)edge->dir ), - af_print_idx( buf1, AF_INDEX_NUM( edge->link, edges ) ), - af_print_idx( buf2, AF_INDEX_NUM( edge->serif, edges ) ), + af_print_idx( buf1, 16, + AF_INDEX_NUM( edge->link, edges ) ), + af_print_idx( buf2, 16, + AF_INDEX_NUM( edge->serif, edges ) ), edge->blue_edge ? 'y' : 'n', - edge->opos / 64.0, - edge->pos / 64.0, + (double)edge->opos / 64, + (double)edge->pos / 64, af_edge_flags_to_string( edge->flags ) )); AF_DUMP(( "\n" )); } @@ -764,7 +872,7 @@ { FT_Error error = FT_Err_Ok; AF_Point points; - FT_UInt old_max, new_max; + FT_Int old_max, new_max; FT_Fixed x_scale = hints->x_scale; FT_Fixed y_scale = hints->y_scale; FT_Pos x_delta = hints->x_delta; @@ -781,8 +889,8 @@ hints->axis[1].num_edges = 0; /* first of all, reallocate the contours array if necessary */ - new_max = (FT_UInt)outline->n_contours; - old_max = (FT_UInt)hints->max_contours; + new_max = outline->n_contours; + old_max = hints->max_contours; if ( new_max <= AF_CONTOURS_EMBEDDED ) { @@ -797,12 +905,12 @@ if ( hints->contours == hints->embedded.contours ) hints->contours = NULL; - new_max = ( new_max + 3 ) & ~3U; /* round up to a multiple of 4 */ + new_max = ( new_max + 3 ) & ~3; /* round up to a multiple of 4 */ if ( FT_RENEW_ARRAY( hints->contours, old_max, new_max ) ) goto Exit; - hints->max_contours = (FT_Int)new_max; + hints->max_contours = new_max; } /* @@ -810,8 +918,8 @@ * note that we reserve two additional point positions, used to * hint metrics appropriately */ - new_max = (FT_UInt)( outline->n_points + 2 ); - old_max = (FT_UInt)hints->max_points; + new_max = outline->n_points + 2; + old_max = hints->max_points; if ( new_max <= AF_POINTS_EMBEDDED ) { @@ -826,12 +934,12 @@ if ( hints->points == hints->embedded.points ) hints->points = NULL; - new_max = ( new_max + 2 + 7 ) & ~7U; /* round up to a multiple of 8 */ + new_max = ( new_max + 2 + 7 ) & ~7; /* round up to a multiple of 8 */ if ( FT_RENEW_ARRAY( hints->points, old_max, new_max ) ) goto Exit; - hints->max_points = (FT_Int)new_max; + hints->max_points = new_max; } hints->num_points = outline->n_points; @@ -855,9 +963,6 @@ hints->x_delta = x_delta; hints->y_delta = y_delta; - hints->xmin_delta = 0; - hints->xmax_delta = 0; - points = hints->points; if ( hints->num_points == 0 ) goto Exit; @@ -1221,7 +1326,7 @@ { AF_AxisHints axis = & hints->axis[dim]; AF_Segment segments = axis->segments; - AF_Segment segment_limit = segments + axis->num_segments; + AF_Segment segment_limit = FT_OFFSET( segments, axis->num_segments ); AF_Segment seg; @@ -1298,7 +1403,7 @@ AF_Point point_limit = points + hints->num_points; AF_AxisHints axis = &hints->axis[dim]; AF_Edge edges = axis->edges; - AF_Edge edge_limit = edges + axis->num_edges; + AF_Edge edge_limit = FT_OFFSET( edges, axis->num_edges ); FT_UInt touch_flag; @@ -1688,33 +1793,4 @@ } -#ifdef AF_CONFIG_OPTION_USE_WARPER - - /* Apply (small) warp scale and warp delta for given dimension. */ - - FT_LOCAL_DEF( void ) - af_glyph_hints_scale_dim( AF_GlyphHints hints, - AF_Dimension dim, - FT_Fixed scale, - FT_Pos delta ) - { - AF_Point points = hints->points; - AF_Point points_limit = points + hints->num_points; - AF_Point point; - - - if ( dim == AF_DIMENSION_HORZ ) - { - for ( point = points; point < points_limit; point++ ) - point->x = FT_MulFix( point->fx, scale ) + delta; - } - else - { - for ( point = points; point < points_limit; point++ ) - point->y = FT_MulFix( point->fy, scale ) + delta; - } - } - -#endif /* AF_CONFIG_OPTION_USE_WARPER */ - /* END */ diff --git a/src/font/freetype-2.10.2/src/autofit/afhints.h b/3rdparty/freetype-2.13.2/src/autofit/afhints.h similarity index 93% rename from src/font/freetype-2.10.2/src/autofit/afhints.h rename to 3rdparty/freetype-2.13.2/src/autofit/afhints.h index 6397f098f..d1cf9529b 100644 --- a/src/font/freetype-2.10.2/src/autofit/afhints.h +++ b/3rdparty/freetype-2.13.2/src/autofit/afhints.h @@ -4,7 +4,7 @@ * * Auto-fitter hinting routines (specification). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -21,8 +21,6 @@ #include "aftypes.h" -#define xxAF_SORT_SEGMENTS - FT_BEGIN_HEADER /* @@ -310,15 +308,12 @@ FT_BEGIN_HEADER typedef struct AF_AxisHintsRec_ { - FT_Int num_segments; /* number of used segments */ - FT_Int max_segments; /* number of allocated segments */ + FT_UInt num_segments; /* number of used segments */ + FT_UInt max_segments; /* number of allocated segments */ AF_Segment segments; /* segments array */ -#ifdef AF_SORT_SEGMENTS - FT_Int mid_segments; -#endif - FT_Int num_edges; /* number of used edges */ - FT_Int max_edges; /* number of allocated edges */ + FT_UInt num_edges; /* number of used edges */ + FT_UInt max_edges; /* number of allocated edges */ AF_Edge edges; /* edges array */ AF_Direction major_dir; /* either vertical or horizontal */ @@ -362,9 +357,6 @@ FT_BEGIN_HEADER /* implementations */ AF_StyleMetrics metrics; - FT_Pos xmin_delta; /* used for warping */ - FT_Pos xmax_delta; - /* Two arrays to avoid allocation penalty. */ /* The `embedded' structure must be the last element! */ struct @@ -383,14 +375,14 @@ FT_BEGIN_HEADER #ifdef FT_DEBUG_AUTOFIT #define AF_HINTS_DO_HORIZONTAL( h ) \ - ( !_af_debug_disable_horz_hints && \ + ( !af_debug_disable_horz_hints_ && \ !AF_HINTS_TEST_SCALER( h, AF_SCALER_FLAG_NO_HORIZONTAL ) ) #define AF_HINTS_DO_VERTICAL( h ) \ - ( !_af_debug_disable_vert_hints && \ + ( !af_debug_disable_vert_hints_ && \ !AF_HINTS_TEST_SCALER( h, AF_SCALER_FLAG_NO_VERTICAL ) ) -#define AF_HINTS_DO_BLUES( h ) ( !_af_debug_disable_blue_hints ) +#define AF_HINTS_DO_BLUES( h ) ( !af_debug_disable_blue_hints_ ) #else /* !FT_DEBUG_AUTOFIT */ @@ -408,10 +400,6 @@ FT_BEGIN_HEADER #define AF_HINTS_DO_ADVANCE( h ) \ !AF_HINTS_TEST_SCALER( h, AF_SCALER_FLAG_NO_ADVANCE ) -#define AF_HINTS_DO_WARP( h ) \ - !AF_HINTS_TEST_SCALER( h, AF_SCALER_FLAG_NO_WARPER ) - - FT_LOCAL( AF_Direction ) af_direction_compute( FT_Pos dx, @@ -459,14 +447,6 @@ FT_BEGIN_HEADER af_glyph_hints_align_weak_points( AF_GlyphHints hints, AF_Dimension dim ); -#ifdef AF_CONFIG_OPTION_USE_WARPER - FT_LOCAL( void ) - af_glyph_hints_scale_dim( AF_GlyphHints hints, - AF_Dimension dim, - FT_Fixed scale, - FT_Pos delta ); -#endif - FT_LOCAL( void ) af_glyph_hints_done( AF_GlyphHints hints ); diff --git a/src/font/freetype-2.10.2/src/autofit/afindic.c b/3rdparty/freetype-2.13.2/src/autofit/afindic.c similarity index 81% rename from src/font/freetype-2.10.2/src/autofit/afindic.c rename to 3rdparty/freetype-2.13.2/src/autofit/afindic.c index bc2837a26..7fb12c63d 100644 --- a/src/font/freetype-2.10.2/src/autofit/afindic.c +++ b/3rdparty/freetype-2.13.2/src/autofit/afindic.c @@ -4,7 +4,7 @@ * * Auto-fitter hinting routines for Indic writing system (body). * - * Copyright (C) 2007-2020 by + * Copyright (C) 2007-2023 by * Rahul Bhalerao , . * * This file is part of the FreeType project, and may only be used, @@ -27,15 +27,13 @@ #include "aferrors.h" -#ifdef AF_CONFIG_OPTION_USE_WARPER -#include "afwarp.h" -#endif - - static FT_Error - af_indic_metrics_init( AF_CJKMetrics metrics, - FT_Face face ) + af_indic_metrics_init( AF_StyleMetrics metrics_, /* AF_CJKMetrics */ + FT_Face face ) { + AF_CJKMetrics metrics = (AF_CJKMetrics)metrics_; + + /* skip blue zone init in CJK routines */ FT_CharMap oldmap = face->charmap; @@ -54,15 +52,14 @@ af_cjk_metrics_check_digits( metrics, face ); } - FT_Set_Charmap( face, oldmap ); - + face->charmap = oldmap; return FT_Err_Ok; } static void - af_indic_metrics_scale( AF_CJKMetrics metrics, - AF_Scaler scaler ) + af_indic_metrics_scale( AF_StyleMetrics metrics, + AF_Scaler scaler ) { /* use CJK routines */ af_cjk_metrics_scale( metrics, scaler ); @@ -70,8 +67,8 @@ static FT_Error - af_indic_hints_init( AF_GlyphHints hints, - AF_CJKMetrics metrics ) + af_indic_hints_init( AF_GlyphHints hints, + AF_StyleMetrics metrics ) { /* use CJK routines */ return af_cjk_hints_init( hints, metrics ); @@ -79,10 +76,10 @@ static FT_Error - af_indic_hints_apply( FT_UInt glyph_index, - AF_GlyphHints hints, - FT_Outline* outline, - AF_CJKMetrics metrics ) + af_indic_hints_apply( FT_UInt glyph_index, + AF_GlyphHints hints, + FT_Outline* outline, + AF_StyleMetrics metrics ) { /* use CJK routines */ return af_cjk_hints_apply( glyph_index, hints, outline, metrics ); @@ -93,10 +90,13 @@ /* metrics class. */ static void - af_indic_get_standard_widths( AF_CJKMetrics metrics, - FT_Pos* stdHW, - FT_Pos* stdVW ) + af_indic_get_standard_widths( AF_StyleMetrics metrics_, /* AF_CJKMetrics */ + FT_Pos* stdHW, + FT_Pos* stdVW ) { + AF_CJKMetrics metrics = (AF_CJKMetrics)metrics_; + + if ( stdHW ) *stdHW = metrics->axis[AF_DIMENSION_VERT].standard_width; diff --git a/src/font/freetype-2.10.2/src/autofit/afindic.h b/3rdparty/freetype-2.13.2/src/autofit/afindic.h similarity index 96% rename from src/font/freetype-2.10.2/src/autofit/afindic.h rename to 3rdparty/freetype-2.13.2/src/autofit/afindic.h index 088b88b19..3eb67f63b 100644 --- a/src/font/freetype-2.10.2/src/autofit/afindic.h +++ b/3rdparty/freetype-2.13.2/src/autofit/afindic.h @@ -5,7 +5,7 @@ * Auto-fitter hinting routines for Indic writing system * (specification). * - * Copyright (C) 2007-2020 by + * Copyright (C) 2007-2023 by * Rahul Bhalerao , . * * This file is part of the FreeType project, and may only be used, diff --git a/src/font/freetype-2.10.2/src/autofit/aflatin.c b/3rdparty/freetype-2.13.2/src/autofit/aflatin.c similarity index 92% rename from src/font/freetype-2.10.2/src/autofit/aflatin.c rename to 3rdparty/freetype-2.13.2/src/autofit/aflatin.c index b453fcdf6..b86367aa9 100644 --- a/src/font/freetype-2.10.2/src/autofit/aflatin.c +++ b/3rdparty/freetype-2.13.2/src/autofit/aflatin.c @@ -4,7 +4,7 @@ * * Auto-fitter hinting routines for latin writing system (body). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,20 +16,14 @@ */ -#include -#include FT_ADVANCES_H -#include FT_INTERNAL_DEBUG_H +#include +#include #include "afglobal.h" #include "aflatin.h" #include "aferrors.h" -#ifdef AF_CONFIG_OPTION_USE_WARPER -#include "afwarp.h" -#endif - - /************************************************************************** * * The macro FT_COMPONENT is used in trace mode. It is an implicit @@ -64,11 +58,11 @@ AF_GlyphHintsRec hints[1]; - FT_TRACE5(( "\n" - "latin standard widths computation (style `%s')\n" - "=====================================================\n" - "\n", + FT_TRACE5(( "\n" )); + FT_TRACE5(( "latin standard widths computation (style `%s')\n", af_style_names[metrics->root.style_class->style] )); + FT_TRACE5(( "=====================================================\n" )); + FT_TRACE5(( "\n" )); af_glyph_hints_init( hints, face->memory ); @@ -155,7 +149,7 @@ goto Exit; } - FT_TRACE5(( "standard character: U+%04lX (glyph index %d)\n", + FT_TRACE5(( "standard character: U+%04lX (glyph index %ld)\n", ch, glyph_index )); error = FT_Load_Glyph( face, glyph_index, FT_LOAD_NO_SCALE ); @@ -206,7 +200,7 @@ (AF_Dimension)dim ); seg = axhints->segments; - limit = seg + axhints->num_segments; + limit = FT_OFFSET( seg, axhints->num_segments ); for ( ; seg < limit; seg++ ) { @@ -258,9 +252,9 @@ dim == AF_DIMENSION_VERT ? "horizontal" : "vertical" )); - FT_TRACE5(( " %d (standard)", axis->standard_width )); + FT_TRACE5(( " %ld (standard)", axis->standard_width )); for ( i = 1; i < axis->width_count; i++ ) - FT_TRACE5(( " %d", axis->widths[i].org )); + FT_TRACE5(( " %ld", axis->widths[i].org )); FT_TRACE5(( "\n" )); } @@ -351,9 +345,9 @@ /* we walk over the blue character strings as specified in the */ /* style's entry in the `af_blue_stringset' array */ - FT_TRACE5(( "latin blue zones computation\n" - "============================\n" - "\n" )); + FT_TRACE5(( "latin blue zones computation\n" )); + FT_TRACE5(( "============================\n" )); + FT_TRACE5(( "\n" )); #ifdef FT_CONFIG_OPTION_USE_HARFBUZZ shaper_buf = af_shaper_buf_create( face ); @@ -502,23 +496,20 @@ /* now compute min or max point indices and coordinates */ points = outline.points; best_point = -1; + best_contour_first = -1; + best_contour_last = -1; best_y = 0; /* make compiler happy */ - best_contour_first = 0; /* ditto */ - best_contour_last = 0; /* ditto */ { FT_Int nn; - FT_Int first = 0; - FT_Int last = -1; + FT_Int pp, first, last; - for ( nn = 0; nn < outline.n_contours; first = last + 1, nn++ ) + last = -1; + for ( nn = 0; nn < outline.n_contours; nn++ ) { - FT_Int old_best_point = best_point; - FT_Int pp; - - - last = outline.contours[nn]; + first = last + 1; + last = outline.contours[nn]; /* Avoid single-point contours since they are never */ /* rasterized. In some fonts, they correspond to mark */ @@ -557,7 +548,7 @@ } } - if ( best_point != old_best_point ) + if ( best_point > best_contour_last ) { best_contour_first = first; best_contour_last = last; @@ -977,9 +968,8 @@ if ( AF_LATIN_IS_X_HEIGHT_BLUE( bs ) ) blue->flags |= AF_LATIN_BLUE_ADJUSTMENT; - FT_TRACE5(( " -> reference = %ld\n" - " overshoot = %ld\n", - *blue_ref, *blue_shoot )); + FT_TRACE5(( " -> reference = %ld\n", *blue_ref )); + FT_TRACE5(( " overshoot = %ld\n", *blue_shoot )); } /* end for loop */ @@ -1032,7 +1022,7 @@ { *a = *b; FT_TRACE5(( "blue zone overlap:" - " adjusting %s %d to %ld\n", + " adjusting %s %td to %ld\n", a_is_top ? "overshoot" : "reference", blue_sorted[i] - axis->blues, *a )); @@ -1050,7 +1040,7 @@ AF_FaceGlobals globals = metrics->root.globals; FT_UShort* gstyles = globals->glyph_styles; - FT_Long i; + FT_UInt i; FT_TRACE5(( "no blue zones found:" @@ -1075,8 +1065,8 @@ af_latin_metrics_check_digits( AF_LatinMetrics metrics, FT_Face face ) { - FT_Bool started = 0, same_width = 1; - FT_Fixed advance = 0, old_advance = 0; + FT_Bool started = 0, same_width = 1; + FT_Long advance = 0, old_advance = 0; /* If HarfBuzz is not available, we need a pointer to a single */ /* unsigned long value. */ @@ -1141,9 +1131,11 @@ /* Initialize global metrics. */ FT_LOCAL_DEF( FT_Error ) - af_latin_metrics_init( AF_LatinMetrics metrics, + af_latin_metrics_init( AF_StyleMetrics metrics_, /* AF_LatinMetrics */ FT_Face face ) { + AF_LatinMetrics metrics = (AF_LatinMetrics)metrics_; + FT_Error error = FT_Err_Ok; FT_CharMap oldmap = face->charmap; @@ -1164,7 +1156,7 @@ } Exit: - FT_Set_Charmap( face, oldmap ); + face->charmap = oldmap; return error; } @@ -1276,29 +1268,28 @@ if ( dist == 0 ) { - FT_TRACE5(( - "af_latin_metrics_scale_dim:" - " x height alignment (style `%s'):\n" - " " - " vertical scaling changed from %.5f to %.5f (by %d%%)\n" - "\n", - af_style_names[metrics->root.style_class->style], - scale / 65536.0, - new_scale / 65536.0, - ( fitted - scaled ) * 100 / scaled )); + FT_TRACE5(( "af_latin_metrics_scale_dim:" + " x height alignment (style `%s'):\n", + af_style_names[metrics->root.style_class->style] )); + FT_TRACE5(( " " + " vertical scaling changed" + " from %.5f to %.5f (by %ld%%)\n", + (double)scale / 65536, + (double)new_scale / 65536, + ( fitted - scaled ) * 100 / scaled )); + FT_TRACE5(( "\n" )); scale = new_scale; } #ifdef FT_DEBUG_LEVEL_TRACE else { - FT_TRACE5(( - "af_latin_metrics_scale_dim:" - " x height alignment (style `%s'):\n" - " " - " excessive vertical scaling abandoned\n" - "\n", - af_style_names[metrics->root.style_class->style] )); + FT_TRACE5(( "af_latin_metrics_scale_dim:" + " x height alignment (style `%s'):\n", + af_style_names[metrics->root.style_class->style] )); + FT_TRACE5(( " " + " excessive vertical scaling abandoned\n" )); + FT_TRACE5(( "\n" )); } #endif } @@ -1333,9 +1324,9 @@ width->cur = FT_MulFix( width->org, scale ); width->fit = width->cur; - FT_TRACE5(( " %d scaled to %.2f\n", + FT_TRACE5(( " %ld scaled to %.2f\n", width->org, - width->cur / 64.0 )); + (double)width->cur / 64 )); } FT_TRACE5(( "\n" )); @@ -1347,9 +1338,11 @@ #ifdef FT_DEBUG_LEVEL_TRACE if ( axis->extra_light ) - FT_TRACE5(( "`%s' style is extra light (at current resolution)\n" - "\n", + { + FT_TRACE5(( "`%s' style is extra light (at current resolution)\n", af_style_names[metrics->root.style_class->style] )); + FT_TRACE5(( "\n" )); + } #endif if ( dim == AF_DIMENSION_VERT ) @@ -1474,16 +1467,16 @@ AF_LatinBlue blue = &axis->blues[nn]; - FT_TRACE5(( " reference %d: %d scaled to %.2f%s\n" - " overshoot %d: %d scaled to %.2f%s\n", + FT_TRACE5(( " reference %d: %ld scaled to %.2f%s\n", nn, blue->ref.org, - blue->ref.fit / 64.0, + (double)blue->ref.fit / 64, ( blue->flags & AF_LATIN_BLUE_ACTIVE ) ? "" - : " (inactive)", + : " (inactive)" )); + FT_TRACE5(( " overshoot %d: %ld scaled to %.2f%s\n", nn, blue->shoot.org, - blue->shoot.fit / 64.0, + (double)blue->shoot.fit / 64, ( blue->flags & AF_LATIN_BLUE_ACTIVE ) ? "" : " (inactive)" )); } @@ -1495,9 +1488,12 @@ /* Scale global values in both directions. */ FT_LOCAL_DEF( void ) - af_latin_metrics_scale( AF_LatinMetrics metrics, + af_latin_metrics_scale( AF_StyleMetrics metrics_, /* AF_LatinMetrics */ AF_Scaler scaler ) { + AF_LatinMetrics metrics = (AF_LatinMetrics)metrics_; + + metrics->root.scaler.render_mode = scaler->render_mode; metrics->root.scaler.face = scaler->face; metrics->root.scaler.flags = scaler->flags; @@ -1510,11 +1506,14 @@ /* Extract standard_width from writing system/script specific */ /* metrics class. */ - FT_LOCAL_DEF( void ) - af_latin_get_standard_widths( AF_LatinMetrics metrics, + FT_CALLBACK_DEF( void ) + af_latin_get_standard_widths( AF_StyleMetrics metrics_, /* AF_LatinMetrics */ FT_Pos* stdHW, FT_Pos* stdVW ) { + AF_LatinMetrics metrics = (AF_LatinMetrics)metrics_; + + if ( stdHW ) *stdHW = metrics->axis[AF_DIMENSION_VERT].standard_width; @@ -1848,6 +1847,31 @@ ( FT_ABS( point->out_dir ) == major_dir || point == point->prev ) ) { + /* + * For efficiency, we restrict the number of segments to 1000, + * which is a heuristic value: it is very unlikely that a glyph + * with so many segments can be hinted in a sensible way. + * Reasons: + * + * - The glyph has really 1000 segments; this implies that it has + * at least 2000 outline points. Assuming 'normal' fonts that + * have superfluous points optimized away, viewing such a glyph + * only makes sense at large magnifications where hinting + * isn't applied anyway. + * + * - We have a broken glyph. Hinting doesn't make sense in this + * case either. + */ + if ( axis->num_segments > 1000 ) + { + FT_TRACE0(( "af_latin_hints_compute_segments:" + " more than 1000 segments in this glyph;\n" )); + FT_TRACE0(( " " + " hinting is suppressed\n" )); + axis->num_segments = 0; + return FT_Err_Ok; + } + /* this is the start of a new segment! */ segment_dir = (AF_Direction)point->out_dir; @@ -1970,7 +1994,7 @@ { AF_AxisHints axis = &hints->axis[dim]; AF_Segment segments = axis->segments; - AF_Segment segment_limit = segments + axis->num_segments; + AF_Segment segment_limit = FT_OFFSET( segments, axis->num_segments ); FT_Pos len_threshold, len_score, dist_score, max_width; AF_Segment seg1, seg2; @@ -2022,7 +2046,7 @@ max = seg2->max_coord; /* compute maximum coordinate difference of the two segments */ - /* (this is, how much they overlap) */ + /* (that is, how much they overlap) */ len = max - min; if ( len >= len_threshold ) { @@ -2090,7 +2114,7 @@ { if ( seg2->link != seg1 ) { - seg1->link = 0; + seg1->link = NULL; seg1->serif = seg2->link; } } @@ -2115,7 +2139,7 @@ FT_Bool top_to_bottom_hinting = 0; AF_Segment segments = axis->segments; - AF_Segment segment_limit = segments + axis->num_segments; + AF_Segment segment_limit = FT_OFFSET( segments, axis->num_segments ); AF_Segment seg; #if 0 @@ -2184,7 +2208,7 @@ for ( seg = segments; seg < segment_limit; seg++ ) { AF_Edge found = NULL; - FT_Int ee; + FT_UInt ee; /* ignore too short segments, too wide ones, and, in this loop, */ @@ -2258,7 +2282,7 @@ for ( seg = segments; seg < segment_limit; seg++ ) { AF_Edge found = NULL; - FT_Int ee; + FT_UInt ee; if ( seg->dir != AF_DIR_NONE ) @@ -2481,7 +2505,7 @@ { AF_AxisHints axis = &hints->axis[AF_DIMENSION_VERT]; AF_Edge edge = axis->edges; - AF_Edge edge_limit = edge + axis->num_edges; + AF_Edge edge_limit = FT_OFFSET( edge, axis->num_edges ); AF_LatinAxis latin = &metrics->axis[AF_DIMENSION_VERT]; FT_Fixed scale = latin->scale; @@ -2591,8 +2615,10 @@ static FT_Error af_latin_hints_init( AF_GlyphHints hints, - AF_LatinMetrics metrics ) + AF_StyleMetrics metrics_ ) /* AF_LatinMetrics */ { + AF_LatinMetrics metrics = (AF_LatinMetrics)metrics_; + FT_Render_Mode mode; FT_UInt32 scaler_flags, other_flags; FT_Face face = metrics->root.scaler.face; @@ -2612,11 +2638,6 @@ /* compute flags depending on render mode, etc. */ mode = metrics->root.scaler.render_mode; -#if 0 /* #ifdef AF_CONFIG_OPTION_USE_WARPER */ - if ( mode == FT_RENDER_MODE_LCD || mode == FT_RENDER_MODE_LCD_V ) - metrics->root.scaler.render_mode = mode = FT_RENDER_MODE_NORMAL; -#endif - scaler_flags = hints->scaler_flags; other_flags = 0; @@ -2654,12 +2675,6 @@ ( face->style_flags & FT_STYLE_FLAG_ITALIC ) != 0 ) scaler_flags |= AF_SCALER_FLAG_NO_HORIZONTAL; -#ifdef AF_CONFIG_OPTION_USE_WARPER - /* get (global) warper flag */ - if ( !metrics->root.globals->module->warping ) - scaler_flags |= AF_SCALER_FLAG_NO_WARPER; -#endif - hints->scaler_flags = scaler_flags; hints->other_flags = other_flags; @@ -2945,10 +2960,11 @@ stem_edge->pos = base_edge->pos + fitted_width; - FT_TRACE5(( " LINK: edge %d (opos=%.2f) linked to %.2f," + FT_TRACE5(( " LINK: edge %td (opos=%.2f) linked to %.2f," " dist was %.2f, now %.2f\n", - stem_edge - hints->axis[dim].edges, stem_edge->opos / 64.0, - stem_edge->pos / 64.0, dist / 64.0, fitted_width / 64.0 )); + stem_edge - hints->axis[dim].edges, + (double)stem_edge->opos / 64, (double)stem_edge->pos / 64, + (double)dist / 64, (double)fitted_width / 64 )); } @@ -2985,7 +3001,7 @@ { AF_AxisHints axis = &hints->axis[dim]; AF_Edge edges = axis->edges; - AF_Edge edge_limit = edges + axis->num_edges; + AF_Edge edge_limit = FT_OFFSET( edges, axis->num_edges ); FT_PtrDist n_edges; AF_Edge edge; AF_Edge anchor = NULL; @@ -3069,15 +3085,17 @@ #ifdef FT_DEBUG_LEVEL_TRACE if ( !anchor ) - FT_TRACE5(( " BLUE_ANCHOR: edge %d (opos=%.2f) snapped to %.2f," - " was %.2f (anchor=edge %d)\n", - edge1 - edges, edge1->opos / 64.0, blue->fit / 64.0, - edge1->pos / 64.0, edge - edges )); + FT_TRACE5(( " BLUE_ANCHOR: edge %td (opos=%.2f) snapped to %.2f," + " was %.2f (anchor=edge %td)\n", + edge1 - edges, + (double)edge1->opos / 64, (double)blue->fit / 64, + (double)edge1->pos / 64, edge - edges )); else - FT_TRACE5(( " BLUE: edge %d (opos=%.2f) snapped to %.2f," + FT_TRACE5(( " BLUE: edge %td (opos=%.2f) snapped to %.2f," " was %.2f\n", - edge1 - edges, edge1->opos / 64.0, blue->fit / 64.0, - edge1->pos / 64.0 )); + edge1 - edges, + (double)edge1->opos / 64, (double)blue->fit / 64, + (double)edge1->pos / 64 )); num_actions++; #endif @@ -3123,7 +3141,7 @@ /* this should not happen, but it's better to be safe */ if ( edge2->blue_edge ) { - FT_TRACE5(( " ASSERTION FAILED for edge %d\n", edge2 - edges )); + FT_TRACE5(( " ASSERTION FAILED for edge %td\n", edge2 - edges )); af_latin_align_linked_edge( hints, dim, edge2, edge ); edge->flags |= AF_EDGE_DONE; @@ -3191,11 +3209,11 @@ anchor = edge; edge->flags |= AF_EDGE_DONE; - FT_TRACE5(( " ANCHOR: edge %d (opos=%.2f) and %d (opos=%.2f)" + FT_TRACE5(( " ANCHOR: edge %td (opos=%.2f) and %td (opos=%.2f)" " snapped to %.2f and %.2f\n", - edge - edges, edge->opos / 64.0, - edge2 - edges, edge2->opos / 64.0, - edge->pos / 64.0, edge2->pos / 64.0 )); + edge - edges, (double)edge->opos / 64, + edge2 - edges, (double)edge2->opos / 64, + (double)edge->pos / 64, (double)edge2->pos / 64 )); af_latin_align_linked_edge( hints, dim, edge, edge2 ); @@ -3220,9 +3238,9 @@ if ( edge2->flags & AF_EDGE_DONE ) { - FT_TRACE5(( " ADJUST: edge %d (pos=%.2f) moved to %.2f\n", - edge - edges, edge->pos / 64.0, - ( edge2->pos - cur_len ) / 64.0 )); + FT_TRACE5(( " ADJUST: edge %td (pos=%.2f) moved to %.2f\n", + edge - edges, (double)edge->pos / 64, + (double)( edge2->pos - cur_len ) / 64 )); edge->pos = edge2->pos - cur_len; } @@ -3261,11 +3279,11 @@ edge->pos = cur_pos1 - cur_len / 2; edge2->pos = cur_pos1 + cur_len / 2; - FT_TRACE5(( " STEM: edge %d (opos=%.2f) linked to %d (opos=%.2f)" + FT_TRACE5(( " STEM: edge %td (opos=%.2f) linked to %td (opos=%.2f)" " snapped to %.2f and %.2f\n", - edge - edges, edge->opos / 64.0, - edge2 - edges, edge2->opos / 64.0, - edge->pos / 64.0, edge2->pos / 64.0 )); + edge - edges, (double)edge->opos / 64, + edge2 - edges, (double)edge2->opos / 64, + (double)edge->pos / 64, (double)edge2->pos / 64 )); } else @@ -3292,11 +3310,11 @@ edge->pos = ( delta1 < delta2 ) ? cur_pos1 : cur_pos2; edge2->pos = edge->pos + cur_len; - FT_TRACE5(( " STEM: edge %d (opos=%.2f) linked to %d (opos=%.2f)" + FT_TRACE5(( " STEM: edge %td (opos=%.2f) linked to %td (opos=%.2f)" " snapped to %.2f and %.2f\n", - edge - edges, edge->opos / 64.0, - edge2 - edges, edge2->opos / 64.0, - edge->pos / 64.0, edge2->pos / 64.0 )); + edge - edges, (double)edge->opos / 64, + edge2 - edges, (double)edge2->opos / 64, + (double)edge->pos / 64, (double)edge2->pos / 64 )); } #ifdef FT_DEBUG_LEVEL_TRACE @@ -3315,10 +3333,10 @@ if ( edge->link && FT_ABS( edge->link->pos - edge[-1].pos ) > 16 ) { #ifdef FT_DEBUG_LEVEL_TRACE - FT_TRACE5(( " BOUND: edge %d (pos=%.2f) moved to %.2f\n", + FT_TRACE5(( " BOUND: edge %td (pos=%.2f) moved to %.2f\n", edge - edges, - edge->pos / 64.0, - edge[-1].pos / 64.0 )); + (double)edge->pos / 64, + (double)edge[-1].pos / 64 )); num_actions++; #endif @@ -3417,19 +3435,20 @@ if ( delta < 64 + 16 ) { af_latin_align_serif_edge( hints, edge->serif, edge ); - FT_TRACE5(( " SERIF: edge %d (opos=%.2f) serif to %d (opos=%.2f)" + FT_TRACE5(( " SERIF: edge %td (opos=%.2f) serif to %td (opos=%.2f)" " aligned to %.2f\n", - edge - edges, edge->opos / 64.0, - edge->serif - edges, edge->serif->opos / 64.0, - edge->pos / 64.0 )); + edge - edges, (double)edge->opos / 64, + edge->serif - edges, (double)edge->serif->opos / 64, + (double)edge->pos / 64 )); } else if ( !anchor ) { edge->pos = FT_PIX_ROUND( edge->opos ); anchor = edge; - FT_TRACE5(( " SERIF_ANCHOR: edge %d (opos=%.2f)" + FT_TRACE5(( " SERIF_ANCHOR: edge %td (opos=%.2f)" " snapped to %.2f\n", - edge-edges, edge->opos / 64.0, edge->pos / 64.0 )); + edge - edges, + (double)edge->opos / 64, (double)edge->pos / 64 )); } else { @@ -3455,19 +3474,20 @@ after->pos - before->pos, after->opos - before->opos ); - FT_TRACE5(( " SERIF_LINK1: edge %d (opos=%.2f) snapped to %.2f" - " from %d (opos=%.2f)\n", - edge - edges, edge->opos / 64.0, - edge->pos / 64.0, - before - edges, before->opos / 64.0 )); + FT_TRACE5(( " SERIF_LINK1: edge %td (opos=%.2f) snapped to %.2f" + " from %td (opos=%.2f)\n", + edge - edges, (double)edge->opos / 64, + (double)edge->pos / 64, + before - edges, (double)before->opos / 64 )); } else { edge->pos = anchor->pos + ( ( edge->opos - anchor->opos + 16 ) & ~31 ); - FT_TRACE5(( " SERIF_LINK2: edge %d (opos=%.2f)" + FT_TRACE5(( " SERIF_LINK2: edge %td (opos=%.2f)" " snapped to %.2f\n", - edge - edges, edge->opos / 64.0, edge->pos / 64.0 )); + edge - edges, + (double)edge->opos / 64, (double)edge->pos / 64 )); } } @@ -3485,10 +3505,10 @@ if ( edge->link && FT_ABS( edge->link->pos - edge[-1].pos ) > 16 ) { #ifdef FT_DEBUG_LEVEL_TRACE - FT_TRACE5(( " BOUND: edge %d (pos=%.2f) moved to %.2f\n", + FT_TRACE5(( " BOUND: edge %td (pos=%.2f) moved to %.2f\n", edge - edges, - edge->pos / 64.0, - edge[-1].pos / 64.0 )); + (double)edge->pos / 64, + (double)edge[-1].pos / 64 )); num_actions++; #endif @@ -3506,10 +3526,10 @@ if ( edge->link && FT_ABS( edge->link->pos - edge[-1].pos ) > 16 ) { #ifdef FT_DEBUG_LEVEL_TRACE - FT_TRACE5(( " BOUND: edge %d (pos=%.2f) moved to %.2f\n", + FT_TRACE5(( " BOUND: edge %td (pos=%.2f) moved to %.2f\n", edge - edges, - edge->pos / 64.0, - edge[1].pos / 64.0 )); + (double)edge->pos / 64, + (double)edge[1].pos / 64 )); num_actions++; #endif @@ -3534,8 +3554,10 @@ af_latin_hints_apply( FT_UInt glyph_index, AF_GlyphHints hints, FT_Outline* outline, - AF_LatinMetrics metrics ) + AF_StyleMetrics metrics_ ) /* AF_LatinMetrics */ { + AF_LatinMetrics metrics = (AF_LatinMetrics)metrics_; + FT_Error error; int dim; @@ -3576,24 +3598,6 @@ /* grid-fit the outline */ for ( dim = 0; dim < AF_DIMENSION_MAX; dim++ ) { -#ifdef AF_CONFIG_OPTION_USE_WARPER - if ( dim == AF_DIMENSION_HORZ && - metrics->root.scaler.render_mode == FT_RENDER_MODE_NORMAL && - AF_HINTS_DO_WARP( hints ) ) - { - AF_WarperRec warper; - FT_Fixed scale; - FT_Pos delta; - - - af_warper_compute( &warper, hints, (AF_Dimension)dim, - &scale, &delta ); - af_glyph_hints_scale_dim( hints, (AF_Dimension)dim, - scale, delta ); - continue; - } -#endif /* AF_CONFIG_OPTION_USE_WARPER */ - if ( ( dim == AF_DIMENSION_HORZ && AF_HINTS_DO_HORIZONTAL( hints ) ) || ( dim == AF_DIMENSION_VERT && AF_HINTS_DO_VERTICAL( hints ) ) ) { diff --git a/src/font/freetype-2.10.2/src/autofit/aflatin.h b/3rdparty/freetype-2.13.2/src/autofit/aflatin.h similarity index 98% rename from src/font/freetype-2.10.2/src/autofit/aflatin.h rename to 3rdparty/freetype-2.13.2/src/autofit/aflatin.h index 62bc4c8d4..31aa91d3b 100644 --- a/src/font/freetype-2.10.2/src/autofit/aflatin.h +++ b/3rdparty/freetype-2.13.2/src/autofit/aflatin.h @@ -5,7 +5,7 @@ * Auto-fitter hinting routines for latin writing system * (specification). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -116,11 +116,11 @@ FT_BEGIN_HEADER FT_LOCAL( FT_Error ) - af_latin_metrics_init( AF_LatinMetrics metrics, + af_latin_metrics_init( AF_StyleMetrics metrics, FT_Face face ); FT_LOCAL( void ) - af_latin_metrics_scale( AF_LatinMetrics metrics, + af_latin_metrics_scale( AF_StyleMetrics metrics, AF_Scaler scaler ); FT_LOCAL( void ) diff --git a/src/font/freetype-2.10.2/src/autofit/afloader.c b/3rdparty/freetype-2.13.2/src/autofit/afloader.c similarity index 94% rename from src/font/freetype-2.10.2/src/autofit/afloader.c rename to 3rdparty/freetype-2.13.2/src/autofit/afloader.c index a53fbf2d2..7c47d562a 100644 --- a/src/font/freetype-2.10.2/src/autofit/afloader.c +++ b/3rdparty/freetype-2.13.2/src/autofit/afloader.c @@ -4,7 +4,7 @@ * * Auto-fitter glyph loading routines (body). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -22,7 +22,7 @@ #include "aferrors.h" #include "afmodule.h" -#include FT_INTERNAL_CALC_H +#include /* Initialize glyph loader. */ @@ -55,10 +55,8 @@ error = af_face_globals_new( face, &loader->globals, module ); if ( !error ) { - face->autohint.data = - (FT_Pointer)loader->globals; - face->autohint.finalizer = - (FT_Generic_Finalizer)af_face_globals_free; + face->autohint.data = (FT_Pointer)loader->globals; + face->autohint.finalizer = af_face_globals_free; } } @@ -105,7 +103,6 @@ globals->stem_darkening_for_ppem; FT_Fixed em_size = af_intToFixed( face->units_per_EM ); - FT_Fixed em_ratio = FT_DivFix( af_intToFixed( 1000 ), em_size ); FT_Matrix scale_down_matrix = { 0x10000L, 0, 0, 0x10000L }; @@ -142,12 +139,11 @@ darken_by_font_units_x = - af_intToFixed( af_loader_compute_darkening( loader, - face, - stdVW ) ); - darken_x = FT_DivFix( FT_MulFix( darken_by_font_units_x, - size_metrics->x_scale ), - em_ratio ); + af_loader_compute_darkening( loader, + face, + stdVW ) ; + darken_x = FT_MulFix( darken_by_font_units_x, + size_metrics->x_scale ); globals->standard_vertical_width = stdVW; globals->stem_darkening_for_ppem = size_metrics->x_ppem; @@ -161,12 +157,11 @@ darken_by_font_units_y = - af_intToFixed( af_loader_compute_darkening( loader, - face, - stdHW ) ); - darken_y = FT_DivFix( FT_MulFix( darken_by_font_units_y, - size_metrics->y_scale ), - em_ratio ); + af_loader_compute_darkening( loader, + face, + stdHW ) ; + darken_y = FT_MulFix( darken_by_font_units_y, + size_metrics->y_scale ); globals->standard_horizontal_width = stdHW; globals->stem_darkening_for_ppem = size_metrics->x_ppem; @@ -232,9 +227,6 @@ AF_WritingSystemClass writing_system_class; - if ( !size ) - return FT_THROW( Invalid_Size_Handle ); - FT_ZERO( &scaler ); if ( !size_internal->autohint_metrics.x_scale || @@ -300,12 +292,6 @@ if ( error ) goto Exit; -#ifdef FT_OPTION_AUTOFIT2 - /* XXX: undocumented hook to activate the latin2 writing system. */ - if ( load_flags & ( 1UL << 20 ) ) - style_options = AF_STYLE_LTN2_DFLT; -#endif - /* * Glyphs (really code points) are assigned to scripts. Script * analysis is done lazily: For each glyph that passes through here, @@ -482,8 +468,8 @@ FT_Pos pp2x = loader->pp2.x; - loader->pp1.x = FT_PIX_ROUND( pp1x + hints->xmin_delta ); - loader->pp2.x = FT_PIX_ROUND( pp2x + hints->xmax_delta ); + loader->pp1.x = FT_PIX_ROUND( pp1x ); + loader->pp2.x = FT_PIX_ROUND( pp2x ); slot->lsb_delta = loader->pp1.x - pp1x; slot->rsb_delta = loader->pp2.x - pp2x; @@ -594,7 +580,7 @@ * * XXX: Currently a crude adaption of the original algorithm. Do better? */ - FT_LOCAL_DEF( FT_Int32 ) + FT_LOCAL_DEF( FT_Fixed ) af_loader_compute_darkening( AF_Loader loader, FT_Face face, FT_Pos standard_width ) @@ -713,7 +699,7 @@ } /* Convert darken_amount from per 1000 em to true character space. */ - return af_fixedToInt( FT_DivFix( darken_amount, em_ratio ) ); + return FT_DivFix( darken_amount, em_ratio ); } diff --git a/src/font/freetype-2.10.2/src/autofit/afloader.h b/3rdparty/freetype-2.13.2/src/autofit/afloader.h similarity index 97% rename from src/font/freetype-2.10.2/src/autofit/afloader.h rename to 3rdparty/freetype-2.13.2/src/autofit/afloader.h index 97282371c..e4e197e37 100644 --- a/src/font/freetype-2.10.2/src/autofit/afloader.h +++ b/3rdparty/freetype-2.13.2/src/autofit/afloader.h @@ -4,7 +4,7 @@ * * Auto-fitter glyph loading routines (specification). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -75,7 +75,7 @@ FT_BEGIN_HEADER FT_UInt gindex, FT_Int32 load_flags ); - FT_LOCAL_DEF( FT_Int32 ) + FT_LOCAL( FT_Fixed ) af_loader_compute_darkening( AF_Loader loader, FT_Face face, FT_Pos standard_width ); diff --git a/src/font/freetype-2.10.2/src/autofit/afmodule.c b/3rdparty/freetype-2.13.2/src/autofit/afmodule.c similarity index 77% rename from src/font/freetype-2.10.2/src/autofit/afmodule.c rename to 3rdparty/freetype-2.13.2/src/autofit/afmodule.c index 0bcae4cc2..20a6b96bc 100644 --- a/src/font/freetype-2.10.2/src/autofit/afmodule.c +++ b/3rdparty/freetype-2.13.2/src/autofit/afmodule.c @@ -4,7 +4,7 @@ * * Auto-fitter module implementation (body). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -43,20 +43,20 @@ #endif - int _af_debug_disable_horz_hints; - int _af_debug_disable_vert_hints; - int _af_debug_disable_blue_hints; + int af_debug_disable_horz_hints_; + int af_debug_disable_vert_hints_; + int af_debug_disable_blue_hints_; /* we use a global object instead of a local one for debugging */ - AF_GlyphHintsRec _af_debug_hints_rec[1]; + static AF_GlyphHintsRec af_debug_hints_rec_[1]; - void* _af_debug_hints = _af_debug_hints_rec; + void* af_debug_hints_ = af_debug_hints_rec_; #endif -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_DEBUG_H -#include FT_DRIVER_H -#include FT_SERVICE_PROPERTIES_H +#include +#include +#include +#include /************************************************************************** @@ -89,10 +89,8 @@ error = af_face_globals_new( face, &globals, module ); if ( !error ) { - face->autohint.data = - (FT_Pointer)globals; - face->autohint.finalizer = - (FT_Generic_Finalizer)af_face_globals_free; + face->autohint.data = (FT_Pointer)globals; + face->autohint.finalizer = af_face_globals_free; } } @@ -119,8 +117,8 @@ if ( !ft_strcmp( property_name, "fallback-script" ) ) { - FT_UInt* fallback_script; - FT_UInt ss; + AF_Script* fallback_script; + FT_UInt ss; #ifdef FT_CONFIG_OPTION_ENVIRONMENT_PROPERTIES @@ -128,7 +126,7 @@ return FT_THROW( Invalid_Argument ); #endif - fallback_script = (FT_UInt*)value; + fallback_script = (AF_Script*)value; /* We translate the fallback script to a fallback style that uses */ /* `fallback-script' as its script and `AF_COVERAGE_NONE' as its */ @@ -138,8 +136,8 @@ AF_StyleClass style_class = af_style_classes[ss]; - if ( (FT_UInt)style_class->script == *fallback_script && - style_class->coverage == AF_COVERAGE_DEFAULT ) + if ( style_class->script == *fallback_script && + style_class->coverage == AF_COVERAGE_DEFAULT ) { module->fallback_style = ss; break; @@ -148,8 +146,8 @@ if ( !af_style_classes[ss] ) { - FT_TRACE0(( "af_property_set: Invalid value %d for property `%s'\n", - fallback_script, property_name )); + FT_TRACE2(( "af_property_set: Invalid value %d for property `%s'\n", + *fallback_script, property_name )); return FT_THROW( Invalid_Argument ); } @@ -157,7 +155,7 @@ } else if ( !ft_strcmp( property_name, "default-script" ) ) { - FT_UInt* default_script; + AF_Script* default_script; #ifdef FT_CONFIG_OPTION_ENVIRONMENT_PROPERTIES @@ -165,7 +163,7 @@ return FT_THROW( Invalid_Argument ); #endif - default_script = (FT_UInt*)value; + default_script = (AF_Script*)value; module->default_script = *default_script; @@ -190,35 +188,6 @@ return error; } -#ifdef AF_CONFIG_OPTION_USE_WARPER - else if ( !ft_strcmp( property_name, "warping" ) ) - { -#ifdef FT_CONFIG_OPTION_ENVIRONMENT_PROPERTIES - if ( value_is_string ) - { - const char* s = (const char*)value; - long w = ft_strtol( s, NULL, 10 ); - - - if ( w == 0 ) - module->warping = 0; - else if ( w == 1 ) - module->warping = 1; - else - return FT_THROW( Invalid_Argument ); - } - else -#endif - { - FT_Bool* warping = (FT_Bool*)value; - - - module->warping = *warping; - } - - return error; - } -#endif /* AF_CONFIG_OPTION_USE_WARPER */ else if ( !ft_strcmp( property_name, "darkening-parameters" ) ) { FT_Int* darken_params; @@ -307,7 +276,7 @@ return error; } - FT_TRACE0(( "af_property_set: missing property `%s'\n", + FT_TRACE2(( "af_property_set: missing property `%s'\n", property_name )); return FT_THROW( Missing_Property ); } @@ -320,11 +289,6 @@ { FT_Error error = FT_Err_Ok; AF_Module module = (AF_Module)ft_module; - FT_UInt fallback_style = module->fallback_style; - FT_UInt default_script = module->default_script; -#ifdef AF_CONFIG_OPTION_USE_WARPER - FT_Bool warping = module->warping; -#endif if ( !ft_strcmp( property_name, "glyph-to-script-map" ) ) @@ -341,9 +305,9 @@ } else if ( !ft_strcmp( property_name, "fallback-script" ) ) { - FT_UInt* val = (FT_UInt*)value; + AF_Script* val = (AF_Script*)value; - AF_StyleClass style_class = af_style_classes[fallback_style]; + AF_StyleClass style_class = af_style_classes[module->fallback_style]; *val = style_class->script; @@ -352,10 +316,10 @@ } else if ( !ft_strcmp( property_name, "default-script" ) ) { - FT_UInt* val = (FT_UInt*)value; + AF_Script* val = (AF_Script*)value; - *val = default_script; + *val = module->default_script; return error; } @@ -371,17 +335,6 @@ return error; } -#ifdef AF_CONFIG_OPTION_USE_WARPER - else if ( !ft_strcmp( property_name, "warping" ) ) - { - FT_Bool* val = (FT_Bool*)value; - - - *val = warping; - - return error; - } -#endif /* AF_CONFIG_OPTION_USE_WARPER */ else if ( !ft_strcmp( property_name, "darkening-parameters" ) ) { FT_Int* darken_params = module->darken_params; @@ -410,7 +363,7 @@ return error; } - FT_TRACE0(( "af_property_get: missing property `%s'\n", + FT_TRACE2(( "af_property_get: missing property `%s'\n", property_name )); return FT_THROW( Missing_Property ); } @@ -419,8 +372,9 @@ FT_DEFINE_SERVICE_PROPERTIESREC( af_service_properties, - (FT_Properties_SetFunc)af_property_set, /* set_property */ - (FT_Properties_GetFunc)af_property_get ) /* get_property */ + af_property_set, /* FT_Properties_SetFunc set_property */ + af_property_get /* FT_Properties_GetFunc get_property */ + ) FT_DEFINE_SERVICEDESCREC1( @@ -447,9 +401,6 @@ module->fallback_style = AF_STYLE_FALLBACK; module->default_script = AF_SCRIPT_DEFAULT; -#ifdef AF_CONFIG_OPTION_USE_WARPER - module->warping = 0; -#endif module->no_stem_darkening = TRUE; module->darken_params[0] = CFF_CONFIG_OPTION_DARKENING_PARAMETER_X1; @@ -471,19 +422,21 @@ FT_UNUSED( ft_module ); #ifdef FT_DEBUG_AUTOFIT - if ( _af_debug_hints_rec->memory ) - af_glyph_hints_done( _af_debug_hints_rec ); + if ( af_debug_hints_rec_->memory ) + af_glyph_hints_done( af_debug_hints_rec_ ); #endif } FT_CALLBACK_DEF( FT_Error ) - af_autofitter_load_glyph( AF_Module module, - FT_GlyphSlot slot, - FT_Size size, - FT_UInt glyph_index, - FT_Int32 load_flags ) + af_autofitter_load_glyph( FT_AutoHinter module_, + FT_GlyphSlot slot, + FT_Size size, + FT_UInt glyph_index, + FT_Int32 load_flags ) { + AF_Module module = (AF_Module)module_; + FT_Error error = FT_Err_Ok; FT_Memory memory = module->root.library->memory; @@ -491,7 +444,7 @@ /* in debug mode, we use a global object that survives this routine */ - AF_GlyphHints hints = _af_debug_hints_rec; + AF_GlyphHints hints = af_debug_hints_rec_; AF_LoaderRec loader[1]; FT_UNUSED( size ); @@ -547,11 +500,11 @@ FT_DEFINE_AUTOHINTER_INTERFACE( af_autofitter_interface, - NULL, /* reset_face */ - NULL, /* get_global_hints */ - NULL, /* done_global_hints */ - (FT_AutoHinter_GlyphLoadFunc)af_autofitter_load_glyph ) /* load_glyph */ - + NULL, /* FT_AutoHinter_GlobalResetFunc reset_face */ + NULL, /* FT_AutoHinter_GlobalGetFunc get_global_hints */ + NULL, /* FT_AutoHinter_GlobalDoneFunc done_global_hints */ + af_autofitter_load_glyph /* FT_AutoHinter_GlyphLoadFunc load_glyph */ + ) FT_DEFINE_MODULE( autofit_module_class, @@ -565,9 +518,9 @@ (const void*)&af_autofitter_interface, - (FT_Module_Constructor)af_autofitter_init, /* module_init */ - (FT_Module_Destructor) af_autofitter_done, /* module_done */ - (FT_Module_Requester) af_get_interface /* get_interface */ + af_autofitter_init, /* FT_Module_Constructor module_init */ + af_autofitter_done, /* FT_Module_Destructor module_done */ + af_get_interface /* FT_Module_Requester get_interface */ ) diff --git a/src/font/freetype-2.10.2/src/autofit/afmodule.h b/3rdparty/freetype-2.13.2/src/autofit/afmodule.h similarity index 82% rename from src/font/freetype-2.10.2/src/autofit/afmodule.h rename to 3rdparty/freetype-2.13.2/src/autofit/afmodule.h index efa0240b4..4b8b4562c 100644 --- a/src/font/freetype-2.10.2/src/autofit/afmodule.h +++ b/3rdparty/freetype-2.13.2/src/autofit/afmodule.h @@ -4,7 +4,7 @@ * * Auto-fitter module implementation (specification). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,9 +19,8 @@ #ifndef AFMODULE_H_ #define AFMODULE_H_ -#include -#include FT_INTERNAL_OBJECTS_H -#include FT_MODULE_H +#include +#include FT_BEGIN_HEADER @@ -37,16 +36,14 @@ FT_BEGIN_HEADER FT_ModuleRec root; FT_UInt fallback_style; - FT_UInt default_script; -#ifdef AF_CONFIG_OPTION_USE_WARPER - FT_Bool warping; -#endif + AF_Script default_script; FT_Bool no_stem_darkening; FT_Int darken_params[8]; } AF_ModuleRec, *AF_Module; +FT_DECLARE_AUTOHINTER_INTERFACE( af_autofitter_interface ) FT_DECLARE_MODULE( autofit_module_class ) diff --git a/src/font/freetype-2.10.2/src/autofit/afranges.c b/3rdparty/freetype-2.13.2/src/autofit/afranges.c similarity index 99% rename from src/font/freetype-2.10.2/src/autofit/afranges.c rename to 3rdparty/freetype-2.13.2/src/autofit/afranges.c index d6ecf8891..cfcaf340a 100644 --- a/src/font/freetype-2.10.2/src/autofit/afranges.c +++ b/3rdparty/freetype-2.13.2/src/autofit/afranges.c @@ -4,7 +4,7 @@ * * Auto-fitter Unicode script ranges (body). * - * Copyright (C) 2013-2020 by + * Copyright (C) 2013-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -664,6 +664,18 @@ }; + const AF_Script_UniRangeRec af_medf_uniranges[] = + { + AF_UNIRANGE_REC( 0x16E40, 0x16E9F ), /* Medefaidrin */ + AF_UNIRANGE_REC( 0, 0 ) + }; + + const AF_Script_UniRangeRec af_medf_nonbase_uniranges[] = + { + AF_UNIRANGE_REC( 0, 0 ) + }; + + const AF_Script_UniRangeRec af_mong_uniranges[] = { AF_UNIRANGE_REC( 0x1800, 0x18AF ), /* Mongolian */ diff --git a/src/font/freetype-2.10.2/src/autofit/afranges.h b/3rdparty/freetype-2.13.2/src/autofit/afranges.h similarity index 97% rename from src/font/freetype-2.10.2/src/autofit/afranges.h rename to 3rdparty/freetype-2.13.2/src/autofit/afranges.h index c2ffda4b0..5775738bc 100644 --- a/src/font/freetype-2.10.2/src/autofit/afranges.h +++ b/3rdparty/freetype-2.13.2/src/autofit/afranges.h @@ -4,7 +4,7 @@ * * Auto-fitter Unicode script ranges (specification). * - * Copyright (C) 2013-2020 by + * Copyright (C) 2013-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, diff --git a/src/font/freetype-2.10.2/src/autofit/afscript.h b/3rdparty/freetype-2.13.2/src/autofit/afscript.h similarity index 97% rename from src/font/freetype-2.10.2/src/autofit/afscript.h rename to 3rdparty/freetype-2.13.2/src/autofit/afscript.h index 36caaddc5..3a101937d 100644 --- a/src/font/freetype-2.10.2/src/autofit/afscript.h +++ b/3rdparty/freetype-2.13.2/src/autofit/afscript.h @@ -4,7 +4,7 @@ * * Auto-fitter scripts (specification only). * - * Copyright (C) 2013-2020 by + * Copyright (C) 2013-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -243,6 +243,12 @@ HINTING_BOTTOM_TO_TOP, "\xE0\xB4\xA0 \xE0\xB4\xB1" ) /* ഠ റ */ + SCRIPT( medf, MEDF, + "Medefaidrin", + HB_SCRIPT_MEDEFAIDRIN, + HINTING_BOTTOM_TO_TOP, + "\xF0\x96\xB9\xA1 \xF0\x96\xB9\x9B \xF0\x96\xB9\xAF" ) /* 𖹡 𖹛 𖹯 */ + SCRIPT( mong, MONG, "Mongolian", HB_SCRIPT_MONGOLIAN, diff --git a/src/font/freetype-2.10.2/src/autofit/afshaper.c b/3rdparty/freetype-2.13.2/src/autofit/afshaper.c similarity index 92% rename from src/font/freetype-2.10.2/src/autofit/afshaper.c rename to 3rdparty/freetype-2.13.2/src/autofit/afshaper.c index d3902db2e..abc6f1d29 100644 --- a/src/font/freetype-2.10.2/src/autofit/afshaper.c +++ b/3rdparty/freetype-2.13.2/src/autofit/afshaper.c @@ -4,7 +4,7 @@ * * HarfBuzz interface for accessing OpenType features (body). * - * Copyright (C) 2013-2020 by + * Copyright (C) 2013-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,9 +16,8 @@ */ -#include -#include FT_FREETYPE_H -#include FT_ADVANCES_H +#include +#include #include "afglobal.h" #include "aftypes.h" #include "afshaper.h" @@ -133,13 +132,24 @@ /* Convert a HarfBuzz script tag into the corresponding OpenType */ /* tag or tags -- some Indic scripts like Devanagari have an old */ /* and a new set of features. */ - hb_ot_tags_from_script( script, - &script_tags[0], - &script_tags[1] ); + { + unsigned int tags_count = 3; + hb_tag_t tags[3]; + + + hb_ot_tags_from_script_and_language( script, + HB_LANGUAGE_INVALID, + &tags_count, + tags, + NULL, + NULL ); + script_tags[0] = tags_count > 0 ? tags[0] : HB_TAG_NONE; + script_tags[1] = tags_count > 1 ? tags[1] : HB_TAG_NONE; + script_tags[2] = tags_count > 2 ? tags[2] : HB_TAG_NONE; + } - /* `hb_ot_tags_from_script' usually returns HB_OT_TAG_DEFAULT_SCRIPT */ - /* as the second tag. We change that to HB_TAG_NONE except for the */ - /* default script. */ + /* If the second tag is HB_OT_TAG_DEFAULT_SCRIPT, change that to */ + /* HB_TAG_NONE except for the default script. */ if ( default_script ) { if ( script_tags[0] == HB_TAG_NONE ) @@ -158,9 +168,6 @@ /* HarfBuzz maps them to `DFLT', which we don't want to handle here */ if ( script_tags[0] == HB_OT_TAG_DEFAULT_SCRIPT ) goto Exit; - - if ( script_tags[1] == HB_OT_TAG_DEFAULT_SCRIPT ) - script_tags[1] = HB_TAG_NONE; } gsub_lookups = hb_set_create(); @@ -174,9 +181,9 @@ if ( hb_set_is_empty( gsub_lookups ) ) goto Exit; /* nothing to do */ - FT_TRACE4(( "GSUB lookups (style `%s'):\n" - " ", + FT_TRACE4(( "GSUB lookups (style `%s'):\n", af_style_names[style_class->style] )); + FT_TRACE4(( " " )); #ifdef FT_DEBUG_LEVEL_TRACE count = 0; @@ -203,12 +210,13 @@ #ifdef FT_DEBUG_LEVEL_TRACE if ( !count ) FT_TRACE4(( " (none)" )); - FT_TRACE4(( "\n\n" )); + FT_TRACE4(( "\n" )); + FT_TRACE4(( "\n" )); #endif - FT_TRACE4(( "GPOS lookups (style `%s'):\n" - " ", + FT_TRACE4(( "GPOS lookups (style `%s'):\n", af_style_names[style_class->style] )); + FT_TRACE4(( " " )); gpos_lookups = hb_set_create(); hb_ot_layout_collect_lookups( face, @@ -243,13 +251,14 @@ #ifdef FT_DEBUG_LEVEL_TRACE if ( !count ) FT_TRACE4(( " (none)" )); - FT_TRACE4(( "\n\n" )); + FT_TRACE4(( "\n" )); + FT_TRACE4(( "\n" )); #endif /* * We now check whether we can construct blue zones, using glyphs * covered by the feature only. In case there is not a single zone - * (this is, not a single character is covered), we skip this coverage. + * (that is, not a single character is covered), we skip this coverage. * */ if ( style_class->coverage != AF_COVERAGE_DEFAULT ) @@ -304,9 +313,9 @@ * hinted and usually rendered glyph. * * Consider the superscript feature of font `pala.ttf': Some of the - * glyphs are `real', this is, they have a zero vertical offset, but + * glyphs are `real', that is, they have a zero vertical offset, but * most of them are small caps glyphs shifted up to the superscript - * position (this is, the `sups' feature is present in both the GSUB and + * position (that is, the `sups' feature is present in both the GSUB and * GPOS tables). The code for blue zones computation actually uses a * feature's y offset so that the `real' glyphs get correct hints. But * later on it is impossible to decide whether a glyph index belongs to, @@ -354,8 +363,10 @@ { #ifdef FT_DEBUG_LEVEL_TRACE if ( !( count % 10 ) ) - FT_TRACE4(( "\n" - " " )); + { + FT_TRACE4(( "\n" )); + FT_TRACE4(( " " )); + } FT_TRACE4(( " %d", idx )); count++; @@ -377,9 +388,12 @@ #ifdef FT_DEBUG_LEVEL_TRACE if ( !count ) - FT_TRACE4(( "\n" - " (none)" )); - FT_TRACE4(( "\n\n" )); + { + FT_TRACE4(( "\n" )); + FT_TRACE4(( " (none)" )); + } + FT_TRACE4(( "\n" )); + FT_TRACE4(( "\n" )); #endif Exit: diff --git a/src/font/freetype-2.10.2/src/autofit/afshaper.h b/3rdparty/freetype-2.13.2/src/autofit/afshaper.h similarity index 94% rename from src/font/freetype-2.10.2/src/autofit/afshaper.h rename to 3rdparty/freetype-2.13.2/src/autofit/afshaper.h index a7dbf34f1..054a18ffb 100644 --- a/src/font/freetype-2.10.2/src/autofit/afshaper.h +++ b/3rdparty/freetype-2.13.2/src/autofit/afshaper.h @@ -4,7 +4,7 @@ * * HarfBuzz interface for accessing OpenType features (specification). * - * Copyright (C) 2013-2020 by + * Copyright (C) 2013-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,15 +20,14 @@ #define AFSHAPER_H_ -#include -#include FT_FREETYPE_H +#include #ifdef FT_CONFIG_OPTION_USE_HARFBUZZ #include #include -#include +#include "ft-hb.h" #endif diff --git a/src/font/freetype-2.10.2/src/autofit/afstyles.h b/3rdparty/freetype-2.13.2/src/autofit/afstyles.h similarity index 98% rename from src/font/freetype-2.10.2/src/autofit/afstyles.h rename to 3rdparty/freetype-2.13.2/src/autofit/afstyles.h index 8d411ab0d..73ebef017 100644 --- a/src/font/freetype-2.10.2/src/autofit/afstyles.h +++ b/3rdparty/freetype-2.13.2/src/autofit/afstyles.h @@ -4,7 +4,7 @@ * * Auto-fitter styles (specification only). * - * Copyright (C) 2013-2020 by + * Copyright (C) 2013-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -299,15 +299,6 @@ AF_BLUE_STRINGSET_LATP, AF_COVERAGE_DEFAULT ) -#ifdef FT_OPTION_AUTOFIT2 - STYLE( ltn2_dflt, LTN2_DFLT, - "Latin 2 default style", - AF_WRITING_SYSTEM_LATIN2, - AF_SCRIPT_LATN, - AF_BLUE_STRINGSET_LATN, - AF_COVERAGE_DEFAULT ) -#endif - STYLE( lisu_dflt, LISU_DFLT, "Lisu default style", AF_WRITING_SYSTEM_LATIN, @@ -322,6 +313,13 @@ AF_BLUE_STRINGSET_MLYM, AF_COVERAGE_DEFAULT ) + STYLE( medf_dflt, MEDF_DFLT, + "Medefaidrin default style", + AF_WRITING_SYSTEM_LATIN, + AF_SCRIPT_MEDF, + AF_BLUE_STRINGSET_MEDF, + AF_COVERAGE_DEFAULT ) + STYLE( mong_dflt, MONG_DFLT, "Mongolian default style", AF_WRITING_SYSTEM_LATIN, diff --git a/src/font/freetype-2.10.2/src/autofit/aftypes.h b/3rdparty/freetype-2.13.2/src/autofit/aftypes.h similarity index 86% rename from src/font/freetype-2.10.2/src/autofit/aftypes.h rename to 3rdparty/freetype-2.13.2/src/autofit/aftypes.h index 7ca0b59e3..661519449 100644 --- a/src/font/freetype-2.10.2/src/autofit/aftypes.h +++ b/3rdparty/freetype-2.13.2/src/autofit/aftypes.h @@ -4,7 +4,7 @@ * * Auto-fitter types (specification only). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -32,12 +32,11 @@ #ifndef AFTYPES_H_ #define AFTYPES_H_ -#include -#include FT_FREETYPE_H -#include FT_OUTLINE_H -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_DEBUG_H +#include +#include +#include +#include #include "afblue.h" @@ -58,10 +57,10 @@ FT_BEGIN_HEADER #ifdef FT_DEBUG_AUTOFIT -extern int _af_debug_disable_horz_hints; -extern int _af_debug_disable_vert_hints; -extern int _af_debug_disable_blue_hints; -extern void* _af_debug_hints; +extern int af_debug_disable_horz_hints_; +extern int af_debug_disable_vert_hints_; +extern int af_debug_disable_blue_hints_; +extern void* af_debug_hints_; #endif /* FT_DEBUG_AUTOFIT */ @@ -93,63 +92,6 @@ extern void* _af_debug_hints; FT_Pos threshold ); - /*************************************************************************/ - /*************************************************************************/ - /***** *****/ - /***** A N G L E T Y P E S *****/ - /***** *****/ - /*************************************************************************/ - /*************************************************************************/ - - /* - * The auto-fitter doesn't need a very high angular accuracy; - * this allows us to speed up some computations considerably with a - * light Cordic algorithm (see afangles.c). - */ - - typedef FT_Int AF_Angle; - - -#define AF_ANGLE_PI 256 -#define AF_ANGLE_2PI ( AF_ANGLE_PI * 2 ) -#define AF_ANGLE_PI2 ( AF_ANGLE_PI / 2 ) -#define AF_ANGLE_PI4 ( AF_ANGLE_PI / 4 ) - - -#if 0 - /* - * compute the angle of a given 2-D vector - */ - FT_LOCAL( AF_Angle ) - af_angle_atan( FT_Pos dx, - FT_Pos dy ); - - - /* - * compute `angle2 - angle1'; the result is always within - * the range [-AF_ANGLE_PI .. AF_ANGLE_PI - 1] - */ - FT_LOCAL( AF_Angle ) - af_angle_diff( AF_Angle angle1, - AF_Angle angle2 ); -#endif /* 0 */ - - -#define AF_ANGLE_DIFF( result, angle1, angle2 ) \ - FT_BEGIN_STMNT \ - AF_Angle _delta = (angle2) - (angle1); \ - \ - \ - while ( _delta <= -AF_ANGLE_PI ) \ - _delta += AF_ANGLE_2PI; \ - \ - while ( _delta > AF_ANGLE_PI ) \ - _delta -= AF_ANGLE_2PI; \ - \ - result = _delta; \ - FT_END_STMNT - - /* * opaque handle to glyph-specific hints -- see `afhints.h' for more * details @@ -173,18 +115,17 @@ extern void* _af_debug_hints; #define AF_SCALER_FLAG_NO_HORIZONTAL 1U /* disable horizontal hinting */ #define AF_SCALER_FLAG_NO_VERTICAL 2U /* disable vertical hinting */ #define AF_SCALER_FLAG_NO_ADVANCE 4U /* disable advance hinting */ -#define AF_SCALER_FLAG_NO_WARPER 8U /* disable warper */ typedef struct AF_ScalerRec_ { - FT_Face face; /* source font face */ - FT_Fixed x_scale; /* from font units to 1/64th device pixels */ - FT_Fixed y_scale; /* from font units to 1/64th device pixels */ - FT_Pos x_delta; /* in 1/64th device pixels */ - FT_Pos y_delta; /* in 1/64th device pixels */ - FT_Render_Mode render_mode; /* monochrome, anti-aliased, LCD, etc. */ - FT_UInt32 flags; /* additional control flags, see above */ + FT_Face face; /* source font face */ + FT_Fixed x_scale; /* from font units to 1/64 device pixels */ + FT_Fixed y_scale; /* from font units to 1/64 device pixels */ + FT_Pos x_delta; /* in 1/64 device pixels */ + FT_Pos y_delta; /* in 1/64 device pixels */ + FT_Render_Mode render_mode; /* monochrome, anti-aliased, LCD, etc. */ + FT_UInt32 flags; /* additional control flags, see above */ } AF_ScalerRec, *AF_Scaler; @@ -257,7 +198,6 @@ extern void* _af_debug_hints; * outline according to the results of the glyph analyzer. */ -#define AFWRTSYS_H_ /* don't load header files */ #undef WRITING_SYSTEM #define WRITING_SYSTEM( ws, WS ) \ AF_WRITING_SYSTEM_ ## WS, @@ -266,14 +206,12 @@ extern void* _af_debug_hints; typedef enum AF_WritingSystem_ { -#include "afwrtsys.h" +#include "afws-iter.h" AF_WRITING_SYSTEM_MAX /* do not remove */ } AF_WritingSystem; -#undef AFWRTSYS_H_ - typedef struct AF_WritingSystemClassRec_ { diff --git a/3rdparty/freetype-2.13.2/src/autofit/afws-decl.h b/3rdparty/freetype-2.13.2/src/autofit/afws-decl.h new file mode 100644 index 000000000..48c888afe --- /dev/null +++ b/3rdparty/freetype-2.13.2/src/autofit/afws-decl.h @@ -0,0 +1,33 @@ +/**************************************************************************** + * + * afws-decl.h + * + * Auto-fitter writing system declarations (specification only). + * + * Copyright (C) 2013-2023 by + * David Turner, Robert Wilhelm, and Werner Lemberg. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + +#ifndef AFWS_DECL_H_ +#define AFWS_DECL_H_ + + /* Since preprocessor directives can't create other preprocessor */ + /* directives, we have to include the header files manually. */ + +#include "afdummy.h" +#include "aflatin.h" +#include "afcjk.h" +#include "afindic.h" + +#endif /* AFWS_DECL_H_ */ + + +/* END */ diff --git a/3rdparty/freetype-2.13.2/src/autofit/afws-iter.h b/3rdparty/freetype-2.13.2/src/autofit/afws-iter.h new file mode 100644 index 000000000..a0a686f8c --- /dev/null +++ b/3rdparty/freetype-2.13.2/src/autofit/afws-iter.h @@ -0,0 +1,31 @@ +/**************************************************************************** + * + * afws-iter.h + * + * Auto-fitter writing systems iterator (specification only). + * + * Copyright (C) 2013-2023 by + * David Turner, Robert Wilhelm, and Werner Lemberg. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + /* This header may be included multiple times. */ + /* Define `WRITING_SYSTEM' as needed. */ + + + /* Add new writing systems here. The arguments are the writing system */ + /* name in lowercase and uppercase, respectively. */ + + WRITING_SYSTEM( dummy, DUMMY ) + WRITING_SYSTEM( latin, LATIN ) + WRITING_SYSTEM( cjk, CJK ) + WRITING_SYSTEM( indic, INDIC ) + + +/* END */ diff --git a/src/font/freetype-2.10.2/src/autofit/autofit.c b/3rdparty/freetype-2.13.2/src/autofit/autofit.c similarity index 87% rename from src/font/freetype-2.10.2/src/autofit/autofit.c rename to 3rdparty/freetype-2.13.2/src/autofit/autofit.c index 88be8bf2b..8bd609b5e 100644 --- a/src/font/freetype-2.10.2/src/autofit/autofit.c +++ b/3rdparty/freetype-2.13.2/src/autofit/autofit.c @@ -4,7 +4,7 @@ * * Auto-fitter module (body). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -17,9 +17,8 @@ #define FT_MAKE_OPTION_SINGLE_OBJECT -#include -#include "afangles.c" +#include "ft-hb.c" #include "afblue.c" #include "afcjk.c" #include "afdummy.c" @@ -27,12 +26,10 @@ #include "afhints.c" #include "afindic.c" #include "aflatin.c" -#include "aflatin2.c" #include "afloader.c" #include "afmodule.c" #include "afranges.c" #include "afshaper.c" -#include "afwarp.c" /* END */ diff --git a/3rdparty/freetype-2.13.2/src/autofit/ft-hb.c b/3rdparty/freetype-2.13.2/src/autofit/ft-hb.c new file mode 100644 index 000000000..71aee0455 --- /dev/null +++ b/3rdparty/freetype-2.13.2/src/autofit/ft-hb.c @@ -0,0 +1,115 @@ +/* + * Copyright © 2009, 2023 Red Hat, Inc. + * Copyright © 2015 Google, Inc. + * + * Permission is hereby granted, without written agreement and without + * license or royalty fees, to use, copy, modify, and distribute this + * software and its documentation for any purpose, provided that the + * above copyright notice and the following two paragraphs appear in + * all copies of this software. + * + * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR + * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES + * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN + * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH + * DAMAGE. + * + * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING, + * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS + * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO + * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS. + * + * Red Hat Author(s): Behdad Esfahbod, Matthias Clasen + * Google Author(s): Behdad Esfahbod + */ + +#include +#include + +#ifdef FT_CONFIG_OPTION_USE_HARFBUZZ + +#include "ft-hb.h" + +/* The following three functions are a more or less verbatim + * copy of corresponding HarfBuzz code from hb-ft.cc + */ + +static hb_blob_t * +hb_ft_reference_table_ (hb_face_t *face, hb_tag_t tag, void *user_data) +{ + FT_Face ft_face = (FT_Face) user_data; + FT_Byte *buffer; + FT_ULong length = 0; + FT_Error error; + + FT_UNUSED (face); + + /* Note: FreeType like HarfBuzz uses the NONE tag for fetching the entire blob */ + + error = FT_Load_Sfnt_Table (ft_face, tag, 0, NULL, &length); + if (error) + return NULL; + + buffer = (FT_Byte *) ft_smalloc (length); + if (!buffer) + return NULL; + + error = FT_Load_Sfnt_Table (ft_face, tag, 0, buffer, &length); + if (error) + { + free (buffer); + return NULL; + } + + return hb_blob_create ((const char *) buffer, length, + HB_MEMORY_MODE_WRITABLE, + buffer, ft_sfree); +} + +static hb_face_t * +hb_ft_face_create_ (FT_Face ft_face, + hb_destroy_func_t destroy) +{ + hb_face_t *face; + + if (!ft_face->stream->read) { + hb_blob_t *blob; + + blob = hb_blob_create ((const char *) ft_face->stream->base, + (unsigned int) ft_face->stream->size, + HB_MEMORY_MODE_READONLY, + ft_face, destroy); + face = hb_face_create (blob, ft_face->face_index); + hb_blob_destroy (blob); + } else { + face = hb_face_create_for_tables (hb_ft_reference_table_, ft_face, destroy); + } + + hb_face_set_index (face, ft_face->face_index); + hb_face_set_upem (face, ft_face->units_per_EM); + + return face; +} + +FT_LOCAL_DEF(hb_font_t *) +hb_ft_font_create_ (FT_Face ft_face, + hb_destroy_func_t destroy) +{ + hb_font_t *font; + hb_face_t *face; + + face = hb_ft_face_create_ (ft_face, destroy); + font = hb_font_create (face); + hb_face_destroy (face); + return font; +} + +#else /* !FT_CONFIG_OPTION_USE_HARFBUZZ */ + +/* ANSI C doesn't like empty source files */ +typedef int ft_hb_dummy_; + +#endif /* !FT_CONFIG_OPTION_USE_HARFBUZZ */ + +/* END */ diff --git a/3rdparty/freetype-2.13.2/src/autofit/ft-hb.h b/3rdparty/freetype-2.13.2/src/autofit/ft-hb.h new file mode 100644 index 000000000..92a5774bc --- /dev/null +++ b/3rdparty/freetype-2.13.2/src/autofit/ft-hb.h @@ -0,0 +1,48 @@ +/* + * Copyright © 2009, 2023 Red Hat, Inc. + * Copyright © 2015 Google, Inc. + * + * Permission is hereby granted, without written agreement and without + * license or royalty fees, to use, copy, modify, and distribute this + * software and its documentation for any purpose, provided that the + * above copyright notice and the following two paragraphs appear in + * all copies of this software. + * + * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR + * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES + * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN + * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH + * DAMAGE. + * + * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING, + * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS + * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO + * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS. + * + * Red Hat Author(s): Behdad Esfahbod, Matthias Clasen + * Google Author(s): Behdad Esfahbod + */ + +#ifndef FT_HB_H +#define FT_HB_H + +#include + +#include +#include + + +FT_BEGIN_HEADER + +FT_LOCAL(hb_font_t *) +hb_ft_font_create_ (FT_Face ft_face, + hb_destroy_func_t destroy); + + +FT_END_HEADER + +#endif /* FT_HB_H */ + + +/* END */ diff --git a/src/font/freetype-2.10.2/src/autofit/module.mk b/3rdparty/freetype-2.13.2/src/autofit/module.mk similarity index 95% rename from src/font/freetype-2.10.2/src/autofit/module.mk rename to 3rdparty/freetype-2.13.2/src/autofit/module.mk index c32781f47..95cb20ad2 100644 --- a/src/font/freetype-2.10.2/src/autofit/module.mk +++ b/3rdparty/freetype-2.13.2/src/autofit/module.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 2003-2020 by +# Copyright (C) 2003-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, diff --git a/src/font/freetype-2.10.2/src/autofit/rules.mk b/3rdparty/freetype-2.13.2/src/autofit/rules.mk similarity index 82% rename from src/font/freetype-2.10.2/src/autofit/rules.mk rename to 3rdparty/freetype-2.13.2/src/autofit/rules.mk index 553ddce6b..a46ba3f0f 100644 --- a/src/font/freetype-2.10.2/src/autofit/rules.mk +++ b/3rdparty/freetype-2.13.2/src/autofit/rules.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 2003-2020 by +# Copyright (C) 2003-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, @@ -28,8 +28,7 @@ AUTOF_COMPILE := $(CC) $(ANSIFLAGS) \ # AUTOF driver sources (i.e., C files) # -AUTOF_DRV_SRC := $(AUTOF_DIR)/afangles.c \ - $(AUTOF_DIR)/afblue.c \ +AUTOF_DRV_SRC := $(AUTOF_DIR)/afblue.c \ $(AUTOF_DIR)/afcjk.c \ $(AUTOF_DIR)/afdummy.c \ $(AUTOF_DIR)/afglobal.c \ @@ -40,17 +39,18 @@ AUTOF_DRV_SRC := $(AUTOF_DIR)/afangles.c \ $(AUTOF_DIR)/afmodule.c \ $(AUTOF_DIR)/afranges.c \ $(AUTOF_DIR)/afshaper.c \ - $(AUTOF_DIR)/afwarp.c + $(AUTOF_DIR)/ft-hb.c # AUTOF driver headers # -AUTOF_DRV_H := $(AUTOF_DRV_SRC:%c=%h) \ - $(AUTOF_DIR)/afcover.h \ - $(AUTOF_DIR)/aferrors.h \ - $(AUTOF_DIR)/afscript.h \ - $(AUTOF_DIR)/afstyles.h \ - $(AUTOF_DIR)/aftypes.h \ - $(AUTOF_DIR)/afwrtsys.h +AUTOF_DRV_H := $(AUTOF_DRV_SRC:%c=%h) \ + $(AUTOF_DIR)/afcover.h \ + $(AUTOF_DIR)/aferrors.h \ + $(AUTOF_DIR)/afscript.h \ + $(AUTOF_DIR)/afstyles.h \ + $(AUTOF_DIR)/aftypes.h \ + $(AUTOF_DIR)/afws-decl.h \ + $(AUTOF_DIR)/afws-iter.h # AUTOF driver object(s) diff --git a/src/font/freetype-2.10.2/src/base/ftadvanc.c b/3rdparty/freetype-2.13.2/src/base/ftadvanc.c similarity index 93% rename from src/font/freetype-2.10.2/src/base/ftadvanc.c rename to 3rdparty/freetype-2.13.2/src/base/ftadvanc.c index 310bbba41..de25476fe 100644 --- a/src/font/freetype-2.10.2/src/base/ftadvanc.c +++ b/3rdparty/freetype-2.13.2/src/base/ftadvanc.c @@ -4,7 +4,7 @@ * * Quick computation of advance widths (body). * - * Copyright (C) 2008-2020 by + * Copyright (C) 2008-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,15 +16,14 @@ */ -#include -#include FT_INTERNAL_DEBUG_H +#include -#include FT_ADVANCES_H -#include FT_INTERNAL_OBJECTS_H +#include +#include static FT_Error - _ft_face_scale_advances( FT_Face face, + ft_face_scale_advances_( FT_Face face, FT_Fixed* advances, FT_UInt count, FT_Int32 flags ) @@ -97,7 +96,7 @@ error = func( face, gindex, 1, flags, padvance ); if ( !error ) - return _ft_face_scale_advances( face, padvance, 1, flags ); + return ft_face_scale_advances_( face, padvance, 1, flags ); if ( FT_ERR_NEQ( error, Unimplemented_Feature ) ) return error; @@ -143,7 +142,7 @@ { error = func( face, start, count, flags, padvances ); if ( !error ) - return _ft_face_scale_advances( face, padvances, count, flags ); + return ft_face_scale_advances_( face, padvances, count, flags ); if ( FT_ERR_NEQ( error, Unimplemented_Feature ) ) return error; diff --git a/src/font/freetype-2.10.2/src/base/ftbase.c b/3rdparty/freetype-2.13.2/src/base/ftbase.c similarity index 94% rename from src/font/freetype-2.10.2/src/base/ftbase.c rename to 3rdparty/freetype-2.13.2/src/base/ftbase.c index b8242bb96..156510f00 100644 --- a/src/font/freetype-2.10.2/src/base/ftbase.c +++ b/3rdparty/freetype-2.13.2/src/base/ftbase.c @@ -4,7 +4,7 @@ * * Single object library component (body only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,7 +16,6 @@ */ -#include #define FT_MAKE_OPTION_SINGLE_OBJECT #include "ftadvanc.c" diff --git a/src/font/freetype-2.10.2/src/base/ftbase.h b/3rdparty/freetype-2.13.2/src/base/ftbase.h similarity index 92% rename from src/font/freetype-2.10.2/src/base/ftbase.h rename to 3rdparty/freetype-2.13.2/src/base/ftbase.h index 472713add..00790d3b2 100644 --- a/src/font/freetype-2.10.2/src/base/ftbase.h +++ b/3rdparty/freetype-2.13.2/src/base/ftbase.h @@ -4,7 +4,7 @@ * * Private functions used in the `base' module (specification). * - * Copyright (C) 2008-2020 by + * Copyright (C) 2008-2023 by * David Turner, Robert Wilhelm, Werner Lemberg, and suzuki toshiya. * * This file is part of the FreeType project, and may only be used, @@ -20,13 +20,17 @@ #define FTBASE_H_ -#include -#include FT_INTERNAL_OBJECTS_H +#include FT_BEGIN_HEADER + FT_DECLARE_GLYPH( ft_bitmap_glyph_class ) + FT_DECLARE_GLYPH( ft_outline_glyph_class ) + FT_DECLARE_GLYPH( ft_svg_glyph_class ) + + #ifdef FT_CONFIG_OPTION_MAC_FONTS /* MacOS resource fork cannot exceed 16MB at least for Carbon code; */ diff --git a/src/font/freetype-2.10.2/src/base/ftbbox.c b/3rdparty/freetype-2.13.2/src/base/ftbbox.c similarity index 93% rename from src/font/freetype-2.10.2/src/base/ftbbox.c rename to 3rdparty/freetype-2.13.2/src/base/ftbbox.c index 9d9f9c401..385fea404 100644 --- a/src/font/freetype-2.10.2/src/base/ftbbox.c +++ b/3rdparty/freetype-2.13.2/src/base/ftbbox.c @@ -4,7 +4,7 @@ * * FreeType bbox computation (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used @@ -24,14 +24,13 @@ */ -#include -#include FT_INTERNAL_DEBUG_H +#include -#include FT_BBOX_H -#include FT_IMAGE_H -#include FT_OUTLINE_H -#include FT_INTERNAL_CALC_H -#include FT_INTERNAL_OBJECTS_H +#include +#include +#include +#include +#include typedef struct TBBox_Rec_ @@ -83,10 +82,13 @@ * @Return: * Always 0. Needed for the interface only. */ - static int - BBox_Move_To( FT_Vector* to, - TBBox_Rec* user ) + FT_CALLBACK_DEF( int ) + BBox_Move_To( const FT_Vector* to, + void* user_ ) { + TBBox_Rec* user = (TBBox_Rec*)user_; + + FT_UPDATE_BBOX( to, user->bbox ); user->last = *to; @@ -117,10 +119,13 @@ * @Return: * Always 0. Needed for the interface only. */ - static int - BBox_Line_To( FT_Vector* to, - TBBox_Rec* user ) + FT_CALLBACK_DEF( int ) + BBox_Line_To( const FT_Vector* to, + void* user_ ) { + TBBox_Rec* user = (TBBox_Rec*)user_; + + user->last = *to; return 0; @@ -206,11 +211,14 @@ * In the case of a non-monotonous arc, we compute directly the * extremum coordinates, as it is sufficiently fast. */ - static int - BBox_Conic_To( FT_Vector* control, - FT_Vector* to, - TBBox_Rec* user ) + FT_CALLBACK_DEF( int ) + BBox_Conic_To( const FT_Vector* control, + const FT_Vector* to, + void* user_ ) { + TBBox_Rec* user = (TBBox_Rec*)user_; + + /* in case `to' is implicit and not included in bbox yet */ FT_UPDATE_BBOX( to, user->bbox ); @@ -411,12 +419,15 @@ * In the case of a non-monotonous arc, we don't compute directly * extremum coordinates, we subdivide instead. */ - static int - BBox_Cubic_To( FT_Vector* control1, - FT_Vector* control2, - FT_Vector* to, - TBBox_Rec* user ) + FT_CALLBACK_DEF( int ) + BBox_Cubic_To( const FT_Vector* control1, + const FT_Vector* control2, + const FT_Vector* to, + void* user_ ) { + TBBox_Rec* user = (TBBox_Rec*)user_; + + /* We don't need to check `to' since it is always an on-point, */ /* thus within the bbox. Only segments with an off-point outside */ /* the bbox can possibly reach new extreme values. */ diff --git a/src/font/freetype-2.10.2/src/base/ftbdf.c b/3rdparty/freetype-2.13.2/src/base/ftbdf.c similarity index 92% rename from src/font/freetype-2.10.2/src/base/ftbdf.c rename to 3rdparty/freetype-2.13.2/src/base/ftbdf.c index a239e5f87..f697c00fe 100644 --- a/src/font/freetype-2.10.2/src/base/ftbdf.c +++ b/3rdparty/freetype-2.13.2/src/base/ftbdf.c @@ -4,7 +4,7 @@ * * FreeType API for accessing BDF-specific strings (body). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,11 +16,10 @@ */ -#include -#include FT_INTERNAL_DEBUG_H +#include -#include FT_INTERNAL_OBJECTS_H -#include FT_SERVICE_BDF_H +#include +#include /* documentation is in ftbdf.h */ diff --git a/src/font/freetype-2.10.2/src/base/ftbitmap.c b/3rdparty/freetype-2.13.2/src/base/ftbitmap.c similarity index 91% rename from src/font/freetype-2.10.2/src/base/ftbitmap.c rename to 3rdparty/freetype-2.13.2/src/base/ftbitmap.c index 18ac4c5f3..1c93648dc 100644 --- a/src/font/freetype-2.10.2/src/base/ftbitmap.c +++ b/3rdparty/freetype-2.13.2/src/base/ftbitmap.c @@ -4,7 +4,7 @@ * * FreeType utility functions for bitmaps (body). * - * Copyright (C) 2004-2020 by + * Copyright (C) 2004-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,12 +16,11 @@ */ -#include -#include FT_INTERNAL_DEBUG_H +#include -#include FT_BITMAP_H -#include FT_IMAGE_H -#include FT_INTERNAL_OBJECTS_H +#include +#include +#include /************************************************************************** @@ -67,11 +66,8 @@ { FT_Memory memory; FT_Error error = FT_Err_Ok; - - FT_Int pitch; - FT_ULong size; - - FT_Int source_pitch_sign, target_pitch_sign; + FT_Int pitch; + FT_Int flip; if ( !library ) @@ -83,53 +79,29 @@ if ( source == target ) return FT_Err_Ok; - source_pitch_sign = source->pitch < 0 ? -1 : 1; - target_pitch_sign = target->pitch < 0 ? -1 : 1; + flip = ( source->pitch < 0 && target->pitch > 0 ) || + ( source->pitch > 0 && target->pitch < 0 ); - if ( !source->buffer ) - { - *target = *source; - if ( source_pitch_sign != target_pitch_sign ) - target->pitch = -target->pitch; + memory = library->memory; + FT_FREE( target->buffer ); + + *target = *source; + + if ( flip ) + target->pitch = -target->pitch; + if ( !source->buffer ) return FT_Err_Ok; - } - memory = library->memory; pitch = source->pitch; - if ( pitch < 0 ) pitch = -pitch; - size = (FT_ULong)pitch * source->rows; - - if ( target->buffer ) - { - FT_Int target_pitch = target->pitch; - FT_ULong target_size; - - if ( target_pitch < 0 ) - target_pitch = -target_pitch; - target_size = (FT_ULong)target_pitch * target->rows; - - if ( target_size != size ) - (void)FT_QREALLOC( target->buffer, target_size, size ); - } - else - (void)FT_QALLOC( target->buffer, size ); + FT_MEM_QALLOC_MULT( target->buffer, target->rows, pitch ); if ( !error ) { - unsigned char *p; - - - p = target->buffer; - *target = *source; - target->buffer = p; - - if ( source_pitch_sign == target_pitch_sign ) - FT_MEM_COPY( target->buffer, source->buffer, size ); - else + if ( flip ) { /* take care of bitmap flow */ FT_UInt i; @@ -147,6 +119,9 @@ t -= pitch; } } + else + FT_MEM_COPY( target->buffer, source->buffer, + (FT_Long)source->rows * pitch ); } return error; @@ -481,7 +456,7 @@ * A gamma of 2.2 is fair to assume. And then, we need to * undo the premultiplication too. * - * https://accessibility.kde.org/hsl-adjusted.php + * http://www.brucelindbloom.com/index.html?WorkingSpaceInfo.html#SideNotes * * We do the computation with integers only, applying a gamma of 2.0. * We guarantee 32-bit arithmetic to avoid overflow but the resulting @@ -489,9 +464,9 @@ * */ - l = ( 4732UL /* 0.0722 * 65536 */ * bgra[0] * bgra[0] + - 46871UL /* 0.7152 * 65536 */ * bgra[1] * bgra[1] + - 13933UL /* 0.2126 * 65536 */ * bgra[2] * bgra[2] ) >> 16; + l = ( 4731UL /* 0.072186 * 65536 */ * bgra[0] * bgra[0] + + 46868UL /* 0.715158 * 65536 */ * bgra[1] * bgra[1] + + 13937UL /* 0.212656 * 65536 */ * bgra[2] * bgra[2] ) >> 16; /* * Final transparency can be determined as follows. @@ -543,39 +518,31 @@ case FT_PIXEL_MODE_LCD_V: case FT_PIXEL_MODE_BGRA: { - FT_Int pad, old_target_pitch, target_pitch; - FT_ULong old_size; + FT_Int width = (FT_Int)source->width; + FT_Int neg = ( target->pitch == 0 && source->pitch < 0 ) || + target->pitch < 0; - old_target_pitch = target->pitch; - if ( old_target_pitch < 0 ) - old_target_pitch = -old_target_pitch; - - old_size = target->rows * (FT_UInt)old_target_pitch; + FT_Bitmap_Done( library, target ); target->pixel_mode = FT_PIXEL_MODE_GRAY; target->rows = source->rows; target->width = source->width; - pad = 0; - if ( alignment > 0 ) + if ( alignment ) { - pad = (FT_Int)source->width % alignment; - if ( pad != 0 ) - pad = alignment - pad; - } + FT_Int rem = width % alignment; - target_pitch = (FT_Int)source->width + pad; - if ( target_pitch > 0 && - (FT_ULong)target->rows > FT_ULONG_MAX / (FT_ULong)target_pitch ) - return FT_THROW( Invalid_Argument ); + if ( rem ) + width = alignment > 0 ? width - rem + alignment + : width - rem - alignment; + } - if ( FT_QREALLOC( target->buffer, - old_size, target->rows * (FT_UInt)target_pitch ) ) + if ( FT_QALLOC_MULT( target->buffer, target->rows, width ) ) return error; - target->pitch = target->pitch < 0 ? -target_pitch : target_pitch; + target->pitch = neg ? -width : width; } break; @@ -908,14 +875,14 @@ final_rows = ( final_ury - final_lly ) >> 6; #ifdef FT_DEBUG_LEVEL_TRACE - FT_TRACE5(( "FT_Bitmap_Blend:\n" - " source bitmap: (%d, %d) -- (%d, %d); %d x %d\n", + FT_TRACE5(( "FT_Bitmap_Blend:\n" )); + FT_TRACE5(( " source bitmap: (%ld, %ld) -- (%ld, %ld); %d x %d\n", source_llx / 64, source_lly / 64, source_urx / 64, source_ury / 64, source_->width, source_->rows )); if ( target->width && target->rows ) - FT_TRACE5(( " target bitmap: (%d, %d) -- (%d, %d); %d x %d\n", + FT_TRACE5(( " target bitmap: (%ld, %ld) -- (%ld, %ld); %d x %d\n", target_llx / 64, target_lly / 64, target_urx / 64, target_ury / 64, target->width, target->rows )); @@ -923,7 +890,7 @@ FT_TRACE5(( " target bitmap: empty\n" )); if ( final_width && final_rows ) - FT_TRACE5(( " final bitmap: (%d, %d) -- (%d, %d); %d x %d\n", + FT_TRACE5(( " final bitmap: (%ld, %ld) -- (%ld, %ld); %d x %d\n", final_llx / 64, final_lly / 64, final_urx / 64, final_ury / 64, final_width, final_rows )); diff --git a/src/font/freetype-2.10.2/src/base/ftcalc.c b/3rdparty/freetype-2.13.2/src/base/ftcalc.c similarity index 91% rename from src/font/freetype-2.10.2/src/base/ftcalc.c rename to 3rdparty/freetype-2.13.2/src/base/ftcalc.c index 53550057b..c5bc7e3b1 100644 --- a/src/font/freetype-2.10.2/src/base/ftcalc.c +++ b/3rdparty/freetype-2.13.2/src/base/ftcalc.c @@ -4,7 +4,7 @@ * * Arithmetic computations (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -32,12 +32,11 @@ */ -#include -#include FT_GLYPH_H -#include FT_TRIGONOMETRY_H -#include FT_INTERNAL_CALC_H -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_OBJECTS_H +#include +#include +#include +#include +#include #ifdef FT_MULFIX_ASSEMBLER @@ -46,7 +45,7 @@ /* we need to emulate a 64-bit data type if a real one isn't available */ -#ifndef FT_LONG64 +#ifndef FT_INT64 typedef struct FT_Int64_ { @@ -55,7 +54,7 @@ } FT_Int64; -#endif /* !FT_LONG64 */ +#endif /* !FT_INT64 */ /************************************************************************** @@ -80,7 +79,7 @@ FT_END_STMNT /* The following three functions are available regardless of whether */ - /* FT_LONG64 is defined. */ + /* FT_INT64 is defined. */ /* documentation is in freetype.h */ @@ -110,7 +109,7 @@ #ifndef FT_MSB - FT_BASE_DEF ( FT_Int ) + FT_BASE_DEF( FT_Int ) FT_MSB( FT_UInt32 z ) { FT_Int shift = 0; @@ -165,7 +164,7 @@ } -#ifdef FT_LONG64 +#ifdef FT_INT64 /* documentation is in freetype.h */ @@ -273,7 +272,7 @@ } -#else /* !FT_LONG64 */ +#else /* !FT_INT64 */ static void @@ -652,7 +651,7 @@ } -#endif /* !FT_LONG64 */ +#endif /* !FT_INT64 */ /* documentation is in ftglyph.h */ @@ -750,65 +749,43 @@ FT_BASE_DEF( FT_Bool ) FT_Matrix_Check( const FT_Matrix* matrix ) { - FT_Matrix m; - FT_Fixed val[4]; - FT_Fixed nonzero_minval, maxval; - FT_Fixed temp1, temp2; - FT_UInt i; + FT_Fixed xx, xy, yx, yy; + FT_Fixed val; + FT_Int shift; + FT_ULong temp1, temp2; if ( !matrix ) return 0; - val[0] = FT_ABS( matrix->xx ); - val[1] = FT_ABS( matrix->xy ); - val[2] = FT_ABS( matrix->yx ); - val[3] = FT_ABS( matrix->yy ); - - /* - * To avoid overflow, we ensure that each value is not larger than - * - * int(sqrt(2^31 / 4)) = 23170 ; - * - * we also check that no value becomes zero if we have to scale. - */ - - maxval = 0; - nonzero_minval = FT_LONG_MAX; - - for ( i = 0; i < 4; i++ ) - { - if ( val[i] > maxval ) - maxval = val[i]; - if ( val[i] && val[i] < nonzero_minval ) - nonzero_minval = val[i]; - } + xx = matrix->xx; + xy = matrix->xy; + yx = matrix->yx; + yy = matrix->yy; + val = FT_ABS( xx ) | FT_ABS( xy ) | FT_ABS( yx ) | FT_ABS( yy ); - /* we only handle 32bit values */ - if ( maxval > 0x7FFFFFFFL ) + /* we only handle non-zero 32-bit values */ + if ( !val || val > 0x7FFFFFFFL ) return 0; - if ( maxval > 23170 ) - { - FT_Fixed scale = FT_DivFix( maxval, 23170 ); - + /* Scale matrix to avoid the temp1 overflow, which is */ + /* more stringent than avoiding the temp2 overflow. */ - if ( !FT_DivFix( nonzero_minval, scale ) ) - return 0; /* value range too large */ + shift = FT_MSB( val ) - 12; - m.xx = FT_DivFix( matrix->xx, scale ); - m.xy = FT_DivFix( matrix->xy, scale ); - m.yx = FT_DivFix( matrix->yx, scale ); - m.yy = FT_DivFix( matrix->yy, scale ); + if ( shift > 0 ) + { + xx >>= shift; + xy >>= shift; + yx >>= shift; + yy >>= shift; } - else - m = *matrix; - temp1 = FT_ABS( m.xx * m.yy - m.xy * m.yx ); - temp2 = m.xx * m.xx + m.xy * m.xy + m.yx * m.yx + m.yy * m.yy; + temp1 = 32U * (FT_ULong)FT_ABS( xx * yy - xy * yx ); + temp2 = (FT_ULong)( xx * xx ) + (FT_ULong)( xy * xy ) + + (FT_ULong)( yx * yx ) + (FT_ULong)( yy * yy ); - if ( temp1 == 0 || - temp2 / temp1 > 50 ) + if ( temp1 <= temp2 ) return 0; return 1; @@ -986,7 +963,7 @@ /* we silently ignore overflow errors since such large values */ /* lead to even more (harmless) rendering errors later on */ -#ifdef FT_LONG64 +#ifdef FT_INT64 FT_Int64 delta = SUB_INT64( MUL_INT64( in_x, out_y ), MUL_INT64( in_y, out_x ) ); @@ -1062,7 +1039,7 @@ /* */ /* This approach has the advantage that the angle between */ /* `in' and `out' is not checked. In case one of the two */ - /* vectors is `dominant', this is, much larger than the */ + /* vectors is `dominant', that is, much larger than the */ /* other vector, we thus always have a flat corner. */ /* */ /* hypotenuse */ @@ -1086,4 +1063,65 @@ } + FT_BASE_DEF( FT_Int32 ) + FT_MulAddFix( FT_Fixed* s, + FT_Int32* f, + FT_UInt count ) + { + FT_UInt i; + FT_Int64 temp; + + +#ifdef FT_INT64 + temp = 0; + + for ( i = 0; i < count; ++i ) + temp += (FT_Int64)s[i] * f[i]; + + return (FT_Int32)( ( temp + 0x8000 ) >> 16 ); +#else + temp.hi = 0; + temp.lo = 0; + + for ( i = 0; i < count; ++i ) + { + FT_Int64 multResult; + + FT_Int sign = 1; + FT_UInt32 carry = 0; + + FT_UInt32 scalar; + FT_UInt32 factor; + + + scalar = (FT_UInt32)s[i]; + factor = (FT_UInt32)f[i]; + + FT_MOVE_SIGN( s[i], scalar, sign ); + FT_MOVE_SIGN( f[i], factor, sign ); + + ft_multo64( scalar, factor, &multResult ); + + if ( sign < 0 ) + { + /* Emulated `FT_Int64` negation. */ + carry = ( multResult.lo == 0 ); + + multResult.lo = ~multResult.lo + 1; + multResult.hi = ~multResult.hi + carry; + } + + FT_Add64( &temp, &multResult, &temp ); + } + + /* Shift and round value. */ + return (FT_Int32)( ( ( temp.hi << 16 ) | ( temp.lo >> 16 ) ) + + ( 1 & ( temp.lo >> 15 ) ) ); + + +#endif /* !FT_INT64 */ + + } + + /* END */ diff --git a/src/font/freetype-2.10.2/src/base/ftcid.c b/3rdparty/freetype-2.13.2/src/base/ftcid.c similarity index 94% rename from src/font/freetype-2.10.2/src/base/ftcid.c rename to 3rdparty/freetype-2.13.2/src/base/ftcid.c index 17c25730e..866cd23e9 100644 --- a/src/font/freetype-2.10.2/src/base/ftcid.c +++ b/3rdparty/freetype-2.13.2/src/base/ftcid.c @@ -4,7 +4,7 @@ * * FreeType API for accessing CID font information. * - * Copyright (C) 2007-2020 by + * Copyright (C) 2007-2023 by * Derek Clegg and Michael Toftdal. * * This file is part of the FreeType project, and may only be used, @@ -16,10 +16,9 @@ */ -#include -#include FT_CID_H -#include FT_INTERNAL_OBJECTS_H -#include FT_SERVICE_CID_H +#include +#include +#include /* documentation is in ftcid.h */ diff --git a/src/font/freetype-2.10.2/src/base/ftcolor.c b/3rdparty/freetype-2.13.2/src/base/ftcolor.c similarity index 94% rename from src/font/freetype-2.10.2/src/base/ftcolor.c rename to 3rdparty/freetype-2.13.2/src/base/ftcolor.c index 986e9924a..bcd6e893d 100644 --- a/src/font/freetype-2.10.2/src/base/ftcolor.c +++ b/3rdparty/freetype-2.13.2/src/base/ftcolor.c @@ -4,7 +4,7 @@ * * FreeType's glyph color management (body). * - * Copyright (C) 2018-2020 by + * Copyright (C) 2018-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,11 +16,10 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_SFNT_H -#include FT_INTERNAL_TRUETYPE_TYPES_H -#include FT_COLOR_H +#include +#include +#include +#include #ifdef TT_CONFIG_OPTION_COLOR_LAYERS diff --git a/src/font/freetype-2.10.2/src/base/ftdbgmem.c b/3rdparty/freetype-2.13.2/src/base/ftdbgmem.c similarity index 90% rename from src/font/freetype-2.10.2/src/base/ftdbgmem.c rename to 3rdparty/freetype-2.13.2/src/base/ftdbgmem.c index 7f06c8600..8fab50dd0 100644 --- a/src/font/freetype-2.10.2/src/base/ftdbgmem.c +++ b/3rdparty/freetype-2.13.2/src/base/ftdbgmem.c @@ -4,7 +4,7 @@ * * Memory debugger (body). * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -18,11 +18,11 @@ #include #include FT_CONFIG_CONFIG_H -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_MEMORY_H -#include FT_SYSTEM_H -#include FT_ERRORS_H -#include FT_TYPES_H +#include +#include +#include +#include +#include #ifdef FT_DEBUG_MEMORY @@ -35,8 +35,8 @@ #include FT_CONFIG_STANDARD_LIBRARY_H - FT_BASE_DEF( const char* ) _ft_debug_file = NULL; - FT_BASE_DEF( long ) _ft_debug_lineno = 0; + FT_BASE_DEF( const char* ) ft_debug_file_ = NULL; + FT_BASE_DEF( long ) ft_debug_lineno_ = 0; extern void FT_DumpMemory( FT_Memory memory ); @@ -302,46 +302,6 @@ } - static FT_MemTable - ft_mem_table_new( FT_Memory memory ) - { - FT_MemTable table; - - - table = (FT_MemTable)memory->alloc( memory, sizeof ( *table ) ); - if ( !table ) - goto Exit; - - FT_ZERO( table ); - - table->size = FT_MEM_SIZE_MIN; - table->nodes = 0; - - table->memory = memory; - - table->memory_user = memory->user; - - table->alloc = memory->alloc; - table->realloc = memory->realloc; - table->free = memory->free; - - table->buckets = (FT_MemNode *) - memory->alloc( - memory, - table->size * (FT_Long)sizeof ( FT_MemNode ) ); - if ( table->buckets ) - FT_ARRAY_ZERO( table->buckets, table->size ); - else - { - memory->free( memory, table ); - table = NULL; - } - - Exit: - return table; - } - - static void ft_mem_table_destroy( FT_MemTable table ) { @@ -350,8 +310,6 @@ FT_Long leaks = 0; - FT_DumpMemory( table->memory ); - /* remove all blocks from the table, revealing leaked ones */ for ( i = 0; i < table->size; i++ ) { @@ -413,8 +371,6 @@ printf( "FreeType: maximum memory footprint = %ld\n", table->alloc_max ); - ft_mem_table_free( table, table ); - if ( leak_count > 0 ) ft_mem_debug_panic( "FreeType: %ld bytes of memory leaked in %ld blocks\n", @@ -459,8 +415,8 @@ /* cast to FT_PtrDist first since void* can be larger */ /* than FT_UInt32 and GCC 4.1.1 emits a warning */ - hash = (FT_UInt32)(FT_PtrDist)(void*)_ft_debug_file + - (FT_UInt32)( 5 * _ft_debug_lineno ); + hash = (FT_UInt32)(FT_PtrDist)(void*)ft_debug_file_ + + (FT_UInt32)( 5 * ft_debug_lineno_ ); pnode = &table->sources[hash % FT_MEM_SOURCE_BUCKETS]; for (;;) @@ -469,8 +425,8 @@ if ( !node ) break; - if ( node->file_name == _ft_debug_file && - node->line_no == _ft_debug_lineno ) + if ( node->file_name == ft_debug_file_ && + node->line_no == ft_debug_lineno_ ) goto Exit; pnode = &node->link; @@ -481,8 +437,8 @@ ft_mem_debug_panic( "not enough memory to perform memory debugging\n" ); - node->file_name = _ft_debug_file; - node->line_no = _ft_debug_lineno; + node->file_name = ft_debug_file_; + node->line_no = ft_debug_lineno_; node->cur_blocks = 0; node->max_blocks = 0; @@ -539,7 +495,7 @@ "org=%s:%d new=%s:%d\n", node->address, node->size, FT_FILENAME( node->source->file_name ), node->source->line_no, - FT_FILENAME( _ft_debug_file ), _ft_debug_lineno ); + FT_FILENAME( ft_debug_file_ ), ft_debug_lineno_ ); } } @@ -626,7 +582,7 @@ " Block was allocated at (%s:%ld)\n" " and released at (%s:%ld).", address, - FT_FILENAME( _ft_debug_file ), _ft_debug_lineno, + FT_FILENAME( ft_debug_file_ ), ft_debug_lineno_, FT_FILENAME( node->source->file_name ), node->source->line_no, FT_FILENAME( node->free_file_name ), node->free_line_no ); @@ -648,8 +604,8 @@ /* we simply invert the node's size to indicate that the node */ /* was freed. */ node->size = -node->size; - node->free_file_name = _ft_debug_file; - node->free_line_no = _ft_debug_lineno; + node->free_file_name = ft_debug_file_; + node->free_line_no = ft_debug_lineno_; } else { @@ -671,7 +627,7 @@ ft_mem_debug_panic( "trying to free unknown block at %p in (%s:%ld)\n", address, - FT_FILENAME( _ft_debug_file ), _ft_debug_lineno ); + FT_FILENAME( ft_debug_file_ ), ft_debug_lineno_ ); } } @@ -705,8 +661,8 @@ table->alloc_count++; } - _ft_debug_file = ""; - _ft_debug_lineno = 0; + ft_debug_file_ = ""; + ft_debug_lineno_ = 0; return (FT_Pointer)block; } @@ -721,8 +677,8 @@ if ( !block ) ft_mem_debug_panic( "trying to free NULL in (%s:%ld)", - FT_FILENAME( _ft_debug_file ), - _ft_debug_lineno ); + FT_FILENAME( ft_debug_file_ ), + ft_debug_lineno_ ); ft_mem_table_remove( table, (FT_Byte*)block, 0 ); @@ -731,8 +687,8 @@ table->alloc_count--; - _ft_debug_file = ""; - _ft_debug_lineno = 0; + ft_debug_file_ = ""; + ft_debug_lineno_ = 0; } @@ -747,8 +703,8 @@ FT_Pointer new_block; FT_Long delta; - const char* file_name = FT_FILENAME( _ft_debug_file ); - FT_Long line_no = _ft_debug_lineno; + const char* file_name = FT_FILENAME( ft_debug_file_ ); + FT_Long line_no = ft_debug_lineno_; /* unlikely, but possible */ @@ -811,8 +767,8 @@ ft_mem_table_remove( table, (FT_Byte*)block, delta ); - _ft_debug_file = ""; - _ft_debug_lineno = 0; + ft_debug_file_ = ""; + ft_debug_lineno_ = 0; if ( !table->keep_alive ) ft_mem_table_free( table, block ); @@ -821,17 +777,30 @@ } - extern FT_Int + extern void ft_mem_debug_init( FT_Memory memory ) { FT_MemTable table; - FT_Int result = 0; - if ( ft_getenv( "FT2_DEBUG_MEMORY" ) ) + if ( !ft_getenv( "FT2_DEBUG_MEMORY" ) ) + return; + + table = (FT_MemTable)memory->alloc( memory, sizeof ( *table ) ); + + if ( table ) { - table = ft_mem_table_new( memory ); - if ( table ) + FT_ZERO( table ); + + table->memory = memory; + table->memory_user = memory->user; + table->alloc = memory->alloc; + table->realloc = memory->realloc; + table->free = memory->free; + + ft_mem_table_resize( table ); + + if ( table->size ) { const char* p; @@ -876,33 +845,36 @@ if ( keep_alive > 0 ) table->keep_alive = 1; } - - result = 1; } + else + memory->free( memory, table ); } - return result; } extern void ft_mem_debug_done( FT_Memory memory ) { - FT_MemTable table = (FT_MemTable)memory->user; + if ( memory->free == ft_mem_debug_free ) + { + FT_MemTable table = (FT_MemTable)memory->user; - if ( table ) - { + FT_DumpMemory( memory ); + + ft_mem_table_destroy( table ); + memory->free = table->free; memory->realloc = table->realloc; memory->alloc = table->alloc; + memory->user = table->memory_user; - ft_mem_table_destroy( table ); - memory->user = NULL; + memory->free( memory, table ); } } - static int + FT_COMPARE_DEF( int ) ft_mem_source_compare( const void* p1, const void* p2 ) { @@ -922,11 +894,9 @@ extern void FT_DumpMemory( FT_Memory memory ) { - FT_MemTable table = (FT_MemTable)memory->user; - - - if ( table ) + if ( memory->free == ft_mem_debug_free ) { + FT_MemTable table = (FT_MemTable)memory->user; FT_MemSource* bucket = table->sources; FT_MemSource* limit = bucket + FT_MEM_SOURCE_BUCKETS; FT_MemSource* sources; @@ -993,7 +963,7 @@ #else /* !FT_DEBUG_MEMORY */ /* ANSI C doesn't like empty source files */ - typedef int _debug_mem_dummy; + typedef int debug_mem_dummy_; #endif /* !FT_DEBUG_MEMORY */ diff --git a/3rdparty/freetype-2.13.2/src/base/ftdebug.c b/3rdparty/freetype-2.13.2/src/base/ftdebug.c new file mode 100644 index 000000000..61c4563b0 --- /dev/null +++ b/3rdparty/freetype-2.13.2/src/base/ftdebug.c @@ -0,0 +1,644 @@ +/**************************************************************************** + * + * ftdebug.c + * + * Debugging and logging component (body). + * + * Copyright (C) 1996-2023 by + * David Turner, Robert Wilhelm, and Werner Lemberg. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + + /************************************************************************** + * + * This component contains various macros and functions used to ease the + * debugging of the FreeType engine. Its main purpose is in assertion + * checking, tracing, and error detection. + * + * There are now three debugging modes: + * + * - trace mode + * + * Error and trace messages are sent to the log file (which can be the + * standard error output). + * + * - error mode + * + * Only error messages are generated. + * + * - release mode: + * + * No error message is sent or generated. The code is free from any + * debugging parts. + * + */ + + +#include +#include +#include +#include + + +#ifdef FT_DEBUG_LOGGING + + /************************************************************************** + * + * Variables used to control logging. + * + * 1. `ft_default_trace_level` stores the value of trace levels, which are + * provided to FreeType using the `FT2_DEBUG` environment variable. + * + * 2. `ft_fileptr` stores the `FILE*` handle. + * + * 3. `ft_component` is a string that holds the name of `FT_COMPONENT`. + * + * 4. The flag `ft_component_flag` prints the name of `FT_COMPONENT` along + * with the actual log message if set to true. + * + * 5. The flag `ft_timestamp_flag` prints time along with the actual log + * message if set to ture. + * + * 6. `ft_have_newline_char` is used to differentiate between a log + * message with and without a trailing newline character. + * + * 7. `ft_custom_trace_level` stores the custom trace level value, which + * is provided by the user at run-time. + * + * We use `static` to avoid 'unused variable' warnings. + * + */ + static const char* ft_default_trace_level = NULL; + static FILE* ft_fileptr = NULL; + static const char* ft_component = NULL; + static FT_Bool ft_component_flag = FALSE; + static FT_Bool ft_timestamp_flag = FALSE; + static FT_Bool ft_have_newline_char = TRUE; + static const char* ft_custom_trace_level = NULL; + + /* declared in ftdebug.h */ + + dlg_handler ft_default_log_handler = NULL; + FT_Custom_Log_Handler custom_output_handler = NULL; + +#endif /* FT_DEBUG_LOGGING */ + + +#ifdef FT_DEBUG_LEVEL_ERROR + + /* documentation is in ftdebug.h */ + + FT_BASE_DEF( void ) + FT_Message( const char* fmt, + ... ) + { + va_list ap; + + + va_start( ap, fmt ); + vfprintf( stderr, fmt, ap ); + va_end( ap ); + } + + + /* documentation is in ftdebug.h */ + + FT_BASE_DEF( void ) + FT_Panic( const char* fmt, + ... ) + { + va_list ap; + + + va_start( ap, fmt ); + vfprintf( stderr, fmt, ap ); + va_end( ap ); + + exit( EXIT_FAILURE ); + } + + + /* documentation is in ftdebug.h */ + + FT_BASE_DEF( int ) + FT_Throw( FT_Error error, + int line, + const char* file ) + { +#if 0 + /* activating the code in this block makes FreeType very chatty */ + fprintf( stderr, + "%s:%d: error 0x%02x: %s\n", + file, + line, + error, + FT_Error_String( error ) ); +#else + FT_UNUSED( error ); + FT_UNUSED( line ); + FT_UNUSED( file ); +#endif + + return 0; + } + +#endif /* FT_DEBUG_LEVEL_ERROR */ + + +#ifdef FT_DEBUG_LEVEL_TRACE + + /* array of trace levels, initialized to 0; */ + /* this gets adjusted at run-time */ + static int ft_trace_levels_enabled[trace_count]; + + /* array of trace levels, always initialized to 0 */ + static int ft_trace_levels_disabled[trace_count]; + + /* a pointer to either `ft_trace_levels_enabled' */ + /* or `ft_trace_levels_disabled' */ + int* ft_trace_levels; + + /* define array of trace toggle names */ +#define FT_TRACE_DEF( x ) #x , + + static const char* ft_trace_toggles[trace_count + 1] = + { +#include + NULL + }; + +#undef FT_TRACE_DEF + + + /* documentation is in ftdebug.h */ + + FT_BASE_DEF( FT_Int ) + FT_Trace_Get_Count( void ) + { + return trace_count; + } + + + /* documentation is in ftdebug.h */ + + FT_BASE_DEF( const char * ) + FT_Trace_Get_Name( FT_Int idx ) + { + int max = FT_Trace_Get_Count(); + + + if ( idx < max ) + return ft_trace_toggles[idx]; + else + return NULL; + } + + + /* documentation is in ftdebug.h */ + + FT_BASE_DEF( void ) + FT_Trace_Disable( void ) + { + ft_trace_levels = ft_trace_levels_disabled; + } + + + /* documentation is in ftdebug.h */ + + FT_BASE_DEF( void ) + FT_Trace_Enable( void ) + { + ft_trace_levels = ft_trace_levels_enabled; + } + + + /************************************************************************** + * + * Initialize the tracing sub-system. This is done by retrieving the + * value of the `FT2_DEBUG' environment variable. It must be a list of + * toggles, separated by spaces, `;', or `,'. Example: + * + * export FT2_DEBUG="any:3 memory:7 stream:5" + * + * This requests that all levels be set to 3, except the trace level for + * the memory and stream components which are set to 7 and 5, + * respectively. + * + * See the file `include/freetype/internal/fttrace.h' for details of + * the available toggle names. + * + * The level must be between 0 and 7; 0 means quiet (except for serious + * runtime errors), and 7 means _very_ verbose. + */ + FT_BASE_DEF( void ) + ft_debug_init( void ) + { + const char* ft2_debug = NULL; + + +#ifdef FT_DEBUG_LOGGING + if ( ft_custom_trace_level != NULL ) + ft2_debug = ft_custom_trace_level; + else + ft2_debug = ft_default_trace_level; +#else + ft2_debug = ft_getenv( "FT2_DEBUG" ); +#endif + + if ( ft2_debug ) + { + const char* p = ft2_debug; + const char* q; + + + for ( ; *p; p++ ) + { + /* skip leading whitespace and separators */ + if ( *p == ' ' || *p == '\t' || *p == ',' || *p == ';' || *p == '=' ) + continue; + +#ifdef FT_DEBUG_LOGGING + + /* check extra arguments for logging */ + if ( *p == '-' ) + { + const char* r = ++p; + + + if ( *r == 'v' ) + { + const char* s = ++r; + + + ft_component_flag = TRUE; + + if ( *s == 't' ) + { + ft_timestamp_flag = TRUE; + p++; + } + + p++; + } + + else if ( *r == 't' ) + { + const char* s = ++r; + + + ft_timestamp_flag = TRUE; + + if ( *s == 'v' ) + { + ft_component_flag = TRUE; + p++; + } + + p++; + } + } + +#endif /* FT_DEBUG_LOGGING */ + + /* read toggle name, followed by ':' */ + q = p; + while ( *p && *p != ':' ) + p++; + + if ( !*p ) + break; + + if ( *p == ':' && p > q ) + { + FT_Int n, i, len = (FT_Int)( p - q ); + FT_Int level = -1, found = -1; + + + for ( n = 0; n < trace_count; n++ ) + { + const char* toggle = ft_trace_toggles[n]; + + + for ( i = 0; i < len; i++ ) + { + if ( toggle[i] != q[i] ) + break; + } + + if ( i == len && toggle[i] == 0 ) + { + found = n; + break; + } + } + + /* read level */ + p++; + if ( *p ) + { + level = *p - '0'; + if ( level < 0 || level > 7 ) + level = -1; + } + + if ( found >= 0 && level >= 0 ) + { + if ( found == trace_any ) + { + /* special case for `any' */ + for ( n = 0; n < trace_count; n++ ) + ft_trace_levels_enabled[n] = level; + } + else + ft_trace_levels_enabled[found] = level; + } + } + } + } + + ft_trace_levels = ft_trace_levels_enabled; + } + + +#else /* !FT_DEBUG_LEVEL_TRACE */ + + + FT_BASE_DEF( void ) + ft_debug_init( void ) + { + /* nothing */ + } + + + FT_BASE_DEF( FT_Int ) + FT_Trace_Get_Count( void ) + { + return 0; + } + + + FT_BASE_DEF( const char * ) + FT_Trace_Get_Name( FT_Int idx ) + { + FT_UNUSED( idx ); + + return NULL; + } + + + FT_BASE_DEF( void ) + FT_Trace_Disable( void ) + { + /* nothing */ + } + + + /* documentation is in ftdebug.h */ + + FT_BASE_DEF( void ) + FT_Trace_Enable( void ) + { + /* nothing */ + } + +#endif /* !FT_DEBUG_LEVEL_TRACE */ + + +#ifdef FT_DEBUG_LOGGING + + /************************************************************************** + * + * Initialize and de-initialize 'dlg' library. + * + */ + + FT_BASE_DEF( void ) + ft_logging_init( void ) + { + ft_default_log_handler = ft_log_handler; + ft_default_trace_level = ft_getenv( "FT2_DEBUG" ); + + if ( ft_getenv( "FT_LOGGING_FILE" ) ) + ft_fileptr = ft_fopen( ft_getenv( "FT_LOGGING_FILE" ), "w" ); + else + ft_fileptr = stderr; + + ft_debug_init(); + + /* Set the default output handler for 'dlg'. */ + dlg_set_handler( ft_default_log_handler, NULL ); + } + + + FT_BASE_DEF( void ) + ft_logging_deinit( void ) + { + if ( ft_fileptr != stderr ) + ft_fclose( ft_fileptr ); + } + + + /************************************************************************** + * + * An output log handler for FreeType. + * + */ + FT_BASE_DEF( void ) + ft_log_handler( const struct dlg_origin* origin, + const char* string, + void* data ) + { + char features_buf[128]; + char* bufp = features_buf; + + FT_UNUSED( data ); + + + if ( ft_have_newline_char ) + { + const char* features = NULL; + size_t features_length = 0; + + +#define FEATURES_TIMESTAMP "[%h:%m] " +#define FEATURES_COMPONENT "[%t] " +#define FEATURES_TIMESTAMP_COMPONENT "[%h:%m %t] " + + if ( ft_timestamp_flag && ft_component_flag ) + { + features = FEATURES_TIMESTAMP_COMPONENT; + features_length = sizeof ( FEATURES_TIMESTAMP_COMPONENT ); + } + else if ( ft_timestamp_flag ) + { + features = FEATURES_TIMESTAMP; + features_length = sizeof ( FEATURES_TIMESTAMP ); + } + else if ( ft_component_flag ) + { + features = FEATURES_COMPONENT; + features_length = sizeof ( FEATURES_COMPONENT ); + } + + if ( ft_component_flag || ft_timestamp_flag ) + { + ft_strncpy( features_buf, features, features_length ); + bufp += features_length - 1; + } + + if ( ft_component_flag ) + { + size_t tag_length = ft_strlen( *origin->tags ); + size_t i; + + + /* To vertically align tracing messages we compensate the */ + /* different FT_COMPONENT string lengths by inserting an */ + /* appropriate amount of space characters. */ + for ( i = 0; + i < FT_MAX_TRACE_LEVEL_LENGTH - tag_length; + i++ ) + *bufp++ = ' '; + } + } + + /* Finally add the format string for the tracing message. */ + *bufp++ = '%'; + *bufp++ = 'c'; + *bufp = '\0'; + + dlg_generic_outputf_stream( ft_fileptr, + (const char*)features_buf, + origin, + string, + dlg_default_output_styles, + true ); + + if ( ft_strrchr( string, '\n' ) ) + ft_have_newline_char = TRUE; + else + ft_have_newline_char = FALSE; + } + + + /* documentation is in ftdebug.h */ + FT_BASE_DEF( void ) + ft_add_tag( const char* tag ) + { + ft_component = tag; + + dlg_add_tag( tag, NULL ); + } + + + /* documentation is in ftdebug.h */ + FT_BASE_DEF( void ) + ft_remove_tag( const char* tag ) + { + dlg_remove_tag( tag, NULL ); + } + + + /* documentation is in ftlogging.h */ + + FT_EXPORT_DEF( void ) + FT_Trace_Set_Level( const char* level ) + { + ft_component_flag = FALSE; + ft_timestamp_flag = FALSE; + ft_custom_trace_level = level; + + ft_debug_init(); + } + + + /* documentation is in ftlogging.h */ + + FT_EXPORT_DEF( void ) + FT_Trace_Set_Default_Level( void ) + { + ft_component_flag = FALSE; + ft_timestamp_flag = FALSE; + ft_custom_trace_level = NULL; + + ft_debug_init(); + } + + + /************************************************************************** + * + * Functions to handle a custom log handler. + * + */ + + /* documentation is in ftlogging.h */ + + FT_EXPORT_DEF( void ) + FT_Set_Log_Handler( FT_Custom_Log_Handler handler ) + { + custom_output_handler = handler; + } + + + /* documentation is in ftlogging.h */ + + FT_EXPORT_DEF( void ) + FT_Set_Default_Log_Handler( void ) + { + custom_output_handler = NULL; + } + + + /* documentation is in ftdebug.h */ + FT_BASE_DEF( void ) + FT_Logging_Callback( const char* fmt, + ... ) + { + va_list ap; + + + va_start( ap, fmt ); + custom_output_handler( ft_component, fmt, ap ); + va_end( ap ); + } + +#else /* !FT_DEBUG_LOGGING */ + + FT_EXPORT_DEF( void ) + FT_Trace_Set_Level( const char* level ) + { + FT_UNUSED( level ); + } + + + FT_EXPORT_DEF( void ) + FT_Trace_Set_Default_Level( void ) + { + /* nothing */ + } + + + FT_EXPORT_DEF( void ) + FT_Set_Log_Handler( FT_Custom_Log_Handler handler ) + { + FT_UNUSED( handler ); + } + + + FT_EXPORT_DEF( void ) + FT_Set_Default_Log_Handler( void ) + { + /* nothing */ + } + +#endif /* !FT_DEBUG_LOGGING */ + + +/* END */ diff --git a/src/font/freetype-2.10.2/src/base/fterrors.c b/3rdparty/freetype-2.13.2/src/base/fterrors.c similarity index 89% rename from src/font/freetype-2.10.2/src/base/fterrors.c rename to 3rdparty/freetype-2.13.2/src/base/fterrors.c index 8aa688fbe..5ad9709c8 100644 --- a/src/font/freetype-2.10.2/src/base/fterrors.c +++ b/3rdparty/freetype-2.13.2/src/base/fterrors.c @@ -4,7 +4,7 @@ * * FreeType API for error code handling. * - * Copyright (C) 2018-2020 by + * Copyright (C) 2018-2023 by * Armin Hasitzka, David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,9 +16,8 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_ERRORS_H +#include +#include /* documentation is in fterrors.h */ @@ -38,7 +37,7 @@ #define FT_ERRORDEF( e, v, s ) case v: return s; #define FT_ERROR_END_LIST } -#include FT_ERRORS_H +#include #endif /* defined( FT_CONFIG_OPTION_ERROR_STRINGS ) || ... */ diff --git a/src/font/freetype-2.10.2/src/base/ftfntfmt.c b/3rdparty/freetype-2.13.2/src/base/ftfntfmt.c similarity index 87% rename from src/font/freetype-2.10.2/src/base/ftfntfmt.c rename to 3rdparty/freetype-2.13.2/src/base/ftfntfmt.c index 95e9b6e4c..0b41f7cc8 100644 --- a/src/font/freetype-2.10.2/src/base/ftfntfmt.c +++ b/3rdparty/freetype-2.13.2/src/base/ftfntfmt.c @@ -4,7 +4,7 @@ * * FreeType utility file for font formats (body). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,10 +16,9 @@ */ -#include -#include FT_FONT_FORMATS_H -#include FT_INTERNAL_OBJECTS_H -#include FT_SERVICE_FONT_FORMAT_H +#include +#include +#include /* documentation is in ftfntfmt.h */ diff --git a/src/font/freetype-2.10.2/src/base/ftfstype.c b/3rdparty/freetype-2.13.2/src/base/ftfstype.c similarity index 88% rename from src/font/freetype-2.10.2/src/base/ftfstype.c rename to 3rdparty/freetype-2.13.2/src/base/ftfstype.c index 461d85707..ea24e64c6 100644 --- a/src/font/freetype-2.10.2/src/base/ftfstype.c +++ b/3rdparty/freetype-2.13.2/src/base/ftfstype.c @@ -4,7 +4,7 @@ * * FreeType utility file to access FSType data (body). * - * Copyright (C) 2008-2020 by + * Copyright (C) 2008-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -15,11 +15,10 @@ * */ -#include -#include FT_TYPE1_TABLES_H -#include FT_TRUETYPE_TABLES_H -#include FT_INTERNAL_SERVICE_H -#include FT_SERVICE_POSTSCRIPT_INFO_H +#include +#include +#include +#include /* documentation is in freetype.h */ diff --git a/src/font/freetype-2.10.2/src/base/ftgasp.c b/3rdparty/freetype-2.13.2/src/base/ftgasp.c similarity index 92% rename from src/font/freetype-2.10.2/src/base/ftgasp.c rename to 3rdparty/freetype-2.13.2/src/base/ftgasp.c index 0fd80b9cd..29b7b08b7 100644 --- a/src/font/freetype-2.10.2/src/base/ftgasp.c +++ b/3rdparty/freetype-2.13.2/src/base/ftgasp.c @@ -4,7 +4,7 @@ * * Access of TrueType's `gasp' table (body). * - * Copyright (C) 2007-2020 by + * Copyright (C) 2007-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,9 +16,8 @@ */ -#include -#include FT_GASP_H -#include FT_INTERNAL_TRUETYPE_TYPES_H +#include +#include FT_EXPORT_DEF( FT_Int ) diff --git a/src/font/freetype-2.10.2/src/base/ftgloadr.c b/3rdparty/freetype-2.13.2/src/base/ftgloadr.c similarity index 92% rename from src/font/freetype-2.10.2/src/base/ftgloadr.c rename to 3rdparty/freetype-2.13.2/src/base/ftgloadr.c index 6032885c6..9823d09e4 100644 --- a/src/font/freetype-2.10.2/src/base/ftgloadr.c +++ b/3rdparty/freetype-2.13.2/src/base/ftgloadr.c @@ -4,7 +4,7 @@ * * The FreeType glyph loader (body). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg * * This file is part of the FreeType project, and may only be used, @@ -16,11 +16,10 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_GLYPH_LOADER_H -#include FT_INTERNAL_MEMORY_H -#include FT_INTERNAL_OBJECTS_H +#include +#include +#include +#include #undef FT_COMPONENT #define FT_COMPONENT gloader @@ -93,6 +92,7 @@ base->outline.n_points = 0; base->outline.n_contours = 0; + base->outline.flags = 0; base->num_subglyphs = 0; *current = *base; @@ -212,12 +212,12 @@ FT_Outline* current = &loader->current.outline; FT_Bool adjust = 0; - FT_UInt new_max, old_max; + FT_UInt new_max, old_max, min_new_max; error = FT_GlyphLoader_CreateExtra( loader ); if ( error ) - return error; + goto Exit; /* check points & tags */ new_max = (FT_UInt)base->n_points + (FT_UInt)current->n_points + @@ -226,10 +226,18 @@ if ( new_max > old_max ) { - new_max = FT_PAD_CEIL( new_max, 8 ); + if ( new_max > FT_OUTLINE_POINTS_MAX ) + { + error = FT_THROW( Array_Too_Large ); + goto Exit; + } + min_new_max = old_max + ( old_max >> 1 ); + if ( new_max < min_new_max ) + new_max = min_new_max; + new_max = FT_PAD_CEIL( new_max, 8 ); if ( new_max > FT_OUTLINE_POINTS_MAX ) - return FT_THROW( Array_Too_Large ); + new_max = FT_OUTLINE_POINTS_MAX; if ( FT_RENEW_ARRAY( base->points, old_max, new_max ) || FT_RENEW_ARRAY( base->tags, old_max, new_max ) ) @@ -254,7 +262,7 @@ error = FT_GlyphLoader_CreateExtra( loader ); if ( error ) - return error; + goto Exit; /* check contours */ old_max = loader->max_contours; @@ -262,10 +270,18 @@ n_contours; if ( new_max > old_max ) { - new_max = FT_PAD_CEIL( new_max, 4 ); + if ( new_max > FT_OUTLINE_CONTOURS_MAX ) + { + error = FT_THROW( Array_Too_Large ); + goto Exit; + } + min_new_max = old_max + ( old_max >> 1 ); + if ( new_max < min_new_max ) + new_max = min_new_max; + new_max = FT_PAD_CEIL( new_max, 4 ); if ( new_max > FT_OUTLINE_CONTOURS_MAX ) - return FT_THROW( Array_Too_Large ); + new_max = FT_OUTLINE_CONTOURS_MAX; if ( FT_RENEW_ARRAY( base->contours, old_max, new_max ) ) goto Exit; diff --git a/src/font/freetype-2.10.2/src/base/ftglyph.c b/3rdparty/freetype-2.13.2/src/base/ftglyph.c similarity index 69% rename from src/font/freetype-2.10.2/src/base/ftglyph.c rename to 3rdparty/freetype-2.13.2/src/base/ftglyph.c index 44654be78..393d4949f 100644 --- a/src/font/freetype-2.10.2/src/base/ftglyph.c +++ b/3rdparty/freetype-2.13.2/src/base/ftglyph.c @@ -4,7 +4,7 @@ * * FreeType convenience functions to handle glyphs (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -28,13 +28,15 @@ */ -#include -#include FT_INTERNAL_DEBUG_H +#include -#include FT_GLYPH_H -#include FT_OUTLINE_H -#include FT_BITMAP_H -#include FT_INTERNAL_OBJECTS_H +#include +#include +#include +#include +#include + +#include "ftbase.h" /************************************************************************** @@ -276,6 +278,240 @@ ) +#ifdef FT_CONFIG_OPTION_SVG + + /*************************************************************************/ + /*************************************************************************/ + /**** ****/ + /**** FT_SvgGlyph support ****/ + /**** ****/ + /*************************************************************************/ + /*************************************************************************/ + + + FT_CALLBACK_DEF( FT_Error ) + ft_svg_glyph_init( FT_Glyph svg_glyph, + FT_GlyphSlot slot ) + { + FT_ULong doc_length; + FT_SVG_Document document; + FT_SvgGlyph glyph = (FT_SvgGlyph)svg_glyph; + + FT_Error error = FT_Err_Ok; + FT_Memory memory = FT_GLYPH( glyph )->library->memory; + + + if ( slot->format != FT_GLYPH_FORMAT_SVG ) + { + error = FT_THROW( Invalid_Glyph_Format ); + goto Exit; + } + + if ( slot->other == NULL ) + { + error = FT_THROW( Invalid_Slot_Handle ); + goto Exit; + } + + document = (FT_SVG_Document)slot->other; + + if ( document->svg_document_length == 0 ) + { + error = FT_THROW( Invalid_Slot_Handle ); + goto Exit; + } + + /* allocate a new document */ + doc_length = document->svg_document_length; + if ( FT_QALLOC( glyph->svg_document, doc_length ) ) + goto Exit; + glyph->svg_document_length = doc_length; + + glyph->glyph_index = slot->glyph_index; + + glyph->metrics = document->metrics; + glyph->units_per_EM = document->units_per_EM; + + glyph->start_glyph_id = document->start_glyph_id; + glyph->end_glyph_id = document->end_glyph_id; + + glyph->transform = document->transform; + glyph->delta = document->delta; + + /* copy the document into glyph */ + FT_MEM_COPY( glyph->svg_document, document->svg_document, doc_length ); + + Exit: + return error; + } + + + FT_CALLBACK_DEF( void ) + ft_svg_glyph_done( FT_Glyph svg_glyph ) + { + FT_SvgGlyph glyph = (FT_SvgGlyph)svg_glyph; + FT_Memory memory = svg_glyph->library->memory; + + + /* just free the memory */ + FT_FREE( glyph->svg_document ); + } + + + FT_CALLBACK_DEF( FT_Error ) + ft_svg_glyph_copy( FT_Glyph svg_source, + FT_Glyph svg_target ) + { + FT_SvgGlyph source = (FT_SvgGlyph)svg_source; + FT_SvgGlyph target = (FT_SvgGlyph)svg_target; + + FT_Error error = FT_Err_Ok; + FT_Memory memory = FT_GLYPH( source )->library->memory; + + + if ( svg_source->format != FT_GLYPH_FORMAT_SVG ) + { + error = FT_THROW( Invalid_Glyph_Format ); + goto Exit; + } + + if ( source->svg_document_length == 0 ) + { + error = FT_THROW( Invalid_Slot_Handle ); + goto Exit; + } + + target->glyph_index = source->glyph_index; + + target->svg_document_length = source->svg_document_length; + + target->metrics = source->metrics; + target->units_per_EM = source->units_per_EM; + + target->start_glyph_id = source->start_glyph_id; + target->end_glyph_id = source->end_glyph_id; + + target->transform = source->transform; + target->delta = source->delta; + + /* allocate space for the SVG document */ + if ( FT_QALLOC( target->svg_document, target->svg_document_length ) ) + goto Exit; + + /* copy the document */ + FT_MEM_COPY( target->svg_document, + source->svg_document, + target->svg_document_length ); + + Exit: + return error; + } + + + FT_CALLBACK_DEF( void ) + ft_svg_glyph_transform( FT_Glyph svg_glyph, + const FT_Matrix* _matrix, + const FT_Vector* _delta ) + { + FT_SvgGlyph glyph = (FT_SvgGlyph)svg_glyph; + FT_Matrix* matrix = (FT_Matrix*)_matrix; + FT_Vector* delta = (FT_Vector*)_delta; + + FT_Matrix tmp_matrix; + FT_Vector tmp_delta; + + FT_Matrix a, b; + FT_Pos x, y; + + + if ( !matrix ) + { + tmp_matrix.xx = 0x10000; + tmp_matrix.xy = 0; + tmp_matrix.yx = 0; + tmp_matrix.yy = 0x10000; + + matrix = &tmp_matrix; + } + + if ( !delta ) + { + tmp_delta.x = 0; + tmp_delta.y = 0; + + delta = &tmp_delta; + } + + a = glyph->transform; + b = *matrix; + FT_Matrix_Multiply( &b, &a ); + + x = ADD_LONG( ADD_LONG( FT_MulFix( matrix->xx, glyph->delta.x ), + FT_MulFix( matrix->xy, glyph->delta.y ) ), + delta->x ); + y = ADD_LONG( ADD_LONG( FT_MulFix( matrix->yx, glyph->delta.x ), + FT_MulFix( matrix->yy, glyph->delta.y ) ), + delta->y ); + + glyph->delta.x = x; + glyph->delta.y = y; + + glyph->transform = a; + } + + + FT_CALLBACK_DEF( FT_Error ) + ft_svg_glyph_prepare( FT_Glyph svg_glyph, + FT_GlyphSlot slot ) + { + FT_SvgGlyph glyph = (FT_SvgGlyph)svg_glyph; + + FT_Error error = FT_Err_Ok; + FT_Memory memory = svg_glyph->library->memory; + + FT_SVG_Document document = NULL; + + + if ( FT_NEW( document ) ) + return error; + + document->svg_document = glyph->svg_document; + document->svg_document_length = glyph->svg_document_length; + + document->metrics = glyph->metrics; + document->units_per_EM = glyph->units_per_EM; + + document->start_glyph_id = glyph->start_glyph_id; + document->end_glyph_id = glyph->end_glyph_id; + + document->transform = glyph->transform; + document->delta = glyph->delta; + + slot->format = FT_GLYPH_FORMAT_SVG; + slot->glyph_index = glyph->glyph_index; + slot->other = document; + + return error; + } + + + FT_DEFINE_GLYPH( + ft_svg_glyph_class, + + sizeof ( FT_SvgGlyphRec ), + FT_GLYPH_FORMAT_SVG, + + ft_svg_glyph_init, /* FT_Glyph_InitFunc glyph_init */ + ft_svg_glyph_done, /* FT_Glyph_DoneFunc glyph_done */ + ft_svg_glyph_copy, /* FT_Glyph_CopyFunc glyph_copy */ + ft_svg_glyph_transform, /* FT_Glyph_TransformFunc glyph_transform */ + NULL, /* FT_Glyph_GetBBoxFunc glyph_bbox */ + ft_svg_glyph_prepare /* FT_Glyph_PrepareFunc glyph_prepare */ + ) + +#endif /* FT_CONFIG_OPTION_SVG */ + + /*************************************************************************/ /*************************************************************************/ /**** ****/ @@ -376,6 +612,12 @@ else if ( format == FT_GLYPH_FORMAT_OUTLINE ) clazz = &ft_outline_glyph_class; +#ifdef FT_CONFIG_OPTION_SVG + /* if it is an SVG glyph */ + else if ( format == FT_GLYPH_FORMAT_SVG ) + clazz = &ft_svg_glyph_class; +#endif + else { /* try to find a renderer that supports the glyph image format */ @@ -440,7 +682,10 @@ Exit2: /* if an error occurred, destroy the glyph */ if ( error ) + { FT_Done_Glyph( glyph ); + *aglyph = NULL; + } else *aglyph = glyph; @@ -452,9 +697,9 @@ /* documentation is in ftglyph.h */ FT_EXPORT_DEF( FT_Error ) - FT_Glyph_Transform( FT_Glyph glyph, - FT_Matrix* matrix, - FT_Vector* delta ) + FT_Glyph_Transform( FT_Glyph glyph, + const FT_Matrix* matrix, + const FT_Vector* delta ) { FT_Error error = FT_Err_Ok; @@ -532,10 +777,10 @@ /* documentation is in ftglyph.h */ FT_EXPORT_DEF( FT_Error ) - FT_Glyph_To_Bitmap( FT_Glyph* the_glyph, - FT_Render_Mode render_mode, - FT_Vector* origin, - FT_Bool destroy ) + FT_Glyph_To_Bitmap( FT_Glyph* the_glyph, + FT_Render_Mode render_mode, + const FT_Vector* origin, + FT_Bool destroy ) { FT_GlyphSlotRec dummy; FT_GlyphSlot_InternalRec dummy_internal; @@ -584,7 +829,7 @@ #if 1 /* if `origin' is set, translate the glyph image */ if ( origin ) - FT_Glyph_Transform( glyph, 0, origin ); + FT_Glyph_Transform( glyph, NULL, origin ); #else FT_UNUSED( origin ); #endif @@ -594,6 +839,16 @@ if ( !error ) error = FT_Render_Glyph_Internal( glyph->library, &dummy, render_mode ); +#ifdef FT_CONFIG_OPTION_SVG + if ( clazz == &ft_svg_glyph_class ) + { + FT_Memory memory = library->memory; + + + FT_FREE( dummy.other ); + } +#endif + #if 1 if ( !destroy && origin ) { @@ -602,7 +857,7 @@ v.x = -origin->x; v.y = -origin->y; - FT_Glyph_Transform( glyph, 0, &v ); + FT_Glyph_Transform( glyph, NULL, &v ); } #endif diff --git a/src/font/freetype-2.10.2/src/base/ftgxval.c b/3rdparty/freetype-2.13.2/src/base/ftgxval.c similarity index 95% rename from src/font/freetype-2.10.2/src/base/ftgxval.c rename to 3rdparty/freetype-2.13.2/src/base/ftgxval.c index fa32c5f6c..6b3c5d248 100644 --- a/src/font/freetype-2.10.2/src/base/ftgxval.c +++ b/3rdparty/freetype-2.13.2/src/base/ftgxval.c @@ -4,7 +4,7 @@ * * FreeType API for validating TrueTypeGX/AAT tables (body). * - * Copyright (C) 2004-2020 by + * Copyright (C) 2004-2023 by * Masatake YAMATO, Redhat K.K, * David Turner, Robert Wilhelm, and Werner Lemberg. * @@ -25,11 +25,10 @@ */ -#include -#include FT_INTERNAL_DEBUG_H +#include -#include FT_INTERNAL_OBJECTS_H -#include FT_SERVICE_GX_VALIDATE_H +#include +#include /* documentation is in ftgxval.h */ diff --git a/src/font/freetype-2.10.2/src/base/fthash.c b/3rdparty/freetype-2.13.2/src/base/fthash.c similarity index 98% rename from src/font/freetype-2.10.2/src/base/fthash.c rename to 3rdparty/freetype-2.13.2/src/base/fthash.c index 387e6d26d..313bbbb4b 100644 --- a/src/font/freetype-2.10.2/src/base/fthash.c +++ b/3rdparty/freetype-2.13.2/src/base/fthash.c @@ -39,9 +39,8 @@ */ -#include -#include FT_INTERNAL_HASH_H -#include FT_INTERNAL_MEMORY_H +#include +#include #define INITIAL_HT_SIZE 241 @@ -244,7 +243,7 @@ nn = *bp; if ( !nn ) { - if ( FT_NEW( nn ) ) + if ( FT_QNEW( nn ) ) goto Exit; *bp = nn; diff --git a/src/font/freetype-2.10.2/src/base/ftinit.c b/3rdparty/freetype-2.13.2/src/base/ftinit.c similarity index 96% rename from src/font/freetype-2.10.2/src/base/ftinit.c rename to 3rdparty/freetype-2.13.2/src/base/ftinit.c index 1aab09a77..c9c71d24b 100644 --- a/src/font/freetype-2.10.2/src/base/ftinit.c +++ b/3rdparty/freetype-2.13.2/src/base/ftinit.c @@ -4,7 +4,7 @@ * * FreeType initialization layer (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -39,9 +39,9 @@ #include #include FT_CONFIG_CONFIG_H -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_DEBUG_H -#include FT_MODULE_H +#include +#include +#include /************************************************************************** @@ -202,6 +202,10 @@ FT_Memory memory; +#ifdef FT_DEBUG_LOGGING + ft_logging_init(); +#endif + /* check of `alibrary' delayed to `FT_New_Library' */ /* First of all, allocate a new system object -- this function is part */ @@ -248,6 +252,10 @@ /* discard memory manager */ FT_Done_Memory( memory ); +#ifdef FT_DEBUG_LOGGING + ft_logging_deinit(); +#endif + return FT_Err_Ok; } diff --git a/src/font/freetype-2.10.2/src/base/ftlcdfil.c b/3rdparty/freetype-2.13.2/src/base/ftlcdfil.c similarity index 97% rename from src/font/freetype-2.10.2/src/base/ftlcdfil.c rename to 3rdparty/freetype-2.13.2/src/base/ftlcdfil.c index d4ef93a51..6c3fd66e0 100644 --- a/src/font/freetype-2.10.2/src/base/ftlcdfil.c +++ b/3rdparty/freetype-2.13.2/src/base/ftlcdfil.c @@ -4,7 +4,7 @@ * * FreeType API for color filtering of subpixel bitmap glyphs (body). * - * Copyright (C) 2006-2020 by + * Copyright (C) 2006-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,12 +16,11 @@ */ -#include -#include FT_INTERNAL_DEBUG_H +#include -#include FT_LCD_FILTER_H -#include FT_IMAGE_H -#include FT_INTERNAL_OBJECTS_H +#include +#include +#include #ifdef FT_CONFIG_OPTION_SUBPIXEL_RENDERING @@ -33,7 +32,7 @@ /* add padding according to filter weights */ - FT_BASE_DEF (void) + FT_BASE_DEF( void ) ft_lcd_padding( FT_BBox* cbox, FT_GlyphSlot slot, FT_Render_Mode mode ) @@ -358,7 +357,7 @@ FT_EXPORT_DEF( FT_Error ) FT_Library_SetLcdGeometry( FT_Library library, - FT_Vector* sub ) + FT_Vector sub[3] ) { FT_UNUSED( library ); FT_UNUSED( sub ); @@ -369,7 +368,7 @@ #else /* !FT_CONFIG_OPTION_SUBPIXEL_RENDERING */ /* add padding to accommodate outline shifts */ - FT_BASE_DEF (void) + FT_BASE_DEF( void ) ft_lcd_padding( FT_BBox* cbox, FT_GlyphSlot slot, FT_Render_Mode mode ) @@ -429,7 +428,7 @@ ft_memcpy( library->lcd_geometry, sub, 3 * sizeof( FT_Vector ) ); - return FT_THROW( Unimplemented_Feature ); + return FT_Err_Ok; } #endif /* !FT_CONFIG_OPTION_SUBPIXEL_RENDERING */ diff --git a/src/font/freetype-2.10.2/src/base/ftmac.c b/3rdparty/freetype-2.13.2/src/base/ftmac.c similarity index 98% rename from src/font/freetype-2.10.2/src/base/ftmac.c rename to 3rdparty/freetype-2.13.2/src/base/ftmac.c index 2de43a014..492d05538 100644 --- a/src/font/freetype-2.10.2/src/base/ftmac.c +++ b/3rdparty/freetype-2.13.2/src/base/ftmac.c @@ -8,7 +8,7 @@ * This file is for Mac OS X only; see builds/mac/ftoldmac.c for * classic platforms built by MPW. * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * Just van Rossum, David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -65,10 +65,10 @@ */ -#include -#include FT_FREETYPE_H -#include FT_TRUETYPE_TAGS_H -#include FT_INTERNAL_STREAM_H +#include +#include +#include +#include #include "ftbase.h" @@ -106,7 +106,7 @@ /* Don't want warnings about our own use of deprecated functions. */ #define FT_DEPRECATED_ATTRIBUTE -#include FT_MAC_H +#include #ifndef kATSOptionFlagsUnRestrictedScope /* since Mac OS X 10.1 */ #define kATSOptionFlagsUnRestrictedScope kATSOptionFlagsDefault @@ -315,7 +315,7 @@ NULL, NULL, NULL ) ) return ( OSType ) 0; - return ((FInfo *)(info.finderInfo))->fdType; + return ( (FInfo *)( info.finderInfo ) )->fdType; } @@ -463,7 +463,7 @@ if ( ps_name_len != 0 ) { - ft_memcpy(ps_name, names[0] + 1, ps_name_len); + ft_memcpy( ps_name, names[0] + 1, ps_name_len ); ps_name[ps_name_len] = 0; } if ( style->indexes[face_index] > 1 && @@ -561,7 +561,7 @@ if ( lwfn_file_name[0] ) { err = lookup_lwfn_by_fond( pathname, lwfn_file_name, - buff, sizeof ( buff ) ); + buff, sizeof ( buff ) ); if ( !err ) have_lwfn = 1; } @@ -632,7 +632,7 @@ old_total_size = total_size; } - if ( FT_ALLOC( buffer, (FT_Long)total_size ) ) + if ( FT_QALLOC( buffer, (FT_Long)total_size ) ) goto Error; /* Second pass: append all POST data to the buffer, add PFB fields. */ @@ -753,7 +753,7 @@ if ( FT_MAC_RFORK_MAX_LEN < sfnt_size ) return FT_THROW( Array_Too_Large ); - if ( FT_ALLOC( sfnt_data, (FT_Long)sfnt_size ) ) + if ( FT_QALLOC( sfnt_data, (FT_Long)sfnt_size ) ) { ReleaseResource( sfnt ); return error; @@ -1082,7 +1082,7 @@ #else /* !FT_MACINTOSH */ /* ANSI C doesn't like empty source files */ - typedef int _ft_mac_dummy; + typedef int ft_mac_dummy_; #endif /* !FT_MACINTOSH */ diff --git a/src/font/freetype-2.10.2/src/base/ftmm.c b/3rdparty/freetype-2.13.2/src/base/ftmm.c similarity index 75% rename from src/font/freetype-2.10.2/src/base/ftmm.c rename to 3rdparty/freetype-2.13.2/src/base/ftmm.c index ef2e3d958..9e2dd7ee7 100644 --- a/src/font/freetype-2.10.2/src/base/ftmm.c +++ b/3rdparty/freetype-2.13.2/src/base/ftmm.c @@ -4,7 +4,7 @@ * * Multiple Master font support (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,13 +16,12 @@ */ -#include -#include FT_INTERNAL_DEBUG_H +#include -#include FT_MULTIPLE_MASTERS_H -#include FT_INTERNAL_OBJECTS_H -#include FT_SERVICE_MULTIPLE_MASTERS_H -#include FT_SERVICE_METRICS_VARIATIONS_H +#include +#include +#include +#include /************************************************************************** @@ -186,6 +185,14 @@ error = FT_ERR( Invalid_Argument ); if ( service->set_mm_design ) error = service->set_mm_design( face, num_coords, coords ); + + if ( !error ) + { + if ( num_coords ) + face->face_flags |= FT_FACE_FLAG_VARIATION; + else + face->face_flags &= ~FT_FACE_FLAG_VARIATION; + } } /* enforce recomputation of auto-hinting data */ @@ -221,6 +228,14 @@ error = FT_ERR( Invalid_Argument ); if ( service->set_mm_weightvector ) error = service->set_mm_weightvector( face, len, weightvector ); + + if ( !error ) + { + if ( len ) + face->face_flags |= FT_FACE_FLAG_VARIATION; + else + face->face_flags &= ~FT_FACE_FLAG_VARIATION; + } } /* enforce recomputation of auto-hinting data */ @@ -284,6 +299,30 @@ if ( service_mm->set_var_design ) error = service_mm->set_var_design( face, num_coords, coords ); + if ( !error || error == -1 ) + { + FT_Bool is_variation_old = FT_IS_VARIATION( face ); + + + if ( num_coords ) + face->face_flags |= FT_FACE_FLAG_VARIATION; + else + face->face_flags &= ~FT_FACE_FLAG_VARIATION; + + if ( service_mm->construct_ps_name ) + { + if ( error == -1 ) + { + /* The PS name of a named instance and a non-named instance */ + /* usually differs, even if the axis values are identical. */ + if ( is_variation_old != FT_IS_VARIATION( face ) ) + service_mm->construct_ps_name( face ); + } + else + service_mm->construct_ps_name( face ); + } + } + /* internal error code -1 means `no change'; we can exit immediately */ if ( error == -1 ) return FT_Err_Ok; @@ -360,6 +399,30 @@ if ( service_mm->set_mm_blend ) error = service_mm->set_mm_blend( face, num_coords, coords ); + if ( !error || error == -1 ) + { + FT_Bool is_variation_old = FT_IS_VARIATION( face ); + + + if ( num_coords ) + face->face_flags |= FT_FACE_FLAG_VARIATION; + else + face->face_flags &= ~FT_FACE_FLAG_VARIATION; + + if ( service_mm->construct_ps_name ) + { + if ( error == -1 ) + { + /* The PS name of a named instance and a non-named instance */ + /* usually differs, even if the axis values are identical. */ + if ( is_variation_old != FT_IS_VARIATION( face ) ) + service_mm->construct_ps_name( face ); + } + else + service_mm->construct_ps_name( face ); + } + } + /* internal error code -1 means `no change'; we can exit immediately */ if ( error == -1 ) return FT_Err_Ok; @@ -411,6 +474,30 @@ if ( service_mm->set_mm_blend ) error = service_mm->set_mm_blend( face, num_coords, coords ); + if ( !error || error == -1 ) + { + FT_Bool is_variation_old = FT_IS_VARIATION( face ); + + + if ( num_coords ) + face->face_flags |= FT_FACE_FLAG_VARIATION; + else + face->face_flags &= ~FT_FACE_FLAG_VARIATION; + + if ( service_mm->construct_ps_name ) + { + if ( error == -1 ) + { + /* The PS name of a named instance and a non-named instance */ + /* usually differs, even if the axis values are identical. */ + if ( is_variation_old != FT_IS_VARIATION( face ) ) + service_mm->construct_ps_name( face ); + } + else + service_mm->construct_ps_name( face ); + } + } + /* internal error code -1 means `no change'; we can exit immediately */ if ( error == -1 ) return FT_Err_Ok; @@ -536,8 +623,35 @@ if ( !error ) { error = FT_ERR( Invalid_Argument ); - if ( service_mm->set_instance ) - error = service_mm->set_instance( face, instance_index ); + if ( service_mm->set_named_instance ) + error = service_mm->set_named_instance( face, instance_index ); + + if ( !error || error == -1 ) + { + FT_Bool is_variation_old = FT_IS_VARIATION( face ); + + + face->face_flags &= ~FT_FACE_FLAG_VARIATION; + face->face_index = ( instance_index << 16 ) | + ( face->face_index & 0xFFFFL ); + + if ( service_mm->construct_ps_name ) + { + if ( error == -1 ) + { + /* The PS name of a named instance and a non-named instance */ + /* usually differs, even if the axis values are identical. */ + if ( is_variation_old != FT_IS_VARIATION( face ) ) + service_mm->construct_ps_name( face ); + } + else + service_mm->construct_ps_name( face ); + } + } + + /* internal error code -1 means `no change'; we can exit immediately */ + if ( error == -1 ) + return FT_Err_Ok; } if ( !error ) @@ -555,11 +669,32 @@ face->autohint.data = NULL; } + return error; + } + + + /* documentation is in ftmm.h */ + + FT_EXPORT_DEF( FT_Error ) + FT_Get_Default_Named_Instance( FT_Face face, + FT_UInt *instance_index ) + { + FT_Error error; + + FT_Service_MultiMasters service_mm = NULL; + + + /* check of `face' delayed to `ft_face_get_mm_service' */ + + error = ft_face_get_mm_service( face, &service_mm ); if ( !error ) { - face->face_index = ( instance_index << 16 ) | - ( face->face_index & 0xFFFFL ); - face->face_flags &= ~FT_FACE_FLAG_VARIATION; + /* no error if `get_default_named_instance` is not available */ + if ( service_mm->get_default_named_instance ) + error = service_mm->get_default_named_instance( face, + instance_index ); + else + error = FT_Err_Ok; } return error; diff --git a/src/font/freetype-2.10.2/src/base/ftobjs.c b/3rdparty/freetype-2.13.2/src/base/ftobjs.c similarity index 88% rename from src/font/freetype-2.10.2/src/base/ftobjs.c rename to 3rdparty/freetype-2.13.2/src/base/ftobjs.c index 1b042614d..89a25bc73 100644 --- a/src/font/freetype-2.10.2/src/base/ftobjs.c +++ b/3rdparty/freetype-2.13.2/src/base/ftobjs.c @@ -4,7 +4,7 @@ * * The FreeType private base classes (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,32 +16,33 @@ */ -#include -#include FT_LIST_H -#include FT_OUTLINE_H -#include FT_FONT_FORMATS_H +#include +#include +#include +#include -#include FT_INTERNAL_VALIDATE_H -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_RFORK_H -#include FT_INTERNAL_STREAM_H -#include FT_INTERNAL_SFNT_H /* for SFNT_Load_Table_Func */ -#include FT_INTERNAL_POSTSCRIPT_AUX_H /* for PS_Driver */ +#include +#include +#include +#include +#include +#include /* for SFNT_Load_Table_Func */ +#include /* for PS_Driver */ +#include -#include FT_TRUETYPE_TABLES_H -#include FT_TRUETYPE_TAGS_H -#include FT_TRUETYPE_IDS_H +#include +#include +#include -#include FT_SERVICE_PROPERTIES_H -#include FT_SERVICE_SFNT_H -#include FT_SERVICE_POSTSCRIPT_NAME_H -#include FT_SERVICE_GLYPH_DICT_H -#include FT_SERVICE_TT_CMAP_H -#include FT_SERVICE_KERNING_H -#include FT_SERVICE_TRUETYPE_ENGINE_H +#include +#include +#include +#include +#include +#include +#include -#include FT_DRIVER_H +#include #ifdef FT_CONFIG_OPTION_MAC_FONTS #include "ftbase.h" @@ -50,7 +51,7 @@ #ifdef FT_DEBUG_LEVEL_TRACE -#include FT_BITMAP_H +#include #if defined( _MSC_VER ) /* Visual C++ (and Intel C++) */ /* We disable the warning `conversion from XXX to YYY, */ @@ -79,6 +80,9 @@ #pragma warning( pop ) #endif + /* This array must stay in sync with the @FT_Pixel_Mode enumeration */ + /* (in file `ftimage.h`). */ + static const char* const pixel_modes[] = { "none", @@ -88,7 +92,8 @@ "gray 4-bit bitmap", "LCD 8-bit bitmap", "vertical LCD 8-bit bitmap", - "BGRA 32-bit color image bitmap" + "BGRA 32-bit color image bitmap", + "SDF 8-bit bitmap" }; #endif /* FT_DEBUG_LEVEL_TRACE */ @@ -194,6 +199,7 @@ FT_Error error; FT_Memory memory; FT_Stream stream = NULL; + FT_UInt mode; *astream = NULL; @@ -205,49 +211,56 @@ return FT_THROW( Invalid_Argument ); memory = library->memory; + mode = args->flags & + ( FT_OPEN_MEMORY | FT_OPEN_STREAM | FT_OPEN_PATHNAME ); - if ( FT_NEW( stream ) ) - goto Exit; - - stream->memory = memory; - - if ( args->flags & FT_OPEN_MEMORY ) + if ( mode == FT_OPEN_MEMORY ) { /* create a memory-based stream */ + if ( FT_NEW( stream ) ) + goto Exit; + FT_Stream_OpenMemory( stream, (const FT_Byte*)args->memory_base, (FT_ULong)args->memory_size ); + stream->memory = memory; } #ifndef FT_CONFIG_OPTION_DISABLE_STREAM_SUPPORT - else if ( args->flags & FT_OPEN_PATHNAME ) + else if ( mode == FT_OPEN_PATHNAME ) { /* create a normal system stream */ + if ( FT_NEW( stream ) ) + goto Exit; + + stream->memory = memory; error = FT_Stream_Open( stream, args->pathname ); - stream->pathname.pointer = args->pathname; + if ( error ) + FT_FREE( stream ); } - else if ( ( args->flags & FT_OPEN_STREAM ) && args->stream ) + else if ( ( mode == FT_OPEN_STREAM ) && args->stream ) { /* use an existing, user-provided stream */ /* in this case, we do not need to allocate a new stream object */ /* since the caller is responsible for closing it himself */ - FT_FREE( stream ); - stream = args->stream; + stream = args->stream; + stream->memory = memory; + error = FT_Err_Ok; } #endif else + { error = FT_THROW( Invalid_Argument ); + if ( ( args->flags & FT_OPEN_STREAM ) && args->stream ) + FT_Stream_Close( args->stream ); + } - if ( error ) - FT_FREE( stream ); - else - stream->memory = memory; /* just to be certain */ - - *astream = stream; + if ( !error ) + *astream = stream; Exit: return error; @@ -317,6 +330,19 @@ if ( !error && clazz->init_slot ) error = clazz->init_slot( slot ); +#ifdef FT_CONFIG_OPTION_SVG + /* if SVG table exists, allocate the space in `slot->other` */ + if ( slot->face->face_flags & FT_FACE_FLAG_SVG ) + { + FT_SVG_Document document = NULL; + + + if ( FT_NEW( document ) ) + goto Exit; + slot->other = document; + } +#endif + Exit: return error; } @@ -361,7 +387,18 @@ FT_Pos width, height, pitch; - if ( slot->format != FT_GLYPH_FORMAT_OUTLINE ) + if ( slot->format == FT_GLYPH_FORMAT_SVG ) + { + FT_Module module; + SVG_Service svg_service; + + + module = FT_Get_Module( slot->library, "ot-svg" ); + svg_service = (SVG_Service)module->clazz->module_interface; + + return (FT_Bool)svg_service->preset_slot( module, slot, FALSE ); + } + else if ( slot->format != FT_GLYPH_FORMAT_OUTLINE ) return 1; if ( origin ) @@ -471,7 +508,7 @@ case FT_PIXEL_MODE_LCD_V: height *= 3; - /* fall through */ + FALL_THROUGH; case FT_PIXEL_MODE_GRAY: default: @@ -524,7 +561,7 @@ else slot->internal->flags |= FT_GLYPH_OWN_BITMAP; - (void)FT_ALLOC( slot->bitmap.buffer, size ); + FT_MEM_ALLOC( slot->bitmap.buffer, size ); return error; } @@ -536,6 +573,8 @@ ft_glyphslot_free_bitmap( slot ); /* clear all public fields in the glyph slot */ + slot->glyph_index = 0; + FT_ZERO( &slot->metrics ); FT_ZERO( &slot->outline ); @@ -551,11 +590,32 @@ slot->subglyphs = NULL; slot->control_data = NULL; slot->control_len = 0; - slot->other = NULL; - slot->format = FT_GLYPH_FORMAT_NONE; + +#ifndef FT_CONFIG_OPTION_SVG + slot->other = NULL; +#else + if ( !( slot->face->face_flags & FT_FACE_FLAG_SVG ) ) + slot->other = NULL; + else + { + if ( slot->internal->flags & FT_GLYPH_OWN_GZIP_SVG ) + { + FT_Memory memory = slot->face->memory; + FT_SVG_Document doc = (FT_SVG_Document)slot->other; + + + FT_FREE( doc->svg_document ); + slot->internal->flags &= ~FT_GLYPH_OWN_GZIP_SVG; + } + } +#endif + + slot->format = FT_GLYPH_FORMAT_NONE; slot->linearHoriAdvance = 0; slot->linearVertAdvance = 0; + slot->advance.x = 0; + slot->advance.y = 0; slot->lsb_delta = 0; slot->rsb_delta = 0; } @@ -568,6 +628,24 @@ FT_Driver_Class clazz = driver->clazz; FT_Memory memory = driver->root.memory; +#ifdef FT_CONFIG_OPTION_SVG + if ( slot->face->face_flags & FT_FACE_FLAG_SVG ) + { + /* Free memory in case SVG was there. */ + /* `slot->internal` might be NULL in out-of-memory situations. */ + if ( slot->internal && slot->internal->flags & FT_GLYPH_OWN_GZIP_SVG ) + { + FT_SVG_Document doc = (FT_SVG_Document)slot->other; + + + FT_FREE( doc->svg_document ); + + slot->internal->flags &= ~FT_GLYPH_OWN_GZIP_SVG; + } + + FT_FREE( slot->other ); + } +#endif if ( clazz->done_slot ) clazz->done_slot( slot ); @@ -735,6 +813,29 @@ } + /* documentation is in freetype.h */ + + FT_EXPORT_DEF( void ) + FT_Get_Transform( FT_Face face, + FT_Matrix* matrix, + FT_Vector* delta ) + { + FT_Face_Internal internal; + + + if ( !face ) + return; + + internal = face->internal; + + if ( matrix ) + *matrix = internal->transform_matrix; + + if ( delta ) + *delta = internal->transform_delta; + } + + static FT_Renderer ft_lookup_glyph_renderer( FT_GlyphSlot slot ); @@ -820,6 +921,11 @@ library = driver->root.library; hinter = library->auto_hinter; + /* undefined scale means no scale */ + if ( face->size->metrics.x_ppem == 0 || + face->size->metrics.y_ppem == 0 ) + load_flags |= FT_LOAD_NO_SCALE; + /* resolve load flags dependencies */ if ( load_flags & FT_LOAD_NO_RECURSE ) @@ -909,11 +1015,22 @@ FT_AutoHinter_Interface hinting; - /* try to load embedded bitmaps first if available */ - /* */ - /* XXX: This is really a temporary hack that should disappear */ - /* promptly with FreeType 2.1! */ - /* */ + /* XXX: The use of the `FT_LOAD_XXX_ONLY` flags is not very */ + /* elegant. */ + + /* try to load SVG documents if available */ + if ( ( load_flags & FT_LOAD_NO_SVG ) == 0 && + FT_HAS_SVG( face ) ) + { + error = driver->clazz->load_glyph( slot, face->size, + glyph_index, + load_flags | FT_LOAD_SVG_ONLY ); + + if ( !error && slot->format == FT_GLYPH_FORMAT_SVG ) + goto Load_Ok; + } + + /* try to load embedded bitmaps if available */ if ( FT_HAS_FIXED_SIZES( face ) && ( load_flags & FT_LOAD_NO_BITMAP ) == 0 ) { @@ -1057,17 +1174,47 @@ #ifdef FT_DEBUG_LEVEL_TRACE FT_TRACE5(( "FT_Load_Glyph: index %d, flags 0x%x\n", glyph_index, load_flags )); - FT_TRACE5(( " x advance: %f\n", slot->advance.x / 64.0 )); - FT_TRACE5(( " y advance: %f\n", slot->advance.y / 64.0 )); - FT_TRACE5(( " linear x advance: %f\n", - slot->linearHoriAdvance / 65536.0 )); - FT_TRACE5(( " linear y advance: %f\n", - slot->linearVertAdvance / 65536.0 )); - FT_TRACE5(( " bitmap %dx%d, %s (mode %d)\n", + FT_TRACE5(( " bitmap %dx%d %s, %s (mode %d)\n", slot->bitmap.width, slot->bitmap.rows, + slot->outline.points ? + slot->bitmap.buffer ? "rendered" + : "preset" + : + slot->internal->flags & FT_GLYPH_OWN_BITMAP ? "owned" + : "unowned", pixel_modes[slot->bitmap.pixel_mode], slot->bitmap.pixel_mode )); + FT_TRACE5(( "\n" )); + FT_TRACE5(( " x advance: %f\n", (double)slot->advance.x / 64 )); + FT_TRACE5(( " y advance: %f\n", (double)slot->advance.y / 64 )); + FT_TRACE5(( " linear x advance: %f\n", + (double)slot->linearHoriAdvance / 65536 )); + FT_TRACE5(( " linear y advance: %f\n", + (double)slot->linearVertAdvance / 65536 )); + + { + FT_Glyph_Metrics* metrics = &slot->metrics; + + + FT_TRACE5(( " metrics:\n" )); + FT_TRACE5(( " width: %f\n", (double)metrics->width / 64 )); + FT_TRACE5(( " height: %f\n", (double)metrics->height / 64 )); + FT_TRACE5(( "\n" )); + FT_TRACE5(( " horiBearingX: %f\n", + (double)metrics->horiBearingX / 64 )); + FT_TRACE5(( " horiBearingY: %f\n", + (double)metrics->horiBearingY / 64 )); + FT_TRACE5(( " horiAdvance: %f\n", + (double)metrics->horiAdvance / 64 )); + FT_TRACE5(( "\n" )); + FT_TRACE5(( " vertBearingX: %f\n", + (double)metrics->vertBearingX / 64 )); + FT_TRACE5(( " vertBearingY: %f\n", + (double)metrics->vertBearingY / 64 )); + FT_TRACE5(( " vertAdvance: %f\n", + (double)metrics->vertAdvance / 64 )); + } #endif Exit: @@ -1099,9 +1246,13 @@ /* destructor for sizes list */ static void destroy_size( FT_Memory memory, - FT_Size size, - FT_Driver driver ) + void* size_, + void* driver_ ) { + FT_Size size = (FT_Size)size_; + FT_Driver driver = (FT_Driver)driver_; + + /* finalize client-specific data */ if ( size->generic.finalizer ) size->generic.finalizer( size ); @@ -1147,10 +1298,12 @@ /* destructor for faces list */ static void destroy_face( FT_Memory memory, - FT_Face face, - FT_Driver driver ) + void* face_, + void* driver_ ) { - FT_Driver_Class clazz = driver->clazz; + FT_Face face = (FT_Face)face_; + FT_Driver driver = (FT_Driver)driver_; + FT_Driver_Class clazz = driver->clazz; /* discard auto-hinting data */ @@ -1164,7 +1317,7 @@ /* discard all sizes for this face */ FT_List_Finalize( &face->sizes_list, - (FT_List_Destructor)destroy_size, + destroy_size, memory, driver ); face->size = NULL; @@ -1200,7 +1353,7 @@ Destroy_Driver( FT_Driver driver ) { FT_List_Finalize( &driver->faces_list, - (FT_List_Destructor)destroy_face, + destroy_face, driver->root.memory, driver ); } @@ -1349,7 +1502,7 @@ static FT_Error open_face( FT_Driver driver, FT_Stream *astream, - FT_Bool external_stream, + FT_Bool *anexternal_stream, FT_Long face_index, FT_Int num_params, FT_Parameter* params, @@ -1375,7 +1528,7 @@ face->stream = *astream; /* set the FT_FACE_FLAG_EXTERNAL_STREAM bit for FT_Done_Face */ - if ( external_stream ) + if ( *anexternal_stream ) face->face_flags |= FT_FACE_FLAG_EXTERNAL_STREAM; if ( FT_NEW( internal ) ) @@ -1405,7 +1558,10 @@ (FT_Int)face_index, num_params, params ); - *astream = face->stream; /* Stream may have been changed. */ + /* Stream may have been changed. */ + *astream = face->stream; + *anexternal_stream = + ( face->face_flags & FT_FACE_FLAG_EXTERNAL_STREAM ) != 0; if ( error ) goto Fail; @@ -1529,14 +1685,13 @@ static void memory_stream_close( FT_Stream stream ) { - FT_Memory memory = stream->memory; + FT_Memory memory = (FT_Memory)stream->descriptor.pointer; FT_FREE( stream->base ); - stream->size = 0; - stream->base = NULL; stream->close = NULL; + FT_FREE( stream ); } @@ -1567,7 +1722,8 @@ FT_Stream_OpenMemory( stream, base, size ); - stream->close = close; + stream->descriptor.pointer = memory; + stream->close = close; *astream = stream; @@ -1588,28 +1744,37 @@ { FT_Open_Args args; FT_Error error; - FT_Stream stream = NULL; FT_Memory memory = library->memory; + args.driver = NULL; + args.flags = 0; + + if ( driver_name ) + { + args.driver = FT_Get_Module( library, driver_name ); + if ( !args.driver ) + { + FT_FREE( base ); + return FT_THROW( Missing_Module ); + } + + args.flags = args.flags | FT_OPEN_DRIVER; + } + + /* `memory_stream_close` also frees the stream object. */ error = new_memory_stream( library, base, size, memory_stream_close, - &stream ); + &args.stream ); if ( error ) { FT_FREE( base ); return error; } - args.flags = FT_OPEN_STREAM; - args.stream = stream; - if ( driver_name ) - { - args.flags = args.flags | FT_OPEN_DRIVER; - args.driver = FT_Get_Module( library, driver_name ); - } + args.flags |= FT_OPEN_STREAM; #ifdef FT_MACINTOSH /* At this point, the face index has served its purpose; */ @@ -1621,21 +1786,7 @@ face_index &= 0x7FFF0000L; /* retain GX data */ #endif - error = ft_open_face_internal( library, &args, face_index, aface, 0 ); - - if ( !error ) - (*aface)->face_flags &= ~FT_FACE_FLAG_EXTERNAL_STREAM; - else -#ifdef FT_MACINTOSH - FT_Stream_Free( stream, 0 ); -#else - { - FT_Stream_Close( stream ); - FT_FREE( stream ); - } -#endif - - return error; + return ft_open_face_internal( library, &args, face_index, aface, 0 ); } @@ -1764,7 +1915,7 @@ if ( error ) goto Exit; - if ( FT_ALLOC( sfnt_ps, (FT_Long)length ) ) + if ( FT_QALLOC( sfnt_ps, (FT_Long)length ) ) goto Exit; error = FT_Stream_Read( stream, (FT_Byte *)sfnt_ps, length ); @@ -1778,7 +1929,7 @@ sfnt_ps, length, FT_MIN( face_index, 0 ), - is_sfnt_cid ? "cid" : "type1", + is_sfnt_cid ? "t1cid" : "type1", aface ); Exit: { @@ -1842,15 +1993,15 @@ /* FT2 allocator takes signed long buffer length, * too large value causing overflow should be checked */ - FT_TRACE4(( " POST fragment #%d: length=0x%08x" - " total pfb_len=0x%08x\n", + FT_TRACE4(( " POST fragment #%d: length=0x%08lx" + " total pfb_len=0x%08lx\n", i, temp, pfb_len + temp + 6 )); if ( FT_MAC_RFORK_MAX_LEN < temp || FT_MAC_RFORK_MAX_LEN - temp < pfb_len + 6 ) { FT_TRACE2(( " MacOS resource length cannot exceed" - " 0x%08x\n", + " 0x%08lx\n", FT_MAC_RFORK_MAX_LEN )); error = FT_THROW( Invalid_Offset ); @@ -1861,20 +2012,20 @@ } FT_TRACE2(( " total buffer size to concatenate" - " %d POST fragments: 0x%08x\n", + " %ld POST fragments: 0x%08lx\n", resource_cnt, pfb_len + 2 )); if ( pfb_len + 2 < 6 ) { FT_TRACE2(( " too long fragment length makes" - " pfb_len confused: pfb_len=0x%08x\n", + " pfb_len confused: pfb_len=0x%08lx\n", pfb_len )); error = FT_THROW( Array_Too_Large ); goto Exit; } - if ( FT_ALLOC( pfb_data, (FT_Long)pfb_len + 2 ) ) + if ( FT_QALLOC( pfb_data, (FT_Long)pfb_len + 2 ) ) goto Exit; pfb_data[0] = 0x80; @@ -1910,7 +2061,7 @@ goto Exit2; FT_TRACE3(( "POST fragment[%d]:" - " offsets=0x%08x, rlen=0x%08x, flags=0x%04x\n", + " offsets=0x%08lx, rlen=0x%08lx, flags=0x%04x\n", i, offsets[i], rlen, flags )); error = FT_ERR( Array_Too_Large ); @@ -1937,8 +2088,8 @@ else { FT_TRACE3(( " Write POST fragment #%d header (4-byte) to buffer" - " %p + 0x%08x\n", - i, pfb_data, pfb_lenpos )); + " %p + 0x%08lx\n", + i, (void*)pfb_data, pfb_lenpos )); if ( pfb_lenpos + 3 > pfb_len + 2 ) goto Exit2; @@ -1952,8 +2103,8 @@ break; FT_TRACE3(( " Write POST fragment #%d header (6-byte) to buffer" - " %p + 0x%08x\n", - i, pfb_data, pfb_pos )); + " %p + 0x%08lx\n", + i, (void*)pfb_data, pfb_pos )); if ( pfb_pos + 6 > pfb_len + 2 ) goto Exit2; @@ -1974,9 +2125,9 @@ if ( pfb_pos > pfb_len || pfb_pos + rlen > pfb_len ) goto Exit2; - FT_TRACE3(( " Load POST fragment #%d (%d byte) to buffer" - " %p + 0x%08x\n", - i, rlen, pfb_data, pfb_pos )); + FT_TRACE3(( " Load POST fragment #%d (%ld byte) to buffer" + " %p + 0x%08lx\n", + i, rlen, (void*)pfb_data, pfb_pos )); error = FT_Stream_Read( stream, (FT_Byte *)pfb_data + pfb_pos, rlen ); if ( error ) @@ -2039,7 +2190,7 @@ FT_Byte* sfnt_data = NULL; FT_Error error; FT_ULong flag_offset; - FT_Long rlen; + FT_ULong rlen; int is_cff; FT_Long face_index_in_resource = 0; @@ -2054,11 +2205,11 @@ if ( error ) goto Exit; - if ( FT_READ_LONG( rlen ) ) + if ( FT_READ_ULONG( rlen ) ) goto Exit; - if ( rlen < 1 ) + if ( !rlen ) return FT_THROW( Cannot_Open_Resource ); - if ( (FT_ULong)rlen > FT_MAC_RFORK_MAX_LEN ) + if ( rlen > FT_MAC_RFORK_MAX_LEN ) return FT_THROW( Invalid_Offset ); error = open_face_PS_from_sfnt_stream( library, @@ -2074,10 +2225,11 @@ if ( error ) goto Exit; - if ( FT_ALLOC( sfnt_data, rlen ) ) + if ( FT_QALLOC( sfnt_data, rlen ) ) return error; - error = FT_Stream_Read( stream, (FT_Byte *)sfnt_data, (FT_ULong)rlen ); - if ( error ) { + error = FT_Stream_Read( stream, (FT_Byte *)sfnt_data, rlen ); + if ( error ) + { FT_FREE( sfnt_data ); goto Exit; } @@ -2085,7 +2237,7 @@ is_cff = rlen > 4 && !ft_memcmp( sfnt_data, "OTTO", 4 ); error = open_face_from_buffer( library, sfnt_data, - (FT_ULong)rlen, + rlen, face_index_in_resource, is_cff ? "cff" : "truetype", aface ); @@ -2260,7 +2412,7 @@ args2.flags = FT_OPEN_PATHNAME; args2.pathname = file_names[i] ? file_names[i] : args->pathname; - FT_TRACE3(( "Try rule %d: %s (offset=%d) ...", + FT_TRACE3(( "Try rule %d: %s (offset=%ld) ...", i, args2.pathname, offsets[i] )); error = FT_Stream_New( library, &args2, &stream2 ); @@ -2389,6 +2541,16 @@ #endif + /* only use lower 31 bits together with sign bit */ + if ( face_index > 0 ) + face_index &= 0x7FFFFFFFL; + else + { + face_index = -face_index; + face_index &= 0x7FFFFFFFL; + face_index = -face_index; + } + #ifdef FT_DEBUG_LEVEL_TRACE FT_TRACE3(( "FT_Open_Face: " )); if ( face_index < 0 ) @@ -2404,7 +2566,7 @@ /* test for valid `library' delayed to `FT_Stream_New' */ - if ( ( !aface && face_index >= 0 ) || !args ) + if ( !args ) return FT_THROW( Invalid_Argument ); external_stream = FT_BOOL( ( args->flags & FT_OPEN_STREAM ) && @@ -2415,6 +2577,14 @@ if ( error ) goto Fail3; + /* Do this error check after `FT_Stream_New` to ensure that the */ + /* 'close' callback is called. */ + if ( !aface && face_index >= 0 ) + { + error = FT_THROW( Invalid_Argument ); + goto Fail3; + } + memory = library->memory; /* If the font driver is specified in the `args' structure, use */ @@ -2436,7 +2606,7 @@ params = args->params; } - error = open_face( driver, &stream, external_stream, face_index, + error = open_face( driver, &stream, &external_stream, face_index, num_params, params, &face ); if ( !error ) goto Success; @@ -2472,7 +2642,7 @@ params = args->params; } - error = open_face( driver, &stream, external_stream, face_index, + error = open_face( driver, &stream, &external_stream, face_index, num_params, params, &face ); if ( !error ) goto Success; @@ -2548,7 +2718,7 @@ FT_TRACE4(( "FT_Open_Face: New face object, adding to list\n" )); /* add the face object to its driver's list */ - if ( FT_NEW( node ) ) + if ( FT_QNEW( node ) ) goto Fail; node->data = face; @@ -2663,10 +2833,10 @@ #ifdef FT_DEBUG_LEVEL_TRACE if ( !error && face_index < 0 ) { - FT_TRACE3(( "FT_Open_Face: The font has %ld face%s\n" - " and %ld named instance%s for face %ld\n", + FT_TRACE3(( "FT_Open_Face: The font has %ld face%s\n", face->num_faces, - face->num_faces == 1 ? "" : "s", + face->num_faces == 1 ? "" : "s" )); + FT_TRACE3(( " and %ld named instance%s for face %ld\n", face->style_flags >> 16, ( face->style_flags >> 16 ) == 1 ? "" : "s", -face_index - 1 )); @@ -2704,8 +2874,8 @@ /* documentation is in freetype.h */ FT_EXPORT_DEF( FT_Error ) - FT_Attach_Stream( FT_Face face, - FT_Open_Args* parameters ) + FT_Attach_Stream( FT_Face face, + const FT_Open_Args* parameters ) { FT_Stream stream; FT_Error error; @@ -2833,7 +3003,7 @@ memory = face->memory; /* Allocate new size object and perform basic initialisation */ - if ( FT_ALLOC( size, clazz->size_object_size ) || FT_NEW( node ) ) + if ( FT_ALLOC( size, clazz->size_object_size ) || FT_QNEW( node ) ) goto Exit; size->face = face; @@ -2858,6 +3028,8 @@ if ( error ) { FT_FREE( node ); + if ( size ) + FT_FREE( size->internal ); FT_FREE( size ); } @@ -3068,10 +3240,12 @@ } - FT_BASE_DEF( void ) + FT_BASE_DEF( FT_Error ) FT_Request_Metrics( FT_Face face, FT_Size_Request req ) { + FT_Error error = FT_Err_Ok; + FT_Size_Metrics* metrics; @@ -3126,34 +3300,49 @@ scaled_h = FT_REQUEST_HEIGHT( req ); /* determine scales */ - if ( req->width ) + if ( req->height || !req->width ) { - metrics->x_scale = FT_DivFix( scaled_w, w ); - - if ( req->height ) + if ( h == 0 ) { - metrics->y_scale = FT_DivFix( scaled_h, h ); - - if ( req->type == FT_SIZE_REQUEST_TYPE_CELL ) - { - if ( metrics->y_scale > metrics->x_scale ) - metrics->y_scale = metrics->x_scale; - else - metrics->x_scale = metrics->y_scale; - } + FT_ERROR(( "FT_Request_Metrics: Divide by zero\n" )); + error = FT_ERR( Divide_By_Zero ); + goto Exit; } - else + + metrics->y_scale = FT_DivFix( scaled_h, h ); + } + + if ( req->width ) + { + if ( w == 0 ) { - metrics->y_scale = metrics->x_scale; - scaled_h = FT_MulDiv( scaled_w, h, w ); + FT_ERROR(( "FT_Request_Metrics: Divide by zero\n" )); + error = FT_ERR( Divide_By_Zero ); + goto Exit; } + + metrics->x_scale = FT_DivFix( scaled_w, w ); } else { - metrics->x_scale = metrics->y_scale = FT_DivFix( scaled_h, h ); + metrics->x_scale = metrics->y_scale; scaled_w = FT_MulDiv( scaled_h, w, h ); } + if ( !req->height ) + { + metrics->y_scale = metrics->x_scale; + scaled_h = FT_MulDiv( scaled_w, h, w ); + } + + if ( req->type == FT_SIZE_REQUEST_TYPE_CELL ) + { + if ( metrics->y_scale > metrics->x_scale ) + metrics->y_scale = metrics->x_scale; + else + metrics->x_scale = metrics->y_scale; + } + Calculate_Ppem: /* calculate the ppems */ if ( req->type != FT_SIZE_REQUEST_TYPE_NOMINAL ) @@ -3162,8 +3351,18 @@ scaled_h = FT_MulFix( face->units_per_EM, metrics->y_scale ); } - metrics->x_ppem = (FT_UShort)( ( scaled_w + 32 ) >> 6 ); - metrics->y_ppem = (FT_UShort)( ( scaled_h + 32 ) >> 6 ); + scaled_w = ( scaled_w + 32 ) >> 6; + scaled_h = ( scaled_h + 32 ) >> 6; + if ( scaled_w > (FT_Long)FT_USHORT_MAX || + scaled_h > (FT_Long)FT_USHORT_MAX ) + { + FT_ERROR(( "FT_Request_Metrics: Resulting ppem size too large\n" )); + error = FT_ERR( Invalid_Pixel_Size ); + goto Exit; + } + + metrics->x_ppem = (FT_UShort)scaled_w; + metrics->y_ppem = (FT_UShort)scaled_h; ft_recompute_scaled_metrics( face, metrics ); } @@ -3173,6 +3372,9 @@ metrics->x_scale = 1L << 16; metrics->y_scale = 1L << 16; } + + Exit: + return error; } @@ -3213,16 +3415,20 @@ FT_Size_Metrics* metrics = &face->size->metrics; - FT_TRACE5(( " x scale: %d (%f)\n", - metrics->x_scale, metrics->x_scale / 65536.0 )); - FT_TRACE5(( " y scale: %d (%f)\n", - metrics->y_scale, metrics->y_scale / 65536.0 )); - FT_TRACE5(( " ascender: %f\n", metrics->ascender / 64.0 )); - FT_TRACE5(( " descender: %f\n", metrics->descender / 64.0 )); - FT_TRACE5(( " height: %f\n", metrics->height / 64.0 )); - FT_TRACE5(( " max advance: %f\n", metrics->max_advance / 64.0 )); - FT_TRACE5(( " x ppem: %d\n", metrics->x_ppem )); - FT_TRACE5(( " y ppem: %d\n", metrics->y_ppem )); + FT_TRACE5(( " x scale: %ld (%f)\n", + metrics->x_scale, (double)metrics->x_scale / 65536 )); + FT_TRACE5(( " y scale: %ld (%f)\n", + metrics->y_scale, (double)metrics->y_scale / 65536 )); + FT_TRACE5(( " ascender: %f\n", + (double)metrics->ascender / 64 )); + FT_TRACE5(( " descender: %f\n", + (double)metrics->descender / 64 )); + FT_TRACE5(( " height: %f\n", + (double)metrics->height / 64 )); + FT_TRACE5(( " max advance: %f\n", + (double)metrics->max_advance / 64 )); + FT_TRACE5(( " x ppem: %d\n", metrics->x_ppem )); + FT_TRACE5(( " y ppem: %d\n", metrics->y_ppem )); } #endif @@ -3236,7 +3442,7 @@ FT_Request_Size( FT_Face face, FT_Size_Request req ) { - FT_Error error = FT_Err_Ok; + FT_Error error; FT_Driver_Class clazz; FT_ULong strike_index; @@ -3244,6 +3450,9 @@ if ( !face ) return FT_THROW( Invalid_Face_Handle ); + if ( !face->size ) + return FT_THROW( Invalid_Size_Handle ); + if ( !req || req->width < 0 || req->height < 0 || req->type >= FT_SIZE_REQUEST_TYPE_MAX ) return FT_THROW( Invalid_Argument ); @@ -3272,13 +3481,15 @@ */ error = FT_Match_Size( face, req, 0, &strike_index ); if ( error ) - return error; + goto Exit; return FT_Select_Size( face, (FT_Int)strike_index ); } else { - FT_Request_Metrics( face, req ); + error = FT_Request_Metrics( face, req ); + if ( error ) + goto Exit; FT_TRACE5(( "FT_Request_Size:\n" )); } @@ -3288,19 +3499,24 @@ FT_Size_Metrics* metrics = &face->size->metrics; - FT_TRACE5(( " x scale: %d (%f)\n", - metrics->x_scale, metrics->x_scale / 65536.0 )); - FT_TRACE5(( " y scale: %d (%f)\n", - metrics->y_scale, metrics->y_scale / 65536.0 )); - FT_TRACE5(( " ascender: %f\n", metrics->ascender / 64.0 )); - FT_TRACE5(( " descender: %f\n", metrics->descender / 64.0 )); - FT_TRACE5(( " height: %f\n", metrics->height / 64.0 )); - FT_TRACE5(( " max advance: %f\n", metrics->max_advance / 64.0 )); - FT_TRACE5(( " x ppem: %d\n", metrics->x_ppem )); - FT_TRACE5(( " y ppem: %d\n", metrics->y_ppem )); + FT_TRACE5(( " x scale: %ld (%f)\n", + metrics->x_scale, (double)metrics->x_scale / 65536 )); + FT_TRACE5(( " y scale: %ld (%f)\n", + metrics->y_scale, (double)metrics->y_scale / 65536 )); + FT_TRACE5(( " ascender: %f\n", + (double)metrics->ascender / 64 )); + FT_TRACE5(( " descender: %f\n", + (double)metrics->descender / 64 )); + FT_TRACE5(( " height: %f\n", + (double)metrics->height / 64 )); + FT_TRACE5(( " max advance: %f\n", + (double)metrics->max_advance / 64 )); + FT_TRACE5(( " x ppem: %d\n", metrics->x_ppem )); + FT_TRACE5(( " y ppem: %d\n", metrics->y_ppem )); } #endif + Exit: return error; } @@ -3450,7 +3666,7 @@ if ( akerning->x != orig_x_rounded || akerning->y != orig_y_rounded ) FT_TRACE5(( "FT_Get_Kerning: horizontal kerning" - " (%d, %d) scaled down to (%d, %d) pixels\n", + " (%ld, %ld) scaled down to (%ld, %ld) pixels\n", orig_x_rounded / 64, orig_y_rounded / 64, akerning->x / 64, akerning->y / 64 )); } @@ -3625,9 +3841,9 @@ FT_CharMap last_charmap = face->charmaps[face->num_charmaps - 1]; - if ( FT_RENEW_ARRAY( face->charmaps, - face->num_charmaps, - face->num_charmaps - 1 ) ) + if ( FT_QRENEW_ARRAY( face->charmaps, + face->num_charmaps, + face->num_charmaps - 1 ) ) return; /* remove it from our list of charmaps */ @@ -3659,7 +3875,7 @@ FT_CharMap charmap, FT_CMap *acmap ) { - FT_Error error = FT_Err_Ok; + FT_Error error; FT_Face face; FT_Memory memory; FT_CMap cmap = NULL; @@ -3684,9 +3900,9 @@ } /* add it to our list of charmaps */ - if ( FT_RENEW_ARRAY( face->charmaps, - face->num_charmaps, - face->num_charmaps + 1 ) ) + if ( FT_QRENEW_ARRAY( face->charmaps, + face->num_charmaps, + face->num_charmaps + 1 ) ) goto Fail; face->charmaps[face->num_charmaps++] = (FT_CharMap)cmap; @@ -3722,7 +3938,7 @@ if ( charcode > 0xFFFFFFFFUL ) { FT_TRACE1(( "FT_Get_Char_Index: too large charcode" )); - FT_TRACE1(( " 0x%x is truncated\n", charcode )); + FT_TRACE1(( " 0x%lx is truncated\n", charcode )); } result = cmap->clazz->char_index( cmap, (FT_UInt32)charcode ); @@ -3898,13 +4114,13 @@ { FT_TRACE1(( "FT_Face_GetCharVariantIndex:" " too large charcode" )); - FT_TRACE1(( " 0x%x is truncated\n", charcode )); + FT_TRACE1(( " 0x%lx is truncated\n", charcode )); } if ( variantSelector > 0xFFFFFFFFUL ) { FT_TRACE1(( "FT_Face_GetCharVariantIndex:" " too large variantSelector" )); - FT_TRACE1(( " 0x%x is truncated\n", variantSelector )); + FT_TRACE1(( " 0x%lx is truncated\n", variantSelector )); } result = vcmap->clazz->char_var_index( vcmap, ucmap, @@ -3941,13 +4157,13 @@ { FT_TRACE1(( "FT_Face_GetCharVariantIsDefault:" " too large charcode" )); - FT_TRACE1(( " 0x%x is truncated\n", charcode )); + FT_TRACE1(( " 0x%lx is truncated\n", charcode )); } if ( variantSelector > 0xFFFFFFFFUL ) { FT_TRACE1(( "FT_Face_GetCharVariantIsDefault:" " too large variantSelector" )); - FT_TRACE1(( " 0x%x is truncated\n", variantSelector )); + FT_TRACE1(( " 0x%lx is truncated\n", variantSelector )); } result = vcmap->clazz->char_var_default( vcmap, @@ -4010,7 +4226,7 @@ if ( charcode > 0xFFFFFFFFUL ) { FT_TRACE1(( "FT_Face_GetVariantsOfChar: too large charcode" )); - FT_TRACE1(( " 0x%x is truncated\n", charcode )); + FT_TRACE1(( " 0x%lx is truncated\n", charcode )); } result = vcmap->clazz->charvariant_list( vcmap, memory, @@ -4044,7 +4260,7 @@ if ( variantSelector > 0xFFFFFFFFUL ) { FT_TRACE1(( "FT_Get_Char_Index: too large variantSelector" )); - FT_TRACE1(( " 0x%x is truncated\n", variantSelector )); + FT_TRACE1(( " 0x%lx is truncated\n", variantSelector )); } result = vcmap->clazz->variantchar_list( vcmap, memory, @@ -4380,7 +4596,7 @@ FT_ListNode node = NULL; - if ( FT_NEW( node ) ) + if ( FT_QNEW( node ) ) goto Exit; { @@ -4392,8 +4608,7 @@ render->glyph_format = clazz->glyph_format; /* allocate raster object if needed */ - if ( clazz->glyph_format == FT_GLYPH_FORMAT_OUTLINE && - clazz->raster_class->raster_new ) + if ( clazz->raster_class && clazz->raster_class->raster_new ) { error = clazz->raster_class->raster_new( memory, &render->raster ); if ( error ) @@ -4403,6 +4618,11 @@ render->render = clazz->render_glyph; } +#ifdef FT_CONFIG_OPTION_SVG + if ( clazz->glyph_format == FT_GLYPH_FORMAT_SVG ) + render->render = clazz->render_glyph; +#endif + /* add to list */ node->data = module; FT_List_Add( &library->renderers, node ); @@ -4440,8 +4660,7 @@ /* release raster object, if any */ - if ( render->clazz->glyph_format == FT_GLYPH_FORMAT_OUTLINE && - render->raster ) + if ( render->raster ) render->clazz->raster_class->raster_done( render->raster ); /* remove from list */ @@ -4536,9 +4755,6 @@ switch ( slot->format ) { - case FT_GLYPH_FORMAT_BITMAP: /* already a bitmap, don't do anything */ - break; - default: if ( slot->internal->load_flags & FT_LOAD_COLOR ) { @@ -4626,7 +4842,7 @@ else renderer = FT_Lookup_Renderer( library, slot->format, &node ); - error = FT_ERR( Unimplemented_Feature ); + error = FT_ERR( Cannot_Render_Glyph ); while ( renderer ) { error = renderer->render( renderer, slot, render_mode, NULL ); @@ -4642,6 +4858,11 @@ /* format. */ renderer = FT_Lookup_Renderer( library, slot->format, &node ); } + + /* it is not an error if we cannot render a bitmap glyph */ + if ( FT_ERR_EQ( error, Cannot_Render_Glyph ) && + slot->format == FT_GLYPH_FORMAT_BITMAP ) + error = FT_Err_Ok; } } @@ -4714,11 +4935,11 @@ /* we use FT_TRACE7 in this block */ if ( !error && - ft_trace_levels[trace_checksum] >= 7 ) + ft_trace_levels[trace_checksum] >= 7 && + slot->bitmap.buffer ) { if ( slot->bitmap.rows < 128U && - slot->bitmap.width < 128U && - slot->bitmap.buffer ) + slot->bitmap.width < 128U ) { int rows = (int)slot->bitmap.rows; int width = (int)slot->bitmap.width; @@ -5129,16 +5350,16 @@ if ( cur == limit ) { - FT_ERROR(( "%s: can't find module `%s'\n", - func_name, module_name )); + FT_TRACE2(( "%s: can't find module `%s'\n", + func_name, module_name )); return FT_THROW( Missing_Module ); } /* check whether we have a service interface */ if ( !cur[0]->clazz->get_interface ) { - FT_ERROR(( "%s: module `%s' doesn't support properties\n", - func_name, module_name )); + FT_TRACE2(( "%s: module `%s' doesn't support properties\n", + func_name, module_name )); return FT_THROW( Unimplemented_Feature ); } @@ -5147,8 +5368,8 @@ FT_SERVICE_ID_PROPERTIES ); if ( !interface ) { - FT_ERROR(( "%s: module `%s' doesn't support properties\n", - func_name, module_name )); + FT_TRACE2(( "%s: module `%s' doesn't support properties\n", + func_name, module_name )); return FT_THROW( Unimplemented_Feature ); } @@ -5161,8 +5382,8 @@ if ( missing_func ) { - FT_ERROR(( "%s: property service of module `%s' is broken\n", - func_name, module_name )); + FT_TRACE2(( "%s: property service of module `%s' is broken\n", + func_name, module_name )); return FT_THROW( Unimplemented_Feature ); } @@ -5272,10 +5493,12 @@ if ( !memory || !alibrary ) return FT_THROW( Invalid_Argument ); +#ifndef FT_DEBUG_LOGGING #ifdef FT_DEBUG_LEVEL_ERROR /* init debugging support */ ft_debug_init(); -#endif +#endif /* FT_DEBUG_LEVEL_ERROR */ +#endif /* !FT_DEBUG_LOGGING */ /* first of all, allocate the library object */ if ( FT_NEW( library ) ) @@ -5547,4 +5770,145 @@ } + /* documentation is in freetype.h */ + + FT_EXPORT_DEF( FT_Bool ) + FT_Get_Color_Glyph_Paint( FT_Face face, + FT_UInt base_glyph, + FT_Color_Root_Transform root_transform, + FT_OpaquePaint* paint ) + { + TT_Face ttface; + SFNT_Service sfnt; + + + if ( !face || !paint ) + return 0; + + if ( !FT_IS_SFNT( face ) ) + return 0; + + ttface = (TT_Face)face; + sfnt = (SFNT_Service)ttface->sfnt; + + if ( sfnt->get_colr_layer ) + return sfnt->get_colr_glyph_paint( ttface, + base_glyph, + root_transform, + paint ); + else + return 0; + } + + + /* documentation is in ftcolor.h */ + + FT_EXPORT_DEF( FT_Bool ) + FT_Get_Color_Glyph_ClipBox( FT_Face face, + FT_UInt base_glyph, + FT_ClipBox* clip_box ) + { + TT_Face ttface; + SFNT_Service sfnt; + + + if ( !face || !clip_box ) + return 0; + + if ( !FT_IS_SFNT( face ) ) + return 0; + + ttface = (TT_Face)face; + sfnt = (SFNT_Service)ttface->sfnt; + + if ( sfnt->get_color_glyph_clipbox ) + return sfnt->get_color_glyph_clipbox( ttface, + base_glyph, + clip_box ); + else + return 0; + } + + + /* documentation is in freetype.h */ + + FT_EXPORT_DEF( FT_Bool ) + FT_Get_Paint_Layers( FT_Face face, + FT_LayerIterator* layer_iterator, + FT_OpaquePaint* paint ) + { + TT_Face ttface; + SFNT_Service sfnt; + + + if ( !face || !paint || !layer_iterator ) + return 0; + + if ( !FT_IS_SFNT( face ) ) + return 0; + + ttface = (TT_Face)face; + sfnt = (SFNT_Service)ttface->sfnt; + + if ( sfnt->get_paint_layers ) + return sfnt->get_paint_layers( ttface, layer_iterator, paint ); + else + return 0; + } + + + /* documentation is in freetype.h */ + + FT_EXPORT_DEF( FT_Bool ) + FT_Get_Paint( FT_Face face, + FT_OpaquePaint opaque_paint, + FT_COLR_Paint* paint ) + { + TT_Face ttface; + SFNT_Service sfnt; + + + if ( !face || !paint ) + return 0; + + if ( !FT_IS_SFNT( face ) ) + return 0; + + ttface = (TT_Face)face; + sfnt = (SFNT_Service)ttface->sfnt; + + if ( sfnt->get_paint ) + return sfnt->get_paint( ttface, opaque_paint, paint ); + else + return 0; + } + + + /* documentation is in freetype.h */ + + FT_EXPORT_DEF( FT_Bool ) + FT_Get_Colorline_Stops ( FT_Face face, + FT_ColorStop * color_stop, + FT_ColorStopIterator *iterator ) + { + TT_Face ttface; + SFNT_Service sfnt; + + + if ( !face || !color_stop || !iterator ) + return 0; + + if ( !FT_IS_SFNT( face ) ) + return 0; + + ttface = (TT_Face)face; + sfnt = (SFNT_Service)ttface->sfnt; + + if ( sfnt->get_colorline_stops ) + return sfnt->get_colorline_stops ( ttface, color_stop, iterator ); + else + return 0; + } + + /* END */ diff --git a/src/font/freetype-2.10.2/src/base/ftotval.c b/3rdparty/freetype-2.13.2/src/base/ftotval.c similarity index 91% rename from src/font/freetype-2.10.2/src/base/ftotval.c rename to 3rdparty/freetype-2.13.2/src/base/ftotval.c index 9f69e0c1f..192e12a71 100644 --- a/src/font/freetype-2.10.2/src/base/ftotval.c +++ b/3rdparty/freetype-2.13.2/src/base/ftotval.c @@ -4,7 +4,7 @@ * * FreeType API for validating OpenType tables (body). * - * Copyright (C) 2004-2020 by + * Copyright (C) 2004-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -15,12 +15,11 @@ * */ -#include -#include FT_INTERNAL_DEBUG_H +#include -#include FT_INTERNAL_OBJECTS_H -#include FT_SERVICE_OPENTYPE_VALIDATE_H -#include FT_OPENTYPE_VALIDATE_H +#include +#include +#include /* documentation is in ftotval.h */ diff --git a/src/font/freetype-2.10.2/src/base/ftoutln.c b/3rdparty/freetype-2.13.2/src/base/ftoutln.c similarity index 91% rename from src/font/freetype-2.10.2/src/base/ftoutln.c rename to 3rdparty/freetype-2.13.2/src/base/ftoutln.c index faaae8329..134f39d2b 100644 --- a/src/font/freetype-2.10.2/src/base/ftoutln.c +++ b/3rdparty/freetype-2.13.2/src/base/ftoutln.c @@ -4,7 +4,7 @@ * * FreeType outline management (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,12 +16,11 @@ */ -#include -#include FT_OUTLINE_H -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_CALC_H -#include FT_INTERNAL_DEBUG_H -#include FT_TRIGONOMETRY_H +#include +#include +#include +#include +#include /************************************************************************** @@ -59,7 +58,9 @@ FT_Error error; FT_Int n; /* index of contour in outline */ - FT_UInt first; /* index of first point in contour */ + FT_Int first; /* index of first point in contour */ + FT_Int last; /* index of last point in contour */ + FT_Int tag; /* current point's state */ FT_Int shift; @@ -74,18 +75,17 @@ shift = func_interface->shift; delta = func_interface->delta; - first = 0; + last = -1; for ( n = 0; n < outline->n_contours; n++ ) { - FT_Int last; /* index of last point in contour */ - - - FT_TRACE5(( "FT_Outline_Decompose: Outline %d\n", n )); + FT_TRACE5(( "FT_Outline_Decompose: Contour %d\n", n )); - last = outline->contours[n]; - if ( last < 0 ) + first = last + 1; + last = outline->contours[n]; + if ( last < first ) goto Invalid_Outline; + limit = outline->points + last; v_start = outline->points[first]; @@ -131,7 +131,7 @@ } FT_TRACE5(( " move to (%.2f, %.2f)\n", - v_start.x / 64.0, v_start.y / 64.0 )); + (double)v_start.x / 64, (double)v_start.y / 64 )); error = func_interface->move_to( &v_start, user ); if ( error ) goto Exit; @@ -153,7 +153,7 @@ vec.y = SCALED( point->y ); FT_TRACE5(( " line to (%.2f, %.2f)\n", - vec.x / 64.0, vec.y / 64.0 )); + (double)vec.x / 64, (double)vec.y / 64 )); error = func_interface->line_to( &vec, user ); if ( error ) goto Exit; @@ -182,8 +182,10 @@ { FT_TRACE5(( " conic to (%.2f, %.2f)" " with control (%.2f, %.2f)\n", - vec.x / 64.0, vec.y / 64.0, - v_control.x / 64.0, v_control.y / 64.0 )); + (double)vec.x / 64, + (double)vec.y / 64, + (double)v_control.x / 64, + (double)v_control.y / 64 )); error = func_interface->conic_to( &v_control, &vec, user ); if ( error ) goto Exit; @@ -198,8 +200,10 @@ FT_TRACE5(( " conic to (%.2f, %.2f)" " with control (%.2f, %.2f)\n", - v_middle.x / 64.0, v_middle.y / 64.0, - v_control.x / 64.0, v_control.y / 64.0 )); + (double)v_middle.x / 64, + (double)v_middle.y / 64, + (double)v_control.x / 64, + (double)v_control.y / 64 )); error = func_interface->conic_to( &v_control, &v_middle, user ); if ( error ) goto Exit; @@ -210,8 +214,10 @@ FT_TRACE5(( " conic to (%.2f, %.2f)" " with control (%.2f, %.2f)\n", - v_start.x / 64.0, v_start.y / 64.0, - v_control.x / 64.0, v_control.y / 64.0 )); + (double)v_start.x / 64, + (double)v_start.y / 64, + (double)v_control.x / 64, + (double)v_control.y / 64 )); error = func_interface->conic_to( &v_control, &v_start, user ); goto Close; @@ -243,9 +249,12 @@ FT_TRACE5(( " cubic to (%.2f, %.2f)" " with controls (%.2f, %.2f) and (%.2f, %.2f)\n", - vec.x / 64.0, vec.y / 64.0, - vec1.x / 64.0, vec1.y / 64.0, - vec2.x / 64.0, vec2.y / 64.0 )); + (double)vec.x / 64, + (double)vec.y / 64, + (double)vec1.x / 64, + (double)vec1.y / 64, + (double)vec2.x / 64, + (double)vec2.y / 64 )); error = func_interface->cubic_to( &vec1, &vec2, &vec, user ); if ( error ) goto Exit; @@ -254,9 +263,12 @@ FT_TRACE5(( " cubic to (%.2f, %.2f)" " with controls (%.2f, %.2f) and (%.2f, %.2f)\n", - v_start.x / 64.0, v_start.y / 64.0, - vec1.x / 64.0, vec1.y / 64.0, - vec2.x / 64.0, vec2.y / 64.0 )); + (double)v_start.x / 64, + (double)v_start.y / 64, + (double)vec1.x / 64, + (double)vec1.y / 64, + (double)vec2.x / 64, + (double)vec2.y / 64 )); error = func_interface->cubic_to( &vec1, &vec2, &v_start, user ); goto Close; } @@ -265,17 +277,15 @@ /* close the contour with a line segment */ FT_TRACE5(( " line to (%.2f, %.2f)\n", - v_start.x / 64.0, v_start.y / 64.0 )); + (double)v_start.x / 64, (double)v_start.y / 64 )); error = func_interface->line_to( &v_start, user ); Close: if ( error ) goto Exit; - - first = (FT_UInt)last + 1; } - FT_TRACE5(( "FT_Outline_Decompose: Done\n", n )); + FT_TRACE5(( "FT_Outline_Decompose: Done\n" )); return FT_Err_Ok; Invalid_Outline: @@ -357,7 +367,7 @@ if ( n_points <= 0 || n_contours <= 0 ) goto Bad; - end0 = end = -1; + end0 = -1; for ( n = 0; n < n_contours; n++ ) { end = outline->contours[n]; @@ -369,7 +379,7 @@ end0 = end; } - if ( end != n_points - 1 ) + if ( end0 != n_points - 1 ) goto Bad; /* XXX: check the tags array */ @@ -377,7 +387,7 @@ } Bad: - return FT_THROW( Invalid_Argument ); + return FT_THROW( Invalid_Outline ); } @@ -539,10 +549,12 @@ if ( !outline ) return; - first = 0; - + last = -1; for ( n = 0; n < outline->n_contours; n++ ) { + /* keep the first contour point as is and swap points around it */ + /* to guarantee that the cubic arches stay valid after reverse */ + first = last + 2; last = outline->contours[n]; /* reverse point table */ @@ -580,8 +592,6 @@ q--; } } - - first = last + 1; } outline->flags ^= FT_OUTLINE_REVERSE_FILL; @@ -930,7 +940,7 @@ points = outline->points; - first = 0; + last = -1; for ( c = 0; c < outline->n_contours; c++ ) { FT_Vector in, out, anchor, shift; @@ -938,8 +948,9 @@ FT_Int i, j, k; - l_in = 0; - last = outline->contours[c]; + first = last + 1; + last = outline->contours[c]; + l_in = 0; /* pacify compiler */ in.x = in.y = anchor.x = anchor.y = 0; @@ -1026,8 +1037,6 @@ in = out; l_in = l_out; } - - first = last + 1; } return FT_Err_Ok; @@ -1043,7 +1052,7 @@ FT_Int xshift, yshift; FT_Vector* points; FT_Vector v_prev, v_cur; - FT_Int c, n, first; + FT_Int c, n, first, last; FT_Pos area = 0; @@ -1061,6 +1070,11 @@ if ( cbox.xMin == cbox.xMax || cbox.yMin == cbox.yMax ) return FT_ORIENTATION_NONE; + /* Reject values large outlines. */ + if ( cbox.xMin < -0x1000000L || cbox.yMin < -0x1000000L || + cbox.xMax > 0x1000000L || cbox.yMax > 0x1000000L ) + return FT_ORIENTATION_NONE; + xshift = FT_MSB( (FT_UInt32)( FT_ABS( cbox.xMax ) | FT_ABS( cbox.xMin ) ) ) - 14; xshift = FT_MAX( xshift, 0 ); @@ -1070,11 +1084,11 @@ points = outline->points; - first = 0; + last = -1; for ( c = 0; c < outline->n_contours; c++ ) { - FT_Int last = outline->contours[c]; - + first = last + 1; + last = outline->contours[c]; v_prev.x = points[last].x >> xshift; v_prev.y = points[last].y >> yshift; @@ -1090,8 +1104,6 @@ v_prev = v_cur; } - - first = last + 1; } if ( area > 0 ) diff --git a/src/font/freetype-2.10.2/src/base/ftpatent.c b/3rdparty/freetype-2.13.2/src/base/ftpatent.c similarity index 78% rename from src/font/freetype-2.10.2/src/base/ftpatent.c rename to 3rdparty/freetype-2.13.2/src/base/ftpatent.c index 077a9b03f..cb5efadff 100644 --- a/src/font/freetype-2.10.2/src/base/ftpatent.c +++ b/3rdparty/freetype-2.13.2/src/base/ftpatent.c @@ -5,7 +5,7 @@ * FreeType API for checking patented TrueType bytecode instructions * (body). Obsolete, retained for backward compatibility. * - * Copyright (C) 2007-2020 by + * Copyright (C) 2007-2023 by * David Turner. * * This file is part of the FreeType project, and may only be used, @@ -16,13 +16,12 @@ * */ -#include -#include FT_FREETYPE_H -#include FT_TRUETYPE_TAGS_H -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_STREAM_H -#include FT_SERVICE_SFNT_H -#include FT_SERVICE_TRUETYPE_GLYF_H +#include +#include +#include +#include +#include +#include /* documentation is in freetype.h */ diff --git a/src/font/freetype-2.10.2/src/base/ftpfr.c b/3rdparty/freetype-2.13.2/src/base/ftpfr.c similarity index 95% rename from src/font/freetype-2.10.2/src/base/ftpfr.c rename to 3rdparty/freetype-2.13.2/src/base/ftpfr.c index 57e65665f..378385a59 100644 --- a/src/font/freetype-2.10.2/src/base/ftpfr.c +++ b/3rdparty/freetype-2.13.2/src/base/ftpfr.c @@ -4,7 +4,7 @@ * * FreeType API for accessing PFR-specific data (body). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -15,11 +15,10 @@ * */ -#include -#include FT_INTERNAL_DEBUG_H +#include -#include FT_INTERNAL_OBJECTS_H -#include FT_SERVICE_PFR_H +#include +#include /* check the format */ diff --git a/src/font/freetype-2.10.2/src/base/ftpsprop.c b/3rdparty/freetype-2.13.2/src/base/ftpsprop.c similarity index 95% rename from src/font/freetype-2.10.2/src/base/ftpsprop.c rename to 3rdparty/freetype-2.13.2/src/base/ftpsprop.c index c63f864c1..cefdf489d 100644 --- a/src/font/freetype-2.10.2/src/base/ftpsprop.c +++ b/3rdparty/freetype-2.13.2/src/base/ftpsprop.c @@ -5,7 +5,7 @@ * Get and set properties of PostScript drivers (body). * See `ftdriver.h' for available properties. * - * Copyright (C) 2017-2020 by + * Copyright (C) 2017-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -17,12 +17,11 @@ */ -#include -#include FT_DRIVER_H -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_POSTSCRIPT_AUX_H -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_POSTSCRIPT_PROPS_H +#include +#include +#include +#include +#include /************************************************************************** @@ -221,7 +220,7 @@ return error; } - FT_TRACE0(( "ps_property_set: missing property `%s'\n", + FT_TRACE2(( "ps_property_set: missing property `%s'\n", property_name )); return FT_THROW( Missing_Property ); } @@ -276,7 +275,7 @@ return error; } - FT_TRACE0(( "ps_property_get: missing property `%s'\n", + FT_TRACE2(( "ps_property_get: missing property `%s'\n", property_name )); return FT_THROW( Missing_Property ); } diff --git a/src/font/freetype-2.10.2/src/base/ftrfork.c b/3rdparty/freetype-2.13.2/src/base/ftrfork.c similarity index 94% rename from src/font/freetype-2.10.2/src/base/ftrfork.c rename to 3rdparty/freetype-2.13.2/src/base/ftrfork.c index 1bf7800f1..2ab430195 100644 --- a/src/font/freetype-2.10.2/src/base/ftrfork.c +++ b/3rdparty/freetype-2.13.2/src/base/ftrfork.c @@ -4,7 +4,7 @@ * * Embedded resource forks accessor (body). * - * Copyright (C) 2004-2020 by + * Copyright (C) 2004-2023 by * Masatake YAMATO and Redhat K.K. * * FT_Raccess_Get_HeaderInfo() and raccess_guess_darwin_hfsplus() are @@ -24,10 +24,9 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_STREAM_H -#include FT_INTERNAL_RFORK_H +#include +#include +#include #include "ftbase.h" @@ -168,16 +167,11 @@ } - static int - ft_raccess_sort_ref_by_id( FT_RFork_Ref* a, - FT_RFork_Ref* b ) + FT_COMPARE_DEF( int ) + ft_raccess_sort_ref_by_id( const void* a, + const void* b ) { - if ( a->res_id < b->res_id ) - return -1; - else if ( a->res_id > b->res_id ) - return 1; - else - return 0; + return ( (FT_RFork_Ref*)a )->res_id - ( (FT_RFork_Ref*)b )->res_id; } @@ -240,7 +234,7 @@ (char)( 0xFF & ( tag_internal >> 16 ) ), (char)( 0xFF & ( tag_internal >> 8 ) ), (char)( 0xFF & ( tag_internal >> 0 ) ) )); - FT_TRACE3(( " : subcount=%d, suboffset=0x%04x\n", + FT_TRACE3(( " : subcount=%d, suboffset=0x%04lx\n", subcnt, rpos )); if ( tag_internal == tag ) @@ -257,7 +251,7 @@ if ( error ) return error; - if ( FT_NEW_ARRAY( ref, *count ) ) + if ( FT_QNEW_ARRAY( ref, *count ) ) return error; for ( j = 0; j < *count; j++ ) @@ -286,7 +280,7 @@ ref[j].offset = temp & 0xFFFFFFL; FT_TRACE3(( " [%d]:" - " resource_id=0x%04x, offset=0x%08x\n", + " resource_id=0x%04x, offset=0x%08lx\n", j, (FT_UShort)ref[j].res_id, ref[j].offset )); } @@ -295,18 +289,17 @@ ft_qsort( ref, (size_t)*count, sizeof ( FT_RFork_Ref ), - ( int(*)(const void*, - const void*) )ft_raccess_sort_ref_by_id ); + ft_raccess_sort_ref_by_id ); FT_TRACE3(( " -- sort resources by their ids --\n" )); for ( j = 0; j < *count; j++ ) FT_TRACE3(( " [%d]:" - " resource_id=0x%04x, offset=0x%08x\n", + " resource_id=0x%04x, offset=0x%08lx\n", j, ref[j].res_id, ref[j].offset )); } - if ( FT_NEW_ARRAY( offsets_internal, *count ) ) + if ( FT_QNEW_ARRAY( offsets_internal, *count ) ) goto Exit; /* XXX: duplicated reference ID, @@ -409,17 +402,17 @@ FT_Long *result_offset ); - CONST_FT_RFORK_RULE_ARRAY_BEGIN(ft_raccess_guess_table, - ft_raccess_guess_rec) - CONST_FT_RFORK_RULE_ARRAY_ENTRY(apple_double, apple_double) - CONST_FT_RFORK_RULE_ARRAY_ENTRY(apple_single, apple_single) - CONST_FT_RFORK_RULE_ARRAY_ENTRY(darwin_ufs_export, darwin_ufs_export) - CONST_FT_RFORK_RULE_ARRAY_ENTRY(darwin_newvfs, darwin_newvfs) - CONST_FT_RFORK_RULE_ARRAY_ENTRY(darwin_hfsplus, darwin_hfsplus) - CONST_FT_RFORK_RULE_ARRAY_ENTRY(vfat, vfat) - CONST_FT_RFORK_RULE_ARRAY_ENTRY(linux_cap, linux_cap) - CONST_FT_RFORK_RULE_ARRAY_ENTRY(linux_double, linux_double) - CONST_FT_RFORK_RULE_ARRAY_ENTRY(linux_netatalk, linux_netatalk) + CONST_FT_RFORK_RULE_ARRAY_BEGIN( ft_raccess_guess_table, + ft_raccess_guess_rec ) + CONST_FT_RFORK_RULE_ARRAY_ENTRY( apple_double, apple_double ) + CONST_FT_RFORK_RULE_ARRAY_ENTRY( apple_single, apple_single ) + CONST_FT_RFORK_RULE_ARRAY_ENTRY( darwin_ufs_export, darwin_ufs_export ) + CONST_FT_RFORK_RULE_ARRAY_ENTRY( darwin_newvfs, darwin_newvfs ) + CONST_FT_RFORK_RULE_ARRAY_ENTRY( darwin_hfsplus, darwin_hfsplus ) + CONST_FT_RFORK_RULE_ARRAY_ENTRY( vfat, vfat ) + CONST_FT_RFORK_RULE_ARRAY_ENTRY( linux_cap, linux_cap ) + CONST_FT_RFORK_RULE_ARRAY_ENTRY( linux_double, linux_double ) + CONST_FT_RFORK_RULE_ARRAY_ENTRY( linux_netatalk, linux_netatalk ) CONST_FT_RFORK_RULE_ARRAY_END @@ -609,7 +602,7 @@ if ( base_file_len + 6 > FT_INT_MAX ) return FT_THROW( Array_Too_Large ); - if ( FT_ALLOC( newpath, base_file_len + 6 ) ) + if ( FT_QALLOC( newpath, base_file_len + 6 ) ) return error; FT_MEM_COPY( newpath, base_file_name, base_file_len ); @@ -645,7 +638,7 @@ if ( base_file_len + 18 > FT_INT_MAX ) return FT_THROW( Array_Too_Large ); - if ( FT_ALLOC( newpath, base_file_len + 18 ) ) + if ( FT_QALLOC( newpath, base_file_len + 18 ) ) return error; FT_MEM_COPY( newpath, base_file_name, base_file_len ); @@ -875,13 +868,11 @@ const char* tmp; const char* slash; size_t new_length; - FT_Error error = FT_Err_Ok; - - FT_UNUSED( error ); + FT_Error error; new_length = ft_strlen( original_name ) + ft_strlen( insertion ); - if ( FT_ALLOC( new_name, new_length + 1 ) ) + if ( FT_QALLOC( new_name, new_length + 1 ) ) return NULL; tmp = ft_strrchr( original_name, '/' ); diff --git a/src/font/freetype-2.10.2/src/base/ftsnames.c b/3rdparty/freetype-2.13.2/src/base/ftsnames.c similarity index 93% rename from src/font/freetype-2.10.2/src/base/ftsnames.c rename to 3rdparty/freetype-2.13.2/src/base/ftsnames.c index 25f5d45be..1917a3f1d 100644 --- a/src/font/freetype-2.10.2/src/base/ftsnames.c +++ b/3rdparty/freetype-2.13.2/src/base/ftsnames.c @@ -7,7 +7,7 @@ * * This is _not_ used to retrieve glyph names! * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,12 +19,11 @@ */ -#include -#include FT_INTERNAL_DEBUG_H +#include -#include FT_SFNT_NAMES_H -#include FT_INTERNAL_TRUETYPE_TYPES_H -#include FT_INTERNAL_STREAM_H +#include +#include +#include #ifdef TT_CONFIG_OPTION_SFNT_NAMES @@ -66,7 +65,7 @@ FT_Stream stream = face->stream; - if ( FT_NEW_ARRAY ( entry->string, entry->stringLength ) || + if ( FT_QNEW_ARRAY ( entry->string, entry->stringLength ) || FT_STREAM_SEEK( entry->stringOffset ) || FT_STREAM_READ( entry->string, entry->stringLength ) ) { @@ -122,7 +121,7 @@ FT_Stream stream = face->stream; - if ( FT_NEW_ARRAY ( entry->string, entry->stringLength ) || + if ( FT_QNEW_ARRAY ( entry->string, entry->stringLength ) || FT_STREAM_SEEK( entry->stringOffset ) || FT_STREAM_READ( entry->string, entry->stringLength ) ) { diff --git a/src/font/freetype-2.10.2/src/base/ftstream.c b/3rdparty/freetype-2.13.2/src/base/ftstream.c similarity index 91% rename from src/font/freetype-2.10.2/src/base/ftstream.c rename to 3rdparty/freetype-2.13.2/src/base/ftstream.c index 7dbf9b55f..64826aceb 100644 --- a/src/font/freetype-2.10.2/src/base/ftstream.c +++ b/3rdparty/freetype-2.13.2/src/base/ftstream.c @@ -4,7 +4,7 @@ * * I/O stream support (body). * - * Copyright (C) 2000-2020 by + * Copyright (C) 2000-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,9 +16,8 @@ */ -#include -#include FT_INTERNAL_STREAM_H -#include FT_INTERNAL_DEBUG_H +#include +#include /************************************************************************** @@ -62,7 +61,7 @@ if ( stream->read ) { - if ( stream->read( stream, pos, 0, 0 ) ) + if ( stream->read( stream, pos, NULL, 0 ) ) { FT_ERROR(( "FT_Stream_Seek:" " invalid i/o; pos = 0x%lx, size = 0x%lx\n", @@ -142,7 +141,9 @@ if ( read_bytes > count ) read_bytes = count; - FT_MEM_COPY( buffer, stream->base + pos, read_bytes ); + /* Allow "reading" zero bytes without UB even if buffer is NULL */ + if ( count ) + FT_MEM_COPY( buffer, stream->base + pos, read_bytes ); } stream->pos = pos + read_bytes; @@ -179,7 +180,9 @@ if ( read_bytes > count ) read_bytes = count; - FT_MEM_COPY( buffer, stream->base + stream->pos, read_bytes ); + /* Allow "reading" zero bytes without UB even if buffer is NULL */ + if ( count ) + FT_MEM_COPY( buffer, stream->base + stream->pos, read_bytes ); } stream->pos += read_bytes; @@ -262,7 +265,7 @@ } #ifdef FT_DEBUG_MEMORY - /* assume _ft_debug_file and _ft_debug_lineno are already set */ + /* assume `ft_debug_file_` and `ft_debug_lineno_` are already set */ stream->base = (unsigned char*)ft_mem_qalloc( memory, (FT_Long)count, &error ); @@ -348,27 +351,27 @@ } - FT_BASE_DEF( FT_Char ) - FT_Stream_GetChar( FT_Stream stream ) + FT_BASE_DEF( FT_Byte ) + FT_Stream_GetByte( FT_Stream stream ) { - FT_Char result; + FT_Byte result; FT_ASSERT( stream && stream->cursor ); result = 0; if ( stream->cursor < stream->limit ) - result = (FT_Char)*stream->cursor++; + result = *stream->cursor++; return result; } - FT_BASE_DEF( FT_UShort ) + FT_BASE_DEF( FT_UInt16 ) FT_Stream_GetUShort( FT_Stream stream ) { FT_Byte* p; - FT_UShort result; + FT_UInt16 result; FT_ASSERT( stream && stream->cursor ); @@ -383,11 +386,11 @@ } - FT_BASE_DEF( FT_UShort ) + FT_BASE_DEF( FT_UInt16 ) FT_Stream_GetUShortLE( FT_Stream stream ) { FT_Byte* p; - FT_UShort result; + FT_UInt16 result; FT_ASSERT( stream && stream->cursor ); @@ -402,11 +405,11 @@ } - FT_BASE_DEF( FT_ULong ) + FT_BASE_DEF( FT_UInt32 ) FT_Stream_GetUOffset( FT_Stream stream ) { FT_Byte* p; - FT_ULong result; + FT_UInt32 result; FT_ASSERT( stream && stream->cursor ); @@ -420,11 +423,11 @@ } - FT_BASE_DEF( FT_ULong ) + FT_BASE_DEF( FT_UInt32 ) FT_Stream_GetULong( FT_Stream stream ) { FT_Byte* p; - FT_ULong result; + FT_UInt32 result; FT_ASSERT( stream && stream->cursor ); @@ -438,11 +441,11 @@ } - FT_BASE_DEF( FT_ULong ) + FT_BASE_DEF( FT_UInt32 ) FT_Stream_GetULongLE( FT_Stream stream ) { FT_Byte* p; - FT_ULong result; + FT_UInt32 result; FT_ASSERT( stream && stream->cursor ); @@ -456,8 +459,8 @@ } - FT_BASE_DEF( FT_Char ) - FT_Stream_ReadChar( FT_Stream stream, + FT_BASE_DEF( FT_Byte ) + FT_Stream_ReadByte( FT_Stream stream, FT_Error* error ) { FT_Byte result = 0; @@ -465,47 +468,46 @@ FT_ASSERT( stream ); - *error = FT_Err_Ok; - - if ( stream->read ) - { - if ( stream->read( stream, stream->pos, &result, 1L ) != 1L ) - goto Fail; - } - else + if ( stream->pos < stream->size ) { - if ( stream->pos < stream->size ) - result = stream->base[stream->pos]; + if ( stream->read ) + { + if ( stream->read( stream, stream->pos, &result, 1L ) != 1L ) + goto Fail; + } else - goto Fail; + result = stream->base[stream->pos]; } + else + goto Fail; + stream->pos++; - return (FT_Char)result; + *error = FT_Err_Ok; + + return result; Fail: *error = FT_THROW( Invalid_Stream_Operation ); - FT_ERROR(( "FT_Stream_ReadChar:" + FT_ERROR(( "FT_Stream_ReadByte:" " invalid i/o; pos = 0x%lx, size = 0x%lx\n", stream->pos, stream->size )); - return 0; + return result; } - FT_BASE_DEF( FT_UShort ) + FT_BASE_DEF( FT_UInt16 ) FT_Stream_ReadUShort( FT_Stream stream, FT_Error* error ) { FT_Byte reads[2]; - FT_Byte* p = 0; - FT_UShort result = 0; + FT_Byte* p; + FT_UInt16 result = 0; FT_ASSERT( stream ); - *error = FT_Err_Ok; - if ( stream->pos + 1 < stream->size ) { if ( stream->read ) @@ -526,6 +528,8 @@ stream->pos += 2; + *error = FT_Err_Ok; + return result; Fail: @@ -534,23 +538,21 @@ " invalid i/o; pos = 0x%lx, size = 0x%lx\n", stream->pos, stream->size )); - return 0; + return result; } - FT_BASE_DEF( FT_UShort ) + FT_BASE_DEF( FT_UInt16 ) FT_Stream_ReadUShortLE( FT_Stream stream, FT_Error* error ) { FT_Byte reads[2]; - FT_Byte* p = 0; - FT_UShort result = 0; + FT_Byte* p; + FT_UInt16 result = 0; FT_ASSERT( stream ); - *error = FT_Err_Ok; - if ( stream->pos + 1 < stream->size ) { if ( stream->read ) @@ -571,6 +573,8 @@ stream->pos += 2; + *error = FT_Err_Ok; + return result; Fail: @@ -579,7 +583,7 @@ " invalid i/o; pos = 0x%lx, size = 0x%lx\n", stream->pos, stream->size )); - return 0; + return result; } @@ -588,14 +592,12 @@ FT_Error* error ) { FT_Byte reads[3]; - FT_Byte* p = 0; + FT_Byte* p; FT_ULong result = 0; FT_ASSERT( stream ); - *error = FT_Err_Ok; - if ( stream->pos + 2 < stream->size ) { if ( stream->read ) @@ -616,6 +618,8 @@ stream->pos += 3; + *error = FT_Err_Ok; + return result; Fail: @@ -624,23 +628,21 @@ " invalid i/o; pos = 0x%lx, size = 0x%lx\n", stream->pos, stream->size )); - return 0; + return result; } - FT_BASE_DEF( FT_ULong ) + FT_BASE_DEF( FT_UInt32 ) FT_Stream_ReadULong( FT_Stream stream, FT_Error* error ) { FT_Byte reads[4]; - FT_Byte* p = 0; - FT_ULong result = 0; + FT_Byte* p; + FT_UInt32 result = 0; FT_ASSERT( stream ); - *error = FT_Err_Ok; - if ( stream->pos + 3 < stream->size ) { if ( stream->read ) @@ -661,6 +663,8 @@ stream->pos += 4; + *error = FT_Err_Ok; + return result; Fail: @@ -669,23 +673,21 @@ " invalid i/o; pos = 0x%lx, size = 0x%lx\n", stream->pos, stream->size )); - return 0; + return result; } - FT_BASE_DEF( FT_ULong ) + FT_BASE_DEF( FT_UInt32 ) FT_Stream_ReadULongLE( FT_Stream stream, FT_Error* error ) { FT_Byte reads[4]; - FT_Byte* p = 0; - FT_ULong result = 0; + FT_Byte* p; + FT_UInt32 result = 0; FT_ASSERT( stream ); - *error = FT_Err_Ok; - if ( stream->pos + 3 < stream->size ) { if ( stream->read ) @@ -706,6 +708,8 @@ stream->pos += 4; + *error = FT_Err_Ok; + return result; Fail: @@ -714,7 +718,7 @@ " invalid i/o; pos = 0x%lx, size = 0x%lx\n", stream->pos, stream->size )); - return 0; + return result; } diff --git a/src/font/freetype-2.10.2/src/base/ftstroke.c b/3rdparty/freetype-2.13.2/src/base/ftstroke.c similarity index 97% rename from src/font/freetype-2.10.2/src/base/ftstroke.c rename to 3rdparty/freetype-2.13.2/src/base/ftstroke.c index 3369dc24b..92f1e4308 100644 --- a/src/font/freetype-2.10.2/src/base/ftstroke.c +++ b/3rdparty/freetype-2.13.2/src/base/ftstroke.c @@ -4,7 +4,7 @@ * * FreeType path stroker (body). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,13 +16,12 @@ */ -#include -#include FT_STROKER_H -#include FT_TRIGONOMETRY_H -#include FT_OUTLINE_H -#include FT_INTERNAL_MEMORY_H -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_OBJECTS_H +#include +#include +#include +#include +#include +#include /* declare an extern to access `ft_outline_glyph_class' globally */ @@ -975,7 +974,8 @@ FT_StrokeBorder border = stroker->borders + side; FT_Angle phi, theta, rotate; FT_Fixed length; - FT_Vector sigma, delta; + FT_Vector sigma = { 0, 0 }; + FT_Vector delta; FT_Error error = FT_Err_Ok; FT_Bool intersect; /* use intersection of lines? */ @@ -1049,7 +1049,7 @@ { /* this is a mitered (pointed) or beveled (truncated) corner */ FT_Fixed radius = stroker->radius; - FT_Vector sigma; + FT_Vector sigma = { 0, 0 }; FT_Angle theta = 0, phi = 0; FT_Bool bevel, fixed_bevel; @@ -1529,7 +1529,8 @@ stroker->angle_in = angle_out; } - stroker->center = *to; + stroker->center = *to; + stroker->line_length = 0; Exit: return error; @@ -1745,7 +1746,8 @@ stroker->angle_in = angle_out; } - stroker->center = *to; + stroker->center = *to; + stroker->line_length = 0; Exit: return error; @@ -1898,13 +1900,9 @@ } else { - FT_Angle turn; - FT_Int inside_side; - - /* close the path if needed */ - if ( stroker->center.x != stroker->subpath_start.x || - stroker->center.y != stroker->subpath_start.y ) + if ( !FT_IS_SMALL( stroker->center.x - stroker->subpath_start.x ) || + !FT_IS_SMALL( stroker->center.y - stroker->subpath_start.y ) ) { error = FT_Stroker_LineTo( stroker, &stroker->subpath_start ); if ( error ) @@ -1913,29 +1911,11 @@ /* process the corner */ stroker->angle_out = stroker->subpath_angle; - turn = FT_Angle_Diff( stroker->angle_in, - stroker->angle_out ); - - /* no specific corner processing is required if the turn is 0 */ - if ( turn != 0 ) - { - /* when we turn to the right, the inside side is 0 */ - /* otherwise, the inside side is 1 */ - inside_side = ( turn < 0 ); - error = ft_stroker_inside( stroker, - inside_side, - stroker->subpath_line_length ); - if ( error ) - goto Exit; - - /* process the outside side */ - error = ft_stroker_outside( stroker, - !inside_side, - stroker->subpath_line_length ); - if ( error ) - goto Exit; - } + error = ft_stroker_process_corner( stroker, + stroker->subpath_line_length ); + if ( error ) + goto Exit; /* then end our two subpaths */ ft_stroke_border_close( stroker->borders + 0, FALSE ); @@ -2075,7 +2055,9 @@ FT_Error error; FT_Int n; /* index of contour in outline */ - FT_UInt first; /* index of first point in contour */ + FT_Int first; /* index of first point in contour */ + FT_Int last; /* index of last point in contour */ + FT_Int tag; /* current point's state */ @@ -2087,22 +2069,17 @@ FT_Stroker_Rewind( stroker ); - first = 0; - + last = -1; for ( n = 0; n < outline->n_contours; n++ ) { - FT_UInt last; /* index of last point in contour */ - - - last = (FT_UInt)outline->contours[n]; - limit = outline->points + last; + first = last + 1; + last = outline->contours[n]; /* skip empty points; we don't stroke these */ if ( last <= first ) - { - first = last + 1; continue; - } + + limit = outline->points + last; v_start = outline->points[first]; v_last = outline->points[last]; @@ -2251,8 +2228,6 @@ if ( error ) goto Exit; } - - first = last + 1; } return FT_Err_Ok; diff --git a/src/font/freetype-2.10.2/src/base/ftsynth.c b/3rdparty/freetype-2.13.2/src/base/ftsynth.c similarity index 78% rename from src/font/freetype-2.10.2/src/base/ftsynth.c rename to 3rdparty/freetype-2.13.2/src/base/ftsynth.c index eee6b952b..f32edd338 100644 --- a/src/font/freetype-2.10.2/src/base/ftsynth.c +++ b/3rdparty/freetype-2.13.2/src/base/ftsynth.c @@ -4,7 +4,7 @@ * * FreeType synthesizing code for emboldening and slanting (body). * - * Copyright (C) 2000-2020 by + * Copyright (C) 2000-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,12 +16,11 @@ */ -#include -#include FT_SYNTHESIS_H -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_OBJECTS_H -#include FT_OUTLINE_H -#include FT_BITMAP_H +#include +#include +#include +#include +#include /************************************************************************** @@ -46,6 +45,18 @@ FT_EXPORT_DEF( void ) FT_GlyphSlot_Oblique( FT_GlyphSlot slot ) + { + /* Value '0x0366A' corresponds to a shear angle of about 12 degrees. */ + FT_GlyphSlot_Slant( slot, 0x0366A, 0 ); + } + + + /* documentation is in ftsynth.h */ + + FT_EXPORT_DEF( void ) + FT_GlyphSlot_Slant( FT_GlyphSlot slot, + FT_Fixed xslant, + FT_Fixed yslant ) { FT_Matrix transform; FT_Outline* outline; @@ -62,13 +73,11 @@ /* we don't touch the advance width */ - /* For italic, simply apply a shear transform, with an angle */ - /* of about 12 degrees. */ - + /* For italic, simply apply a shear transform */ transform.xx = 0x10000L; - transform.yx = 0x00000L; + transform.yx = -yslant; - transform.xy = 0x0366AL; + transform.xy = xslant; transform.yy = 0x10000L; FT_Outline_Transform( outline, &transform ); @@ -88,9 +97,18 @@ FT_EXPORT_DEF( void ) FT_GlyphSlot_Embolden( FT_GlyphSlot slot ) + { + FT_GlyphSlot_AdjustWeight( slot, 0x0AAA, 0x0AAA ); + } + + + FT_EXPORT_DEF( void ) + FT_GlyphSlot_AdjustWeight( FT_GlyphSlot slot, + FT_Fixed xdelta, + FT_Fixed ydelta ) { FT_Library library; - FT_Face face; + FT_Size size; FT_Error error; FT_Pos xstr, ystr; @@ -99,16 +117,15 @@ return; library = slot->library; - face = slot->face; + size = slot->face->size; if ( slot->format != FT_GLYPH_FORMAT_OUTLINE && slot->format != FT_GLYPH_FORMAT_BITMAP ) return; - /* some reasonable strength */ - xstr = FT_MulFix( face->units_per_EM, - face->size->metrics.y_scale ) / 24; - ystr = xstr; + /* express deltas in pixels in 26.6 format */ + xstr = (FT_Pos)size->metrics.x_ppem * xdelta / 1024; + ystr = (FT_Pos)size->metrics.y_ppem * ydelta / 1024; if ( slot->format == FT_GLYPH_FORMAT_OUTLINE ) FT_Outline_EmboldenXY( &slot->outline, xstr, ystr ); @@ -130,7 +147,7 @@ if ( ( ystr >> 6 ) > FT_INT_MAX || ( ystr >> 6 ) < FT_INT_MIN ) { FT_TRACE1(( "FT_GlyphSlot_Embolden:" )); - FT_TRACE1(( "too strong emboldening parameter ystr=%d\n", ystr )); + FT_TRACE1(( "too strong emboldening parameter ystr=%ld\n", ystr )); return; } error = FT_GlyphSlot_Own_Bitmap( slot ); diff --git a/src/font/freetype-2.10.2/src/base/ftsystem.cpp b/3rdparty/freetype-2.13.2/src/base/ftsystem.cpp similarity index 97% rename from src/font/freetype-2.10.2/src/base/ftsystem.cpp rename to 3rdparty/freetype-2.13.2/src/base/ftsystem.cpp index 25d40982e..3b6f40919 100644 --- a/src/font/freetype-2.10.2/src/base/ftsystem.cpp +++ b/3rdparty/freetype-2.13.2/src/base/ftsystem.cpp @@ -30,11 +30,11 @@ extern struct CoreBase *CoreBase; #include #include FT_CONFIG_CONFIG_H -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_STREAM_H -#include FT_SYSTEM_H -#include FT_ERRORS_H -#include FT_TYPES_H +#include +#include +#include +#include +#include /************************************************************************** @@ -237,6 +237,8 @@ extern struct CoreBase *CoreBase; /* documentation is in ftstream.h */ + extern OBJECTPTR modFont; + FT_BASE_DEF( FT_Error ) FT_Stream_Open( FT_Stream stream, const char *filepathname ) { @@ -245,7 +247,6 @@ extern struct CoreBase *CoreBase; OBJECTPTR file = NULL; { - extern OBJECTPTR modFont; pf::SwitchContext ctx(modFont); file = objFile::create::integral(fl::Name("FreetypeTTFile"), fl::Path(filepathname), fl::Flags(FL::READ)); } diff --git a/src/font/freetype-2.10.2/src/base/fttrigon.c b/3rdparty/freetype-2.13.2/src/base/fttrigon.c similarity index 98% rename from src/font/freetype-2.10.2/src/base/fttrigon.c rename to 3rdparty/freetype-2.13.2/src/base/fttrigon.c index dbe11107b..2dd2c3459 100644 --- a/src/font/freetype-2.10.2/src/base/fttrigon.c +++ b/3rdparty/freetype-2.13.2/src/base/fttrigon.c @@ -4,7 +4,7 @@ * * FreeType trigonometric functions (body). * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -29,10 +29,9 @@ * */ -#include -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_CALC_H -#include FT_TRIGONOMETRY_H +#include +#include +#include /* the Cordic shrink factor 0.858785336480436 * 2^32 */ @@ -54,7 +53,7 @@ }; -#ifdef FT_LONG64 +#ifdef FT_INT64 /* multiply a given value by the CORDIC shrink factor */ static FT_Fixed @@ -77,7 +76,7 @@ return s < 0 ? -val : val; } -#else /* !FT_LONG64 */ +#else /* !FT_INT64 */ /* multiply a given value by the CORDIC shrink factor */ static FT_Fixed @@ -126,7 +125,7 @@ return s < 0 ? -val : val; } -#endif /* !FT_LONG64 */ +#endif /* !FT_INT64 */ /* undefined and never called for zero vector */ diff --git a/src/font/freetype-2.10.2/src/base/fttype1.c b/3rdparty/freetype-2.13.2/src/base/fttype1.c similarity index 93% rename from src/font/freetype-2.10.2/src/base/fttype1.c rename to 3rdparty/freetype-2.13.2/src/base/fttype1.c index 61778faa7..637c5cf77 100644 --- a/src/font/freetype-2.10.2/src/base/fttype1.c +++ b/3rdparty/freetype-2.13.2/src/base/fttype1.c @@ -4,7 +4,7 @@ * * FreeType utility file for PS names support (body). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,11 +16,10 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_SERVICE_H -#include FT_SERVICE_POSTSCRIPT_INFO_H +#include +#include +#include +#include /* documentation is in t1tables.h */ diff --git a/src/font/freetype-2.10.2/src/base/ftutil.c b/3rdparty/freetype-2.13.2/src/base/ftutil.c similarity index 98% rename from src/font/freetype-2.10.2/src/base/ftutil.c rename to 3rdparty/freetype-2.13.2/src/base/ftutil.c index 629af174b..6120846d2 100644 --- a/src/font/freetype-2.10.2/src/base/ftutil.c +++ b/3rdparty/freetype-2.13.2/src/base/ftutil.c @@ -4,7 +4,7 @@ * * FreeType utility file for memory and list management (body). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,11 +16,10 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_MEMORY_H -#include FT_INTERNAL_OBJECTS_H -#include FT_LIST_H +#include +#include +#include +#include /************************************************************************** diff --git a/src/font/freetype-2.10.2/src/base/ftver.rc b/3rdparty/freetype-2.13.2/src/base/ftver.rc similarity index 88% rename from src/font/freetype-2.10.2/src/base/ftver.rc rename to 3rdparty/freetype-2.13.2/src/base/ftver.rc index fcbd9eff5..137a6334b 100644 --- a/src/font/freetype-2.10.2/src/base/ftver.rc +++ b/3rdparty/freetype-2.13.2/src/base/ftver.rc @@ -4,7 +4,7 @@ /* */ /* FreeType VERSIONINFO resource for Windows DLLs. */ /* */ -/* Copyright (C) 2018-2020 by */ +/* Copyright (C) 2018-2023 by */ /* David Turner, Robert Wilhelm, and Werner Lemberg. */ /* */ /* This file is part of the FreeType project, and may only be used, */ @@ -18,8 +18,8 @@ #include -#define FT_VERSION 2,10,2,0 -#define FT_VERSION_STR "2.10.2" +#define FT_VERSION 2,13,2,0 +#define FT_VERSION_STR "2.13.2" VS_VERSION_INFO VERSIONINFO FILEVERSION FT_VERSION @@ -38,14 +38,14 @@ FILETYPE VFT_STATIC_LIB BEGIN BLOCK "StringFileInfo" BEGIN - BLOCK "040904E4" + BLOCK "040904B0" BEGIN VALUE "CompanyName", "The FreeType Project" VALUE "FileDescription", "Font Rendering Library" VALUE "FileVersion", FT_VERSION_STR VALUE "ProductName", "FreeType" VALUE "ProductVersion", FT_VERSION_STR - VALUE "LegalCopyright", "\251 2000-2020 The FreeType Project www.freetype.org. All rights reserved." + VALUE "LegalCopyright", L"\x00A9 2000-2023 The FreeType Project www.freetype.org. All rights reserved." VALUE "InternalName", "freetype" VALUE "OriginalFilename", FT_FILENAME END @@ -56,6 +56,6 @@ BEGIN /* The following line should only be modified for localized versions. */ /* It consists of any number of WORD,WORD pairs, with each pair */ /* describing a "language,codepage" combination supported by the file. */ - VALUE "Translation", 0x409, 1252 + VALUE "Translation", 0x409, 1200 END END diff --git a/src/font/freetype-2.10.2/src/base/ftwinfnt.c b/3rdparty/freetype-2.13.2/src/base/ftwinfnt.c similarity index 85% rename from src/font/freetype-2.10.2/src/base/ftwinfnt.c rename to 3rdparty/freetype-2.13.2/src/base/ftwinfnt.c index 77527277c..03b023e07 100644 --- a/src/font/freetype-2.10.2/src/base/ftwinfnt.c +++ b/3rdparty/freetype-2.13.2/src/base/ftwinfnt.c @@ -4,7 +4,7 @@ * * FreeType API for accessing Windows FNT specific info (body). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,11 +16,10 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_WINFONTS_H -#include FT_INTERNAL_OBJECTS_H -#include FT_SERVICE_WINFNT_H +#include +#include +#include +#include /* documentation is in ftwinfnt.h */ diff --git a/src/font/freetype-2.10.2/src/base/md5.c b/3rdparty/freetype-2.13.2/src/base/md5.c similarity index 100% rename from src/font/freetype-2.10.2/src/base/md5.c rename to 3rdparty/freetype-2.13.2/src/base/md5.c diff --git a/src/font/freetype-2.10.2/src/base/md5.h b/3rdparty/freetype-2.13.2/src/base/md5.h similarity index 100% rename from src/font/freetype-2.10.2/src/base/md5.h rename to 3rdparty/freetype-2.13.2/src/base/md5.h diff --git a/src/font/freetype-2.10.2/src/base/rules.mk b/3rdparty/freetype-2.13.2/src/base/rules.mk similarity index 99% rename from src/font/freetype-2.10.2/src/base/rules.mk rename to 3rdparty/freetype-2.13.2/src/base/rules.mk index 411c4c821..b7de9b5ca 100644 --- a/src/font/freetype-2.10.2/src/base/rules.mk +++ b/3rdparty/freetype-2.13.2/src/base/rules.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 1996-2020 by +# Copyright (C) 1996-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, diff --git a/src/font/freetype-2.10.2/src/cache/ftcache.c b/3rdparty/freetype-2.13.2/src/cache/ftcache.c similarity index 93% rename from src/font/freetype-2.10.2/src/cache/ftcache.c rename to 3rdparty/freetype-2.13.2/src/cache/ftcache.c index 4137f6869..1af2e6772 100644 --- a/src/font/freetype-2.10.2/src/cache/ftcache.c +++ b/3rdparty/freetype-2.13.2/src/cache/ftcache.c @@ -4,7 +4,7 @@ * * The FreeType Caching sub-system (body only). * - * Copyright (C) 2000-2020 by + * Copyright (C) 2000-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -17,7 +17,6 @@ #define FT_MAKE_OPTION_SINGLE_OBJECT -#include #include "ftcbasic.c" #include "ftccache.c" diff --git a/src/font/freetype-2.10.2/src/cache/ftcbasic.c b/3rdparty/freetype-2.13.2/src/cache/ftcbasic.c similarity index 94% rename from src/font/freetype-2.10.2/src/cache/ftcbasic.c rename to 3rdparty/freetype-2.13.2/src/cache/ftcbasic.c index a65a90e86..24a56c8d2 100644 --- a/src/font/freetype-2.10.2/src/cache/ftcbasic.c +++ b/3rdparty/freetype-2.13.2/src/cache/ftcbasic.c @@ -4,7 +4,7 @@ * * The FreeType basic cache interface (body). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,10 +16,9 @@ */ -#include -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_DEBUG_H -#include FT_CACHE_H +#include +#include +#include #include "ftcglyph.h" #include "ftcimage.h" #include "ftcsbits.h" @@ -27,6 +26,7 @@ #include "ftccback.h" #include "ftcerror.h" +#undef FT_COMPONENT #define FT_COMPONENT cache @@ -109,13 +109,18 @@ if ( error || !face ) return result; +#ifdef FT_DEBUG_LEVEL_TRACE if ( (FT_ULong)face->num_glyphs > FT_UINT_MAX || 0 > face->num_glyphs ) + { FT_TRACE1(( "ftc_basic_family_get_count:" - " too large number of glyphs in this face, truncated\n", + " the number of glyphs in this face is %ld,\n", face->num_glyphs )); + FT_TRACE1(( " " + " which is too much and thus truncated\n" )); + } +#endif - if ( !error ) - result = (FT_UInt)face->num_glyphs; + result = (FT_UInt)face->num_glyphs; return result; } @@ -177,7 +182,8 @@ if ( !error ) { if ( face->glyph->format == FT_GLYPH_FORMAT_BITMAP || - face->glyph->format == FT_GLYPH_FORMAT_OUTLINE ) + face->glyph->format == FT_GLYPH_FORMAT_OUTLINE || + face->glyph->format == FT_GLYPH_FORMAT_SVG ) { /* ok, copy it */ FT_Glyph glyph; @@ -313,7 +319,7 @@ #if 0xFFFFFFFFUL > FT_UINT_MAX if ( (type->flags & (FT_ULong)FT_UINT_MAX) ) FT_TRACE1(( "FTC_ImageCache_Lookup:" - " higher bits in load_flags 0x%x are dropped\n", + " higher bits in load_flags 0x%lx are dropped\n", (FT_ULong)type->flags & ~((FT_ULong)FT_UINT_MAX) )); #endif @@ -331,7 +337,7 @@ #if 1 /* inlining is about 50% faster! */ FTC_GCACHE_LOOKUP_CMP( cache, ftc_basic_family_compare, - FTC_GNode_Compare, + ftc_gnode_compare, hash, gindex, &query, node, @@ -394,7 +400,7 @@ #if FT_ULONG_MAX > FT_UINT_MAX if ( load_flags > FT_UINT_MAX ) FT_TRACE1(( "FTC_ImageCache_LookupScaler:" - " higher bits in load_flags 0x%x are dropped\n", + " higher bits in load_flags 0x%lx are dropped\n", load_flags & ~((FT_ULong)FT_UINT_MAX) )); #endif @@ -405,7 +411,7 @@ FTC_GCACHE_LOOKUP_CMP( cache, ftc_basic_family_compare, - FTC_GNode_Compare, + ftc_gnode_compare, hash, gindex, &query, node, @@ -511,7 +517,7 @@ #if 0xFFFFFFFFUL > FT_UINT_MAX if ( (type->flags & (FT_ULong)FT_UINT_MAX) ) FT_TRACE1(( "FTC_ImageCache_Lookup:" - " higher bits in load_flags 0x%x are dropped\n", + " higher bits in load_flags 0x%lx are dropped\n", (FT_ULong)type->flags & ~((FT_ULong)FT_UINT_MAX) )); #endif @@ -531,7 +537,7 @@ #if 1 /* inlining is about 50% faster! */ FTC_GCACHE_LOOKUP_CMP( cache, ftc_basic_family_compare, - FTC_SNode_Compare, + ftc_snode_compare, hash, gindex, &query, node, @@ -594,7 +600,7 @@ #if FT_ULONG_MAX > FT_UINT_MAX if ( load_flags > FT_UINT_MAX ) FT_TRACE1(( "FTC_ImageCache_LookupScaler:" - " higher bits in load_flags 0x%x are dropped\n", + " higher bits in load_flags 0x%lx are dropped\n", load_flags & ~((FT_ULong)FT_UINT_MAX) )); #endif @@ -607,7 +613,7 @@ FTC_GCACHE_LOOKUP_CMP( cache, ftc_basic_family_compare, - FTC_SNode_Compare, + ftc_snode_compare, hash, gindex, &query, node, diff --git a/src/font/freetype-2.10.2/src/cache/ftccache.c b/3rdparty/freetype-2.13.2/src/cache/ftccache.c similarity index 84% rename from src/font/freetype-2.10.2/src/cache/ftccache.c rename to 3rdparty/freetype-2.13.2/src/cache/ftccache.c index 1d406c420..e0698557b 100644 --- a/src/font/freetype-2.10.2/src/cache/ftccache.c +++ b/3rdparty/freetype-2.13.2/src/cache/ftccache.c @@ -4,7 +4,7 @@ * * The FreeType internal cache interface (body). * - * Copyright (C) 2000-2020 by + * Copyright (C) 2000-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,10 +16,9 @@ */ -#include #include "ftcmanag.h" -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_DEBUG_H +#include +#include #include "ftccback.h" #include "ftcerror.h" @@ -91,15 +90,14 @@ ftc_get_top_node_for_hash( FTC_Cache cache, FT_Offset hash ) { - FTC_Node* pnode; FT_Offset idx; idx = hash & cache->mask; - if ( idx < cache->p ) - idx = hash & ( 2 * cache->mask + 1 ); - pnode = cache->buckets + idx; - return pnode; + if ( idx >= cache->p ) + idx = hash & ( cache->mask >> 1 ); + + return cache->buckets + idx; } #endif /* !FTC_INLINE */ @@ -115,12 +113,12 @@ for (;;) { FTC_Node node, *pnode; - FT_UFast p = cache->p; - FT_UFast mask = cache->mask; - FT_UFast count = mask + p + 1; /* number of buckets */ + FT_UFast p = cache->p; + FT_UFast size = cache->mask + 1; /* available size */ + FT_UFast half = size >> 1; - /* do we need to shrink the buckets array? */ + /* do we need to expand the buckets array? */ if ( cache->slack < 0 ) { FTC_Node new_list = NULL; @@ -129,20 +127,22 @@ /* try to expand the buckets array _before_ splitting * the bucket lists */ - if ( p >= mask ) + if ( p == size ) { FT_Memory memory = cache->memory; FT_Error error; /* if we can't expand the array, leave immediately */ - if ( FT_RENEW_ARRAY( cache->buckets, - ( mask + 1 ) * 2, ( mask + 1 ) * 4 ) ) + if ( FT_QRENEW_ARRAY( cache->buckets, size, size * 2 ) ) break; + + cache->mask = 2 * size - 1; + half = size; } - /* split a single bucket */ - pnode = cache->buckets + p; + /* the bucket to split */ + pnode = cache->buckets + p - half; for (;;) { @@ -150,7 +150,7 @@ if ( !node ) break; - if ( node->hash & ( mask + 1 ) ) + if ( node->hash & half ) { *pnode = node->link; node->link = new_list; @@ -160,56 +160,50 @@ pnode = &node->link; } - cache->buckets[p + mask + 1] = new_list; + cache->buckets[p] = new_list; cache->slack += FTC_HASH_MAX_LOAD; + cache->p = p + 1; - if ( p >= mask ) - { - cache->mask = 2 * mask + 1; - cache->p = 0; - } - else - cache->p = p + 1; + FT_TRACE2(( "ftc_cache_resize: cache %u increased to %u hashes\n", + cache->index, cache->p )); } - /* do we need to expand the buckets array? */ - else if ( cache->slack > (FT_Long)count * FTC_HASH_SUB_LOAD ) + /* do we need to shrink the buckets array? */ + else if ( cache->slack > (FT_Long)p * FTC_HASH_SUB_LOAD ) { - FT_UFast old_index = p + mask; - FTC_Node* pold; + FTC_Node old_list = cache->buckets[--p]; - if ( old_index + 1 <= FTC_HASH_INITIAL_SIZE ) + if ( p < FTC_HASH_INITIAL_SIZE ) break; - if ( p == 0 ) + if ( p == half ) { FT_Memory memory = cache->memory; FT_Error error; /* if we can't shrink the array, leave immediately */ - if ( FT_RENEW_ARRAY( cache->buckets, - ( mask + 1 ) * 2, mask + 1 ) ) + if ( FT_QRENEW_ARRAY( cache->buckets, size, half ) ) break; - cache->mask >>= 1; - p = cache->mask; + cache->mask = half - 1; } - else - p--; - pnode = cache->buckets + p; + /* the bucket to merge */ + pnode = cache->buckets + p - half; + while ( *pnode ) pnode = &(*pnode)->link; - pold = cache->buckets + old_index; - *pnode = *pold; - *pold = NULL; + *pnode = old_list; cache->slack -= FTC_HASH_MAX_LOAD; cache->p = p; + + FT_TRACE2(( "ftc_cache_resize: cache %u decreased to %u hashes\n", + cache->index, cache->p )); } /* otherwise, the hash table is balanced */ @@ -241,7 +235,7 @@ if ( node == node0 ) break; - pnode = &(*pnode)->link; + pnode = &node->link; } *pnode = node0->link; @@ -309,7 +303,7 @@ #if 0 /* check, just in case of general corruption :-) */ if ( manager->num_nodes == 0 ) - FT_TRACE0(( "ftc_node_destroy: invalid cache node count (%d)\n", + FT_TRACE0(( "ftc_node_destroy: invalid cache node count (%u)\n", manager->num_nodes )); #endif } @@ -324,13 +318,6 @@ /*************************************************************************/ - FT_LOCAL_DEF( FT_Error ) - FTC_Cache_Init( FTC_Cache cache ) - { - return ftc_cache_init( cache ); - } - - FT_LOCAL_DEF( FT_Error ) ftc_cache_init( FTC_Cache cache ) { @@ -338,30 +325,38 @@ FT_Error error; - cache->p = 0; + cache->p = FTC_HASH_INITIAL_SIZE; cache->mask = FTC_HASH_INITIAL_SIZE - 1; cache->slack = FTC_HASH_INITIAL_SIZE * FTC_HASH_MAX_LOAD; - (void)FT_NEW_ARRAY( cache->buckets, FTC_HASH_INITIAL_SIZE * 2 ); + FT_MEM_NEW_ARRAY( cache->buckets, FTC_HASH_INITIAL_SIZE ); return error; } - static void - FTC_Cache_Clear( FTC_Cache cache ) + FT_LOCAL_DEF( FT_Error ) + FTC_Cache_Init( FTC_Cache cache ) + { + return ftc_cache_init( cache ); + } + + + FT_LOCAL_DEF( void ) + ftc_cache_done( FTC_Cache cache ) { - if ( cache && cache->buckets ) + FT_Memory memory = cache->memory; + + + if ( cache->buckets ) { FTC_Manager manager = cache->manager; + FT_UFast count = cache->p; FT_UFast i; - FT_UFast count; - - count = cache->p + cache->mask + 1; for ( i = 0; i < count; i++ ) { - FTC_Node *pnode = cache->buckets + i, next, node = *pnode; + FTC_Node node = cache->buckets[i], next; while ( node ) @@ -378,30 +373,14 @@ cache->clazz.node_free( node, cache ); node = next; } - cache->buckets[i] = NULL; } - ftc_cache_resize( cache ); } - } - - - FT_LOCAL_DEF( void ) - ftc_cache_done( FTC_Cache cache ) - { - if ( cache->memory ) - { - FT_Memory memory = cache->memory; - - - FTC_Cache_Clear( cache ); - FT_FREE( cache->buckets ); - cache->mask = 0; - cache->p = 0; - cache->slack = 0; + FT_FREE( cache->buckets ); - cache->memory = NULL; - } + cache->p = 0; + cache->mask = 0; + cache->slack = 0; } @@ -418,7 +397,7 @@ FTC_Node node ) { node->hash = hash; - node->cache_index = (FT_UInt16)cache->index; + node->cache_index = (FT_UShort)cache->index; node->ref_count = 0; ftc_node_hash_link( node, cache ); @@ -460,7 +439,7 @@ { error = cache->clazz.node_new( &node, query, cache ); } - FTC_CACHE_TRYLOOP_END( NULL ); + FTC_CACHE_TRYLOOP_END( NULL ) if ( error ) node = NULL; @@ -529,7 +508,7 @@ goto NewNode; } else - pnode = &((*pnode)->link); + pnode = &(*pnode)->link; } } @@ -564,16 +543,15 @@ FTC_Cache_RemoveFaceID( FTC_Cache cache, FTC_FaceID face_id ) { - FT_UFast i, count; FTC_Manager manager = cache->manager; FTC_Node frees = NULL; + FT_UFast count = cache->p; + FT_UFast i; - count = cache->p + cache->mask + 1; for ( i = 0; i < count; i++ ) { - FTC_Node* bucket = cache->buckets + i; - FTC_Node* pnode = bucket; + FTC_Node* pnode = cache->buckets + i; for (;;) diff --git a/src/font/freetype-2.10.2/src/cache/ftccache.h b/3rdparty/freetype-2.13.2/src/cache/ftccache.h similarity index 95% rename from src/font/freetype-2.10.2/src/cache/ftccache.h rename to 3rdparty/freetype-2.13.2/src/cache/ftccache.h index 2996ee808..850d2554b 100644 --- a/src/font/freetype-2.10.2/src/cache/ftccache.h +++ b/3rdparty/freetype-2.13.2/src/cache/ftccache.h @@ -4,7 +4,7 @@ * * FreeType internal cache interface (specification). * - * Copyright (C) 2000-2020 by + * Copyright (C) 2000-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,7 +19,7 @@ #ifndef FTCCACHE_H_ #define FTCCACHE_H_ - +#include #include "ftcmru.h" FT_BEGIN_HEADER @@ -72,11 +72,12 @@ FT_BEGIN_HEADER #define FTC_NODE_NEXT( x ) FTC_NODE( (x)->mru.next ) #define FTC_NODE_PREV( x ) FTC_NODE( (x)->mru.prev ) + /* address the hash table entries */ #ifdef FTC_INLINE -#define FTC_NODE_TOP_FOR_HASH( cache, hash ) \ - ( ( cache )->buckets + \ - ( ( ( ( hash ) & ( cache )->mask ) < ( cache )->p ) \ - ? ( ( hash ) & ( ( cache )->mask * 2 + 1 ) ) \ +#define FTC_NODE_TOP_FOR_HASH( cache, hash ) \ + ( ( cache )->buckets + \ + ( ( ( ( hash ) & ( cache )->mask ) >= ( cache )->p ) \ + ? ( ( hash ) & ( ( cache )->mask >> 1 ) ) \ : ( ( hash ) & ( cache )->mask ) ) ) #else FT_LOCAL( FTC_Node* ) @@ -139,11 +140,13 @@ FT_BEGIN_HEADER } FTC_CacheClassRec; - /* each cache really implements a dynamic hash table to manage its nodes */ + /* each cache really implements a hash table to manage its nodes */ + /* the number of the table entries (buckets) can change dynamically */ + /* each bucket contains a linked lists of nodes for a given hash */ typedef struct FTC_CacheRec_ { - FT_UFast p; - FT_UFast mask; + FT_UFast p; /* hash table counter */ + FT_UFast mask; /* hash table index range */ FT_Long slack; FTC_Node* buckets; @@ -210,7 +213,7 @@ FT_BEGIN_HEADER #define FTC_CACHE_LOOKUP_CMP( cache, nodecmp, hash, query, node, error ) \ FT_BEGIN_STMNT \ FTC_Node *_bucket, *_pnode, _node; \ - FTC_Cache _cache = FTC_CACHE(cache); \ + FTC_Cache _cache = FTC_CACHE( cache ); \ FT_Offset _hash = (FT_Offset)(hash); \ FTC_Node_CompareFunc _nodcomp = (FTC_Node_CompareFunc)(nodecmp); \ FT_Bool _list_changed = FALSE; \ @@ -251,7 +254,7 @@ FT_BEGIN_HEADER goto NewNode_; \ } \ else \ - _pnode = &((*_pnode)->link); \ + _pnode = &(*_pnode)->link; \ } \ } \ \ diff --git a/src/font/freetype-2.10.2/src/cache/ftccback.h b/3rdparty/freetype-2.13.2/src/cache/ftccback.h similarity index 95% rename from src/font/freetype-2.10.2/src/cache/ftccback.h rename to 3rdparty/freetype-2.13.2/src/cache/ftccback.h index 252be7c2b..5f9db213a 100644 --- a/src/font/freetype-2.10.2/src/cache/ftccback.h +++ b/3rdparty/freetype-2.13.2/src/cache/ftccback.h @@ -4,7 +4,7 @@ * * Callback functions of the caching sub-system (specification only). * - * Copyright (C) 2004-2020 by + * Copyright (C) 2004-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -18,14 +18,14 @@ #ifndef FTCCBACK_H_ #define FTCCBACK_H_ -#include -#include FT_CACHE_H +#include #include "ftcmru.h" #include "ftcimage.h" #include "ftcmanag.h" #include "ftcglyph.h" #include "ftcsbits.h" +FT_BEGIN_HEADER FT_LOCAL( void ) ftc_inode_free( FTC_Node inode, @@ -85,6 +85,7 @@ ftc_node_destroy( FTC_Node node, FTC_Manager manager ); +FT_END_HEADER #endif /* FTCCBACK_H_ */ diff --git a/src/font/freetype-2.10.2/src/cache/ftccmap.c b/3rdparty/freetype-2.13.2/src/cache/ftccmap.c similarity index 92% rename from src/font/freetype-2.10.2/src/cache/ftccmap.c rename to 3rdparty/freetype-2.13.2/src/cache/ftccmap.c index a5da694d5..84f22a667 100644 --- a/src/font/freetype-2.10.2/src/cache/ftccmap.c +++ b/3rdparty/freetype-2.13.2/src/cache/ftccmap.c @@ -4,7 +4,7 @@ * * FreeType CharMap cache (body) * - * Copyright (C) 2000-2020 by + * Copyright (C) 2000-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,13 +16,12 @@ */ -#include -#include FT_FREETYPE_H -#include FT_CACHE_H +#include +#include #include "ftcmanag.h" -#include FT_INTERNAL_MEMORY_H -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_DEBUG_H +#include +#include +#include #include "ftccback.h" #include "ftcerror.h" @@ -117,7 +116,7 @@ FT_UInt nn; - if ( !FT_NEW( node ) ) + if ( !FT_QNEW( node ) ) { node->face_id = query->face_id; node->cmap_index = query->cmap_index; @@ -274,12 +273,11 @@ if ( error ) goto Exit; - FT_ASSERT( (FT_UInt)( char_code - FTC_CMAP_NODE( node )->first ) < - FTC_CMAP_INDICES_MAX ); + FT_ASSERT( char_code - FTC_CMAP_NODE( node )->first < + FTC_CMAP_INDICES_MAX ); /* something rotten can happen with rogue clients */ - if ( (FT_UInt)( char_code - FTC_CMAP_NODE( node )->first >= - FTC_CMAP_INDICES_MAX ) ) + if ( char_code - FTC_CMAP_NODE( node )->first >= FTC_CMAP_INDICES_MAX ) return 0; /* XXX: should return appropriate error */ gindex = FTC_CMAP_NODE( node )->indices[char_code - @@ -297,21 +295,19 @@ if ( error ) goto Exit; - if ( (FT_UInt)cmap_index < (FT_UInt)face->num_charmaps ) + if ( cmap_index < face->num_charmaps ) { - FT_CharMap old, cmap = NULL; + FT_CharMap old = face->charmap; + FT_CharMap cmap = face->charmaps[cmap_index]; - old = face->charmap; - cmap = face->charmaps[cmap_index]; - - if ( old != cmap && !no_cmap_change ) - FT_Set_Charmap( face, cmap ); + if ( !no_cmap_change ) + face->charmap = cmap; gindex = FT_Get_Char_Index( face, char_code ); - if ( old != cmap && !no_cmap_change ) - FT_Set_Charmap( face, old ); + if ( !no_cmap_change ) + face->charmap = old; } FTC_CMAP_NODE( node )->indices[char_code - diff --git a/src/font/freetype-2.10.2/src/cache/ftcerror.h b/3rdparty/freetype-2.13.2/src/cache/ftcerror.h similarity index 90% rename from src/font/freetype-2.10.2/src/cache/ftcerror.h rename to 3rdparty/freetype-2.13.2/src/cache/ftcerror.h index 15e416ed2..dc1a62013 100644 --- a/src/font/freetype-2.10.2/src/cache/ftcerror.h +++ b/3rdparty/freetype-2.13.2/src/cache/ftcerror.h @@ -4,7 +4,7 @@ * * Caching sub-system error codes (specification only). * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -26,7 +26,7 @@ #ifndef FTCERROR_H_ #define FTCERROR_H_ -#include FT_MODULE_ERRORS_H +#include #undef FTERRORS_H_ @@ -34,7 +34,7 @@ #define FT_ERR_PREFIX FTC_Err_ #define FT_ERR_BASE FT_Mod_Err_Cache -#include FT_ERRORS_H +#include #endif /* FTCERROR_H_ */ diff --git a/src/font/freetype-2.10.2/src/cache/ftcglyph.c b/3rdparty/freetype-2.13.2/src/cache/ftcglyph.c similarity index 76% rename from src/font/freetype-2.10.2/src/cache/ftcglyph.c rename to 3rdparty/freetype-2.13.2/src/cache/ftcglyph.c index 559a2fb4c..d344733f3 100644 --- a/src/font/freetype-2.10.2/src/cache/ftcglyph.c +++ b/3rdparty/freetype-2.13.2/src/cache/ftcglyph.c @@ -4,7 +4,7 @@ * * FreeType Glyph Image (FT_Glyph) cache (body). * - * Copyright (C) 2000-2020 by + * Copyright (C) 2000-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,11 +16,10 @@ */ -#include -#include FT_INTERNAL_OBJECTS_H -#include FT_CACHE_H +#include +#include #include "ftcglyph.h" -#include FT_ERRORS_H +#include #include "ftccback.h" #include "ftcerror.h" @@ -80,20 +79,6 @@ } -#ifdef FTC_INLINE - - FT_LOCAL_DEF( FT_Bool ) - FTC_GNode_Compare( FTC_GNode gnode, - FTC_GQuery gquery, - FTC_Cache cache, - FT_Bool* list_changed ) - { - return ftc_gnode_compare( FTC_NODE( gnode ), gquery, - cache, list_changed ); - } - -#endif - /*************************************************************************/ /*************************************************************************/ /***** *****/ @@ -116,22 +101,22 @@ FT_LOCAL_DEF( FT_Error ) - ftc_gcache_init( FTC_Cache ftccache ) + ftc_gcache_init( FTC_Cache cache ) { - FTC_GCache cache = (FTC_GCache)ftccache; + FTC_GCache gcache = (FTC_GCache)cache; FT_Error error; - error = FTC_Cache_Init( FTC_CACHE( cache ) ); + error = FTC_Cache_Init( cache ); if ( !error ) { - FTC_GCacheClass clazz = (FTC_GCacheClass)FTC_CACHE( cache )->org_class; + FTC_GCacheClass clazz = (FTC_GCacheClass)cache->org_class; - FTC_MruList_Init( &cache->families, + FTC_MruList_Init( &gcache->families, clazz->family_class, 0, /* no maximum here! */ cache, - FTC_CACHE( cache )->memory ); + cache->memory ); } return error; @@ -141,31 +126,31 @@ #if 0 FT_LOCAL_DEF( FT_Error ) - FTC_GCache_Init( FTC_GCache cache ) + FTC_GCache_Init( FTC_GCache gcache ) { - return ftc_gcache_init( FTC_CACHE( cache ) ); + return ftc_gcache_init( FTC_CACHE( gcache ) ); } #endif /* 0 */ FT_LOCAL_DEF( void ) - ftc_gcache_done( FTC_Cache ftccache ) + ftc_gcache_done( FTC_Cache cache ) { - FTC_GCache cache = (FTC_GCache)ftccache; + FTC_GCache gcache = (FTC_GCache)cache; - FTC_Cache_Done( (FTC_Cache)cache ); - FTC_MruList_Done( &cache->families ); + FTC_Cache_Done( cache ); + FTC_MruList_Done( &gcache->families ); } #if 0 FT_LOCAL_DEF( void ) - FTC_GCache_Done( FTC_GCache cache ) + FTC_GCache_Done( FTC_GCache gcache ) { - ftc_gcache_done( FTC_CACHE( cache ) ); + ftc_gcache_done( FTC_CACHE( gcache ) ); } #endif /* 0 */ @@ -184,7 +169,7 @@ #ifndef FTC_INLINE FT_LOCAL_DEF( FT_Error ) - FTC_GCache_Lookup( FTC_GCache cache, + FTC_GCache_Lookup( FTC_GCache gcache, FT_Offset hash, FT_UInt gindex, FTC_GQuery query, @@ -205,7 +190,7 @@ /* out-of-memory condition occurs during glyph node initialization. */ family->num_nodes++; - error = FTC_Cache_Lookup( FTC_CACHE( cache ), hash, query, anode ); + error = FTC_Cache_Lookup( FTC_CACHE( gcache ), hash, query, anode ); if ( --family->num_nodes == 0 ) FTC_FAMILY_FREE( family, cache ); diff --git a/src/font/freetype-2.10.2/src/cache/ftcglyph.h b/3rdparty/freetype-2.13.2/src/cache/ftcglyph.h similarity index 93% rename from src/font/freetype-2.10.2/src/cache/ftcglyph.h rename to 3rdparty/freetype-2.13.2/src/cache/ftcglyph.h index ef689f994..0181e9816 100644 --- a/src/font/freetype-2.10.2/src/cache/ftcglyph.h +++ b/3rdparty/freetype-2.13.2/src/cache/ftcglyph.h @@ -4,7 +4,7 @@ * * FreeType abstract glyph cache (specification). * - * Copyright (C) 2000-2020 by + * Copyright (C) 2000-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -58,7 +58,7 @@ * - FTC_GNode sub-class, e.g. MyNode, with relevant methods: * my_node_new (must call FTC_GNode_Init) * my_node_free (must call FTC_GNode_Done) - * my_node_compare (must call FTC_GNode_Compare) + * my_node_compare (must call ftc_gnode_compare) * my_node_remove_faceid (must call ftc_gnode_unselect in case * of match) * @@ -117,7 +117,6 @@ #define FTCGLYPH_H_ -#include #include "ftcmanag.h" @@ -141,8 +140,8 @@ FT_BEGIN_HEADER } FTC_FamilyRec, *FTC_Family; -#define FTC_FAMILY(x) ( (FTC_Family)(x) ) -#define FTC_FAMILY_P(x) ( (FTC_Family*)(x) ) +#define FTC_FAMILY( x ) ( (FTC_Family)(x) ) +#define FTC_FAMILY_P( x ) ( (FTC_Family*)(x) ) typedef struct FTC_GNodeRec_ @@ -180,19 +179,6 @@ FT_BEGIN_HEADER FT_UInt gindex, /* glyph index for node */ FTC_Family family ); -#ifdef FTC_INLINE - - /* returns TRUE iff the query's glyph index correspond to the node; */ - /* this assumes that the `family' and `hash' fields of the query are */ - /* already correctly set */ - FT_LOCAL( FT_Bool ) - FTC_GNode_Compare( FTC_GNode gnode, - FTC_GQuery gquery, - FTC_Cache cache, - FT_Bool* list_changed ); - -#endif - /* call this function to clear a node's family -- this is necessary */ /* to implement the `node_remove_faceid' cache method correctly */ FT_LOCAL( void ) @@ -246,7 +232,7 @@ FT_BEGIN_HEADER #define FTC_GCACHE_CLASS( x ) ((FTC_GCacheClass)(x)) #define FTC_CACHE_GCACHE_CLASS( x ) \ - FTC_GCACHE_CLASS( FTC_CACHE(x)->org_class ) + FTC_GCACHE_CLASS( FTC_CACHE( x )->org_class ) #define FTC_CACHE_FAMILY_CLASS( x ) \ ( (FTC_MruListClass)FTC_CACHE_GCACHE_CLASS( x )->family_class ) diff --git a/src/font/freetype-2.10.2/src/cache/ftcimage.c b/3rdparty/freetype-2.13.2/src/cache/ftcimage.c similarity index 94% rename from src/font/freetype-2.10.2/src/cache/ftcimage.c rename to 3rdparty/freetype-2.13.2/src/cache/ftcimage.c index 7696b2e52..428e5e1a7 100644 --- a/src/font/freetype-2.10.2/src/cache/ftcimage.c +++ b/3rdparty/freetype-2.13.2/src/cache/ftcimage.c @@ -4,7 +4,7 @@ * * FreeType Image cache (body). * - * Copyright (C) 2000-2020 by + * Copyright (C) 2000-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,11 +16,10 @@ */ -#include -#include FT_CACHE_H +#include #include "ftcimage.h" -#include FT_INTERNAL_MEMORY_H -#include FT_INTERNAL_OBJECTS_H +#include +#include #include "ftccback.h" #include "ftcerror.h" @@ -65,7 +64,7 @@ FTC_INode inode = NULL; - if ( !FT_NEW( inode ) ) + if ( !FT_QNEW( inode ) ) { FTC_GNode gnode = FTC_GNODE( inode ); FTC_Family family = gquery->family; @@ -75,6 +74,7 @@ /* initialize its inner fields */ FTC_GNode_Init( gnode, gindex, family ); + inode->glyph = NULL; /* we will now load the glyph image */ error = clazz->family_load_glyph( family, gindex, cache, diff --git a/src/font/freetype-2.10.2/src/cache/ftcimage.h b/3rdparty/freetype-2.13.2/src/cache/ftcimage.h similarity index 90% rename from src/font/freetype-2.10.2/src/cache/ftcimage.h rename to 3rdparty/freetype-2.13.2/src/cache/ftcimage.h index f99c5074c..d2a807f15 100644 --- a/src/font/freetype-2.10.2/src/cache/ftcimage.h +++ b/3rdparty/freetype-2.13.2/src/cache/ftcimage.h @@ -4,7 +4,7 @@ * * FreeType Generic Image cache (specification) * - * Copyright (C) 2000-2020 by + * Copyright (C) 2000-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -36,8 +36,7 @@ #define FTCIMAGE_H_ -#include -#include FT_CACHE_H +#include #include "ftcglyph.h" FT_BEGIN_HEADER @@ -52,8 +51,8 @@ FT_BEGIN_HEADER } FTC_INodeRec, *FTC_INode; #define FTC_INODE( x ) ( (FTC_INode)( x ) ) -#define FTC_INODE_GINDEX( x ) FTC_GNODE(x)->gindex -#define FTC_INODE_FAMILY( x ) FTC_GNODE(x)->family +#define FTC_INODE_GINDEX( x ) FTC_GNODE( x )->gindex +#define FTC_INODE_FAMILY( x ) FTC_GNODE( x )->family typedef FT_Error (*FTC_IFamily_LoadGlyphFunc)( FTC_Family family, @@ -73,7 +72,7 @@ FT_BEGIN_HEADER #define FTC_IFAMILY_CLASS( x ) ((FTC_IFamilyClass)(x)) #define FTC_CACHE_IFAMILY_CLASS( x ) \ - FTC_IFAMILY_CLASS( FTC_CACHE_GCACHE_CLASS(x)->family_class ) + FTC_IFAMILY_CLASS( FTC_CACHE_GCACHE_CLASS( x )->family_class ) /* can be used as a @FTC_Node_FreeFunc */ diff --git a/src/font/freetype-2.10.2/src/cache/ftcmanag.c b/3rdparty/freetype-2.13.2/src/cache/ftcmanag.c similarity index 92% rename from src/font/freetype-2.10.2/src/cache/ftcmanag.c rename to 3rdparty/freetype-2.13.2/src/cache/ftcmanag.c index a6f1733f6..94f8469c9 100644 --- a/src/font/freetype-2.10.2/src/cache/ftcmanag.c +++ b/3rdparty/freetype-2.13.2/src/cache/ftcmanag.c @@ -4,7 +4,7 @@ * * FreeType Cache Manager (body). * - * Copyright (C) 2000-2020 by + * Copyright (C) 2000-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,12 +16,11 @@ */ -#include -#include FT_CACHE_H +#include #include "ftcmanag.h" -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_DEBUG_H -#include FT_SIZES_H +#include +#include +#include #include "ftccback.h" #include "ftcerror.h" @@ -358,7 +357,7 @@ { FT_Error error; FT_Memory memory; - FTC_Manager manager = 0; + FTC_Manager manager = NULL; if ( !library ) @@ -369,7 +368,7 @@ memory = library->memory; - if ( FT_NEW( manager ) ) + if ( FT_QNEW( manager ) ) goto Exit; if ( max_faces == 0 ) @@ -384,6 +383,7 @@ manager->library = library; manager->memory = memory; manager->max_weight = max_bytes; + manager->cur_weight = 0; manager->request_face = requester; manager->request_data = req_data; @@ -400,6 +400,10 @@ manager, memory ); + manager->nodes_list = NULL; + manager->num_nodes = 0; + manager->num_caches = 0; + *amanager = manager; Exit: @@ -422,7 +426,7 @@ memory = manager->memory; /* now discard all caches */ - for (idx = manager->num_caches; idx-- > 0; ) + for ( idx = manager->num_caches; idx-- > 0; ) { FTC_Cache cache = manager->caches[idx]; @@ -485,8 +489,8 @@ FTC_Cache cache = manager->caches[node->cache_index]; - if ( (FT_UInt)node->cache_index >= manager->num_caches ) - FT_TRACE0(( "FTC_Manager_Check: invalid node (cache index = %ld\n", + if ( node->cache_index >= manager->num_caches ) + FT_TRACE0(( "FTC_Manager_Check: invalid node (cache index = %hu\n", node->cache_index )); else weight += cache->clazz.node_weight( node, cache ); @@ -516,7 +520,7 @@ if ( count != manager->num_nodes ) FT_TRACE0(( "FTC_Manager_Check:" - " invalid cache node count %d instead of %d\n", + " invalid cache node count %u instead of %u\n", manager->num_nodes, count )); } } @@ -533,7 +537,7 @@ FT_LOCAL_DEF( void ) FTC_Manager_Compress( FTC_Manager manager ) { - FTC_Node node, first; + FTC_Node node, prev, first; if ( !manager ) @@ -544,7 +548,7 @@ #ifdef FT_DEBUG_ERROR FTC_Manager_Check( manager ); - FT_TRACE0(( "compressing, weight = %ld, max = %ld, nodes = %d\n", + FT_TRACE0(( "compressing, weight = %ld, max = %ld, nodes = %u\n", manager->cur_weight, manager->max_weight, manager->num_nodes )); #endif @@ -553,20 +557,16 @@ return; /* go to last node -- it's a circular list */ - node = FTC_NODE_PREV( first ); + prev = FTC_NODE_PREV( first ); do { - FTC_Node prev; - - - prev = ( node == first ) ? NULL : FTC_NODE_PREV( node ); + node = prev; + prev = FTC_NODE_PREV( node ); if ( node->ref_count <= 0 ) ftc_node_destroy( node, manager ); - node = prev; - - } while ( node && manager->cur_weight > manager->max_weight ); + } while ( node != first && manager->cur_weight > manager->max_weight ); } @@ -594,7 +594,7 @@ goto Exit; } - if ( !FT_ALLOC( cache, clazz->cache_size ) ) + if ( !FT_QALLOC( cache, clazz->cache_size ) ) { cache->manager = manager; cache->memory = memory; @@ -629,20 +629,20 @@ FT_UInt count ) { FTC_Node first = manager->nodes_list; - FTC_Node node; - FT_UInt result; + FTC_Node prev, node; + FT_UInt result = 0; /* try to remove `count' nodes from the list */ - if ( !first ) /* empty list! */ - return 0; + if ( !first || !count ) + return result; - /* go to last node - it's a circular list */ - node = FTC_NODE_PREV(first); - for ( result = 0; result < count; ) + /* go to last node -- it's a circular list */ + prev = FTC_NODE_PREV( first ); + do { - FTC_Node prev = FTC_NODE_PREV( node ); - + node = prev; + prev = FTC_NODE_PREV( node ); /* don't touch locked nodes */ if ( node->ref_count <= 0 ) @@ -650,13 +650,9 @@ ftc_node_destroy( node, manager ); result++; } + } while ( node != first && result < count ); - if ( node == first ) - break; - - node = prev; - } - return result; + return result; } @@ -690,9 +686,9 @@ FTC_Node_Unref( FTC_Node node, FTC_Manager manager ) { - if ( node && - manager && - (FT_UInt)node->cache_index < manager->num_caches ) + if ( node && + manager && + node->cache_index < manager->num_caches ) node->ref_count--; } diff --git a/src/font/freetype-2.10.2/src/cache/ftcmanag.h b/3rdparty/freetype-2.13.2/src/cache/ftcmanag.h similarity index 98% rename from src/font/freetype-2.10.2/src/cache/ftcmanag.h rename to 3rdparty/freetype-2.13.2/src/cache/ftcmanag.h index 17ade7175..5b30929c9 100644 --- a/src/font/freetype-2.10.2/src/cache/ftcmanag.h +++ b/3rdparty/freetype-2.13.2/src/cache/ftcmanag.h @@ -4,7 +4,7 @@ * * FreeType Cache Manager (specification). * - * Copyright (C) 2000-2020 by + * Copyright (C) 2000-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -63,8 +63,7 @@ #define FTCMANAG_H_ -#include -#include FT_CACHE_H +#include #include "ftcmru.h" #include "ftccache.h" diff --git a/src/font/freetype-2.10.2/src/cache/ftcmru.c b/3rdparty/freetype-2.13.2/src/cache/ftcmru.c similarity index 91% rename from src/font/freetype-2.10.2/src/cache/ftcmru.c rename to 3rdparty/freetype-2.13.2/src/cache/ftcmru.c index 370ae3be0..ad10a06bc 100644 --- a/src/font/freetype-2.10.2/src/cache/ftcmru.c +++ b/3rdparty/freetype-2.13.2/src/cache/ftcmru.c @@ -4,7 +4,7 @@ * * FreeType MRU support (body). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,11 +16,10 @@ */ -#include -#include FT_CACHE_H +#include #include "ftcmru.h" -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_DEBUG_H +#include +#include #include "ftcerror.h" @@ -263,6 +262,8 @@ if ( list->clazz.node_done ) list->clazz.node_done( node, list->data ); } + + /* zero new node in case of node_init failure */ else if ( FT_ALLOC( node, list->clazz.node_size ) ) goto Exit; @@ -328,29 +329,23 @@ FTC_MruNode_CompareFunc selection, FT_Pointer key ) { - FTC_MruNode first, node, next; + FTC_MruNode first = list->nodes; + FTC_MruNode prev, node; - first = list->nodes; - while ( first && ( !selection || selection( first, key ) ) ) - { - FTC_MruList_Remove( list, first ); - first = list->nodes; - } + if ( !first || !selection ) + return; - if ( first ) + prev = first->prev; + do { - node = first->next; - while ( node != first ) - { - next = node->next; + node = prev; + prev = node->prev; - if ( selection( node, key ) ) - FTC_MruList_Remove( list, node ); + if ( selection( node, key ) ) + FTC_MruList_Remove( list, node ); - node = next; - } - } + } while ( node != first ); } diff --git a/src/font/freetype-2.10.2/src/cache/ftcmru.h b/3rdparty/freetype-2.13.2/src/cache/ftcmru.h similarity index 98% rename from src/font/freetype-2.10.2/src/cache/ftcmru.h rename to 3rdparty/freetype-2.13.2/src/cache/ftcmru.h index 1591c2080..45e5249ca 100644 --- a/src/font/freetype-2.10.2/src/cache/ftcmru.h +++ b/3rdparty/freetype-2.13.2/src/cache/ftcmru.h @@ -4,7 +4,7 @@ * * Simple MRU list-cache (specification). * - * Copyright (C) 2000-2020 by + * Copyright (C) 2000-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -44,8 +44,8 @@ #define FTCMRU_H_ -#include -#include FT_FREETYPE_H +#include +#include #ifdef FREETYPE_H #error "freetype.h of FreeType 1 has been loaded!" diff --git a/src/font/freetype-2.10.2/src/cache/ftcsbits.c b/3rdparty/freetype-2.13.2/src/cache/ftcsbits.c similarity index 88% rename from src/font/freetype-2.10.2/src/cache/ftcsbits.c rename to 3rdparty/freetype-2.13.2/src/cache/ftcsbits.c index 24e4aa131..9929a0bcc 100644 --- a/src/font/freetype-2.10.2/src/cache/ftcsbits.c +++ b/3rdparty/freetype-2.13.2/src/cache/ftcsbits.c @@ -4,7 +4,7 @@ * * FreeType sbits manager (body). * - * Copyright (C) 2000-2020 by + * Copyright (C) 2000-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,12 +16,11 @@ */ -#include -#include FT_CACHE_H +#include #include "ftcsbits.h" -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_DEBUG_H -#include FT_ERRORS_H +#include +#include +#include #include "ftccback.h" #include "ftcerror.h" @@ -53,10 +52,8 @@ pitch = -pitch; size = (FT_ULong)pitch * bitmap->rows; - if ( !size ) - return FT_Err_Ok; - if ( !FT_ALLOC( sbit->buffer, size ) ) + if ( !FT_QALLOC( sbit->buffer, size ) ) FT_MEM_COPY( sbit->buffer, bitmap->buffer, size ); return error; @@ -109,13 +106,12 @@ FT_Error error; FTC_GNode gnode = FTC_GNODE( snode ); FTC_Family family = gnode->family; - FT_Memory memory = manager->memory; FT_Face face; FTC_SBit sbit; FTC_SFamilyClass clazz; - if ( (FT_UInt)(gindex - gnode->gindex) >= snode->count ) + if ( gindex - gnode->gindex >= snode->count ) { FT_ERROR(( "ftc_snode_load: invalid glyph index" )); return FT_THROW( Invalid_Argument ); @@ -124,8 +120,6 @@ sbit = snode->sbits + ( gindex - gnode->gindex ); clazz = (FTC_SFamilyClass)family->clazz; - sbit->buffer = 0; - error = clazz->family_load_glyph( family, gindex, manager, &face ); if ( error ) goto BadGlyph; @@ -144,12 +138,13 @@ goto BadGlyph; } - /* Check whether our values fit into 8-bit containers! */ + /* Check whether our values fit into 8/16-bit containers! */ /* If this is not the case, our bitmap is too large */ /* and we will leave it as `missing' with sbit.buffer = 0 */ #define CHECK_CHAR( d ) ( temp = (FT_Char)d, (FT_Int) temp == (FT_Int) d ) #define CHECK_BYTE( d ) ( temp = (FT_Byte)d, (FT_UInt)temp == (FT_UInt)d ) +#define CHECK_SHRT( d ) ( temp = (FT_Short)d, (FT_Int)temp == (FT_Int) d ) /* horizontal advance in pixels */ xadvance = ( slot->advance.x + 32 ) >> 6; @@ -157,7 +152,7 @@ if ( !CHECK_BYTE( bitmap->rows ) || !CHECK_BYTE( bitmap->width ) || - !CHECK_CHAR( bitmap->pitch ) || + !CHECK_SHRT( bitmap->pitch ) || !CHECK_CHAR( slot->bitmap_left ) || !CHECK_CHAR( slot->bitmap_top ) || !CHECK_CHAR( xadvance ) || @@ -170,16 +165,25 @@ sbit->width = (FT_Byte)bitmap->width; sbit->height = (FT_Byte)bitmap->rows; - sbit->pitch = (FT_Char)bitmap->pitch; + sbit->pitch = (FT_Short)bitmap->pitch; sbit->left = (FT_Char)slot->bitmap_left; sbit->top = (FT_Char)slot->bitmap_top; sbit->xadvance = (FT_Char)xadvance; sbit->yadvance = (FT_Char)yadvance; sbit->format = (FT_Byte)bitmap->pixel_mode; - sbit->max_grays = (FT_Byte)(bitmap->num_grays - 1); + sbit->max_grays = (FT_Byte)( bitmap->num_grays - 1 ); - /* copy the bitmap into a new buffer -- ignore error */ - error = ftc_sbit_copy_bitmap( sbit, bitmap, memory ); + if ( slot->internal->flags & FT_GLYPH_OWN_BITMAP ) + { + /* take the bitmap ownership */ + sbit->buffer = bitmap->buffer; + slot->internal->flags &= ~FT_GLYPH_OWN_BITMAP; + } + else + { + /* copy the bitmap into a new buffer -- ignore error */ + error = ftc_sbit_copy_bitmap( sbit, bitmap, manager->memory ); + } /* now, compute size */ if ( asize ) @@ -229,7 +233,7 @@ goto Exit; } - if ( !FT_NEW( snode ) ) + if ( !FT_QNEW( snode ) ) { FT_UInt count, start; @@ -244,7 +248,9 @@ snode->count = count; for ( node_count = 0; node_count < count; node_count++ ) { - snode->sbits[node_count].width = 255; + snode->sbits[node_count].width = 255; + snode->sbits[node_count].height = 0; + snode->sbits[node_count].buffer = NULL; } error = ftc_snode_load( snode, @@ -336,10 +342,10 @@ FT_Bool result; - if (list_changed) + if ( list_changed ) *list_changed = FALSE; - result = FT_BOOL( gnode->family == gquery->family && - (FT_UInt)( gindex - gnode->gindex ) < snode->count ); + result = FT_BOOL( gnode->family == gquery->family && + gindex - gnode->gindex < snode->count ); if ( result ) { /* check if we need to load the glyph bitmap now */ @@ -391,7 +397,7 @@ { error = ftc_snode_load( snode, cache->manager, gindex, &size ); } - FTC_CACHE_TRYLOOP_END( list_changed ); + FTC_CACHE_TRYLOOP_END( list_changed ) ftcsnode->ref_count--; /* unlock the node */ @@ -405,19 +411,4 @@ return result; } - -#ifdef FTC_INLINE - - FT_LOCAL_DEF( FT_Bool ) - FTC_SNode_Compare( FTC_SNode snode, - FTC_GQuery gquery, - FTC_Cache cache, - FT_Bool* list_changed ) - { - return ftc_snode_compare( FTC_NODE( snode ), gquery, - cache, list_changed ); - } - -#endif - /* END */ diff --git a/src/font/freetype-2.10.2/src/cache/ftcsbits.h b/3rdparty/freetype-2.13.2/src/cache/ftcsbits.h similarity index 85% rename from src/font/freetype-2.10.2/src/cache/ftcsbits.h rename to 3rdparty/freetype-2.13.2/src/cache/ftcsbits.h index 2517d1555..e833cb5c3 100644 --- a/src/font/freetype-2.10.2/src/cache/ftcsbits.h +++ b/3rdparty/freetype-2.13.2/src/cache/ftcsbits.h @@ -4,7 +4,7 @@ * * A small-bitmap cache (specification). * - * Copyright (C) 2000-2020 by + * Copyright (C) 2000-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,8 +20,7 @@ #define FTCSBITS_H_ -#include -#include FT_CACHE_H +#include #include "ftcglyph.h" @@ -62,7 +61,7 @@ FT_BEGIN_HEADER typedef const FTC_SFamilyClassRec* FTC_SFamilyClass; -#define FTC_SFAMILY_CLASS( x ) ((FTC_SFamilyClass)(x)) +#define FTC_SFAMILY_CLASS( x ) ( (FTC_SFamilyClass)(x) ) #define FTC_CACHE_SFAMILY_CLASS( x ) \ FTC_SFAMILY_CLASS( FTC_CACHE_GCACHE_CLASS( x )->family_class ) @@ -82,17 +81,6 @@ FT_BEGIN_HEADER FTC_SNode_Weight( FTC_SNode inode ); #endif - -#ifdef FTC_INLINE - - FT_LOCAL( FT_Bool ) - FTC_SNode_Compare( FTC_SNode snode, - FTC_GQuery gquery, - FTC_Cache cache, - FT_Bool* list_changed); - -#endif - /* */ FT_END_HEADER diff --git a/src/font/freetype-2.10.2/src/cache/rules.mk b/3rdparty/freetype-2.13.2/src/cache/rules.mk similarity index 98% rename from src/font/freetype-2.10.2/src/cache/rules.mk rename to 3rdparty/freetype-2.13.2/src/cache/rules.mk index 4738b5153..82b39aa33 100644 --- a/src/font/freetype-2.10.2/src/cache/rules.mk +++ b/3rdparty/freetype-2.13.2/src/cache/rules.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 2000-2020 by +# Copyright (C) 2000-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, diff --git a/src/font/freetype-2.10.2/src/cff/cff.c b/3rdparty/freetype-2.13.2/src/cff/cff.c similarity index 93% rename from src/font/freetype-2.10.2/src/cff/cff.c rename to 3rdparty/freetype-2.13.2/src/cff/cff.c index 755228bb6..b486c389e 100644 --- a/src/font/freetype-2.10.2/src/cff/cff.c +++ b/3rdparty/freetype-2.13.2/src/cff/cff.c @@ -4,7 +4,7 @@ * * FreeType OpenType driver component (body only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -17,7 +17,6 @@ #define FT_MAKE_OPTION_SINGLE_OBJECT -#include #include "cffcmap.c" #include "cffdrivr.c" diff --git a/src/font/freetype-2.10.2/src/cff/cffcmap.c b/3rdparty/freetype-2.13.2/src/cff/cffcmap.c similarity index 64% rename from src/font/freetype-2.10.2/src/cff/cffcmap.c rename to 3rdparty/freetype-2.13.2/src/cff/cffcmap.c index 1a045765d..10d287bc8 100644 --- a/src/font/freetype-2.10.2/src/cff/cffcmap.c +++ b/3rdparty/freetype-2.13.2/src/cff/cffcmap.c @@ -4,7 +4,7 @@ * * CFF character mapping table (cmap) support (body). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,8 +16,7 @@ */ -#include -#include FT_INTERNAL_DEBUG_H +#include #include "cffcmap.h" #include "cffload.h" @@ -33,9 +32,10 @@ /*************************************************************************/ FT_CALLBACK_DEF( FT_Error ) - cff_cmap_encoding_init( CFF_CMapStd cmap, - FT_Pointer pointer ) + cff_cmap_encoding_init( FT_CMap cmap, + FT_Pointer pointer ) { + CFF_CMapStd cffcmap = (CFF_CMapStd)cmap; TT_Face face = (TT_Face)FT_CMAP_FACE( cmap ); CFF_Font cff = (CFF_Font)face->extra.data; CFF_Encoding encoding = &cff->encoding; @@ -43,63 +43,56 @@ FT_UNUSED( pointer ); - cmap->gids = encoding->codes; + cffcmap->gids = encoding->codes; return 0; } FT_CALLBACK_DEF( void ) - cff_cmap_encoding_done( CFF_CMapStd cmap ) + cff_cmap_encoding_done( FT_CMap cmap ) { - cmap->gids = NULL; + CFF_CMapStd cffcmap = (CFF_CMapStd)cmap; + + + cffcmap->gids = NULL; } FT_CALLBACK_DEF( FT_UInt ) - cff_cmap_encoding_char_index( CFF_CMapStd cmap, - FT_UInt32 char_code ) + cff_cmap_encoding_char_index( FT_CMap cmap, + FT_UInt32 char_code ) { - FT_UInt result = 0; + CFF_CMapStd cffcmap = (CFF_CMapStd)cmap; + FT_UInt result = 0; if ( char_code < 256 ) - result = cmap->gids[char_code]; + result = cffcmap->gids[char_code]; return result; } - FT_CALLBACK_DEF( FT_UInt32 ) - cff_cmap_encoding_char_next( CFF_CMapStd cmap, - FT_UInt32 *pchar_code ) + FT_CALLBACK_DEF( FT_UInt ) + cff_cmap_encoding_char_next( FT_CMap cmap, + FT_UInt32 *pchar_code ) { - FT_UInt result = 0; - FT_UInt32 char_code = *pchar_code; + CFF_CMapStd cffcmap = (CFF_CMapStd)cmap; + FT_UInt result = 0; + FT_UInt32 char_code = *pchar_code; - *pchar_code = 0; - - if ( char_code < 255 ) + while ( char_code < 255 ) { - FT_UInt code = (FT_UInt)(char_code + 1); - - - for (;;) + result = cffcmap->gids[++char_code]; + if ( result ) { - if ( code >= 256 ) - break; - - result = cmap->gids[code]; - if ( result != 0 ) - { - *pchar_code = code; - break; - } - - code++; + *pchar_code = char_code; + break; } } + return result; } @@ -131,9 +124,10 @@ /*************************************************************************/ FT_CALLBACK_DEF( const char* ) - cff_sid_to_glyph_name( TT_Face face, + cff_sid_to_glyph_name( void* face_, /* TT_Face */ FT_UInt idx ) { + TT_Face face = (TT_Face)face_; CFF_Font cff = (CFF_Font)face->extra.data; CFF_Charset charset = &cff->charset; FT_UInt sid = charset->sids[idx]; @@ -144,14 +138,15 @@ FT_CALLBACK_DEF( FT_Error ) - cff_cmap_unicode_init( PS_Unicodes unicodes, + cff_cmap_unicode_init( FT_CMap cmap, /* PS_Unicodes */ FT_Pointer pointer ) { - TT_Face face = (TT_Face)FT_CMAP_FACE( unicodes ); - FT_Memory memory = FT_FACE_MEMORY( face ); - CFF_Font cff = (CFF_Font)face->extra.data; - CFF_Charset charset = &cff->charset; - FT_Service_PsCMaps psnames = (FT_Service_PsCMaps)cff->psnames; + PS_Unicodes unicodes = (PS_Unicodes)cmap; + TT_Face face = (TT_Face)FT_CMAP_FACE( cmap ); + FT_Memory memory = FT_FACE_MEMORY( face ); + CFF_Font cff = (CFF_Font)face->extra.data; + CFF_Charset charset = &cff->charset; + FT_Service_PsCMaps psnames = (FT_Service_PsCMaps)cff->psnames; FT_UNUSED( pointer ); @@ -167,17 +162,18 @@ return psnames->unicodes_init( memory, unicodes, cff->num_glyphs, - (PS_GetGlyphNameFunc)&cff_sid_to_glyph_name, + &cff_sid_to_glyph_name, (PS_FreeGlyphNameFunc)NULL, (FT_Pointer)face ); } FT_CALLBACK_DEF( void ) - cff_cmap_unicode_done( PS_Unicodes unicodes ) + cff_cmap_unicode_done( FT_CMap cmap ) /* PS_Unicodes */ { - FT_Face face = FT_CMAP_FACE( unicodes ); - FT_Memory memory = FT_FACE_MEMORY( face ); + PS_Unicodes unicodes = (PS_Unicodes)cmap; + FT_Face face = FT_CMAP_FACE( cmap ); + FT_Memory memory = FT_FACE_MEMORY( face ); FT_FREE( unicodes->maps ); @@ -186,25 +182,27 @@ FT_CALLBACK_DEF( FT_UInt ) - cff_cmap_unicode_char_index( PS_Unicodes unicodes, - FT_UInt32 char_code ) + cff_cmap_unicode_char_index( FT_CMap cmap, /* PS_Unicodes */ + FT_UInt32 char_code ) { - TT_Face face = (TT_Face)FT_CMAP_FACE( unicodes ); - CFF_Font cff = (CFF_Font)face->extra.data; - FT_Service_PsCMaps psnames = (FT_Service_PsCMaps)cff->psnames; + PS_Unicodes unicodes = (PS_Unicodes)cmap; + TT_Face face = (TT_Face)FT_CMAP_FACE( cmap ); + CFF_Font cff = (CFF_Font)face->extra.data; + FT_Service_PsCMaps psnames = (FT_Service_PsCMaps)cff->psnames; return psnames->unicodes_char_index( unicodes, char_code ); } - FT_CALLBACK_DEF( FT_UInt32 ) - cff_cmap_unicode_char_next( PS_Unicodes unicodes, - FT_UInt32 *pchar_code ) + FT_CALLBACK_DEF( FT_UInt ) + cff_cmap_unicode_char_next( FT_CMap cmap, /* PS_Unicodes */ + FT_UInt32 *pchar_code ) { - TT_Face face = (TT_Face)FT_CMAP_FACE( unicodes ); - CFF_Font cff = (CFF_Font)face->extra.data; - FT_Service_PsCMaps psnames = (FT_Service_PsCMaps)cff->psnames; + PS_Unicodes unicodes = (PS_Unicodes)cmap; + TT_Face face = (TT_Face)FT_CMAP_FACE( cmap ); + CFF_Font cff = (CFF_Font)face->extra.data; + FT_Service_PsCMaps psnames = (FT_Service_PsCMaps)cff->psnames; return psnames->unicodes_char_next( unicodes, pchar_code ); diff --git a/src/font/freetype-2.10.2/src/cff/cffcmap.h b/3rdparty/freetype-2.13.2/src/cff/cffcmap.h similarity index 91% rename from src/font/freetype-2.10.2/src/cff/cffcmap.h rename to 3rdparty/freetype-2.13.2/src/cff/cffcmap.h index 319be8824..b2afc2fab 100644 --- a/src/font/freetype-2.10.2/src/cff/cffcmap.h +++ b/3rdparty/freetype-2.13.2/src/cff/cffcmap.h @@ -4,7 +4,7 @@ * * CFF character mapping table (cmap) support (specification). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,7 +19,7 @@ #ifndef CFFCMAP_H_ #define CFFCMAP_H_ -#include FT_INTERNAL_CFF_OBJECTS_TYPES_H +#include FT_BEGIN_HEADER @@ -43,7 +43,7 @@ FT_BEGIN_HEADER } CFF_CMapStdRec; - FT_DECLARE_CMAP_CLASS(cff_cmap_encoding_class_rec) + FT_DECLARE_CMAP_CLASS( cff_cmap_encoding_class_rec ) /*************************************************************************/ @@ -56,7 +56,7 @@ FT_BEGIN_HEADER /* unicode (synthetic) cmaps */ - FT_DECLARE_CMAP_CLASS(cff_cmap_unicode_class_rec) + FT_DECLARE_CMAP_CLASS( cff_cmap_unicode_class_rec ) FT_END_HEADER diff --git a/src/font/freetype-2.10.2/src/cff/cffdrivr.c b/3rdparty/freetype-2.13.2/src/cff/cffdrivr.c similarity index 61% rename from src/font/freetype-2.10.2/src/cff/cffdrivr.c rename to 3rdparty/freetype-2.13.2/src/cff/cffdrivr.c index 6d0dcd09d..9898d625c 100644 --- a/src/font/freetype-2.10.2/src/cff/cffdrivr.c +++ b/3rdparty/freetype-2.13.2/src/cff/cffdrivr.c @@ -4,8 +4,8 @@ * * OpenType font driver implementation (body). * - * Copyright (C) 1996-2020 by - * David Turner, Robert Wilhelm, and Werner Lemberg. + * Copyright (C) 1996-2023 by + * David Turner, Robert Wilhelm, Werner Lemberg, and Dominik Röttsches. * * This file is part of the FreeType project, and may only be used, * modified, and distributed under the terms of the FreeType project @@ -16,18 +16,17 @@ */ -#include -#include FT_FREETYPE_H -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_STREAM_H -#include FT_INTERNAL_SFNT_H -#include FT_INTERNAL_POSTSCRIPT_AUX_H -#include FT_INTERNAL_POSTSCRIPT_PROPS_H -#include FT_SERVICE_CID_H -#include FT_SERVICE_POSTSCRIPT_INFO_H -#include FT_SERVICE_POSTSCRIPT_NAME_H -#include FT_SERVICE_TT_CMAP_H -#include FT_SERVICE_CFF_TABLE_LOAD_H +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include #include "cffdrivr.h" #include "cffgload.h" @@ -37,16 +36,16 @@ #include "cffobjs.h" #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT -#include FT_SERVICE_MULTIPLE_MASTERS_H -#include FT_SERVICE_METRICS_VARIATIONS_H +#include +#include #endif #include "cfferrs.h" -#include FT_SERVICE_FONT_FORMAT_H -#include FT_SERVICE_GLYPH_DICT_H -#include FT_SERVICE_PROPERTIES_H -#include FT_DRIVER_H +#include +#include +#include +#include /************************************************************************** @@ -109,20 +108,20 @@ * They can be implemented by format-specific interfaces. */ FT_CALLBACK_DEF( FT_Error ) - cff_get_kerning( FT_Face ttface, /* TT_Face */ + cff_get_kerning( FT_Face face, /* CFF_Face */ FT_UInt left_glyph, FT_UInt right_glyph, FT_Vector* kerning ) { - TT_Face face = (TT_Face)ttface; - SFNT_Service sfnt = (SFNT_Service)face->sfnt; + CFF_Face cffface = (CFF_Face)face; + SFNT_Service sfnt = (SFNT_Service)cffface->sfnt; kerning->x = 0; kerning->y = 0; if ( sfnt ) - kerning->x = sfnt->get_kerning( face, left_glyph, right_glyph ); + kerning->x = sfnt->get_kerning( cffface, left_glyph, right_glyph ); return FT_Err_Ok; } @@ -159,23 +158,23 @@ * FreeType error code. 0 means success. */ FT_CALLBACK_DEF( FT_Error ) - cff_glyph_load( FT_GlyphSlot cffslot, /* CFF_GlyphSlot */ - FT_Size cffsize, /* CFF_Size */ + cff_glyph_load( FT_GlyphSlot slot, /* CFF_GlyphSlot */ + FT_Size size, /* CFF_Size */ FT_UInt glyph_index, FT_Int32 load_flags ) { FT_Error error; - CFF_GlyphSlot slot = (CFF_GlyphSlot)cffslot; - CFF_Size size = (CFF_Size)cffsize; + CFF_GlyphSlot cffslot = (CFF_GlyphSlot)slot; + CFF_Size cffsize = (CFF_Size)size; - if ( !slot ) + if ( !cffslot ) return FT_THROW( Invalid_Slot_Handle ); FT_TRACE1(( "cff_glyph_load: glyph index %d\n", glyph_index )); /* check whether we want a scaled outline or bitmap */ - if ( !size ) + if ( !cffsize ) load_flags |= FT_LOAD_NO_SCALE | FT_LOAD_NO_HINTING; /* reset the size object if necessary */ @@ -185,12 +184,12 @@ if ( size ) { /* these two objects must have the same parent */ - if ( cffsize->face != cffslot->face ) + if ( size->face != slot->face ) return FT_THROW( Invalid_Face_Handle ); } /* now load the glyph outline if necessary */ - error = cff_slot_load( slot, size, glyph_index, load_flags ); + error = cff_slot_load( cffslot, cffsize, glyph_index, load_flags ); /* force drop-out mode to 2 - irrelevant now */ /* slot->outline.dropout_mode = 2; */ @@ -217,7 +216,7 @@ /* it is no longer necessary that those values are identical to */ /* the values in the `CFF' table */ - TT_Face ttface = (TT_Face)face; + CFF_Face cffface = (CFF_Face)face; FT_Short dummy; @@ -226,7 +225,7 @@ #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT /* no fast retrieval for blended MM fonts without VVAR table */ if ( ( FT_IS_NAMED_INSTANCE( face ) || FT_IS_VARIATION( face ) ) && - !( ttface->variation_support & TT_FACE_FLAG_VAR_VADVANCE ) ) + !( cffface->variation_support & TT_FACE_FLAG_VAR_VADVANCE ) ) return FT_THROW( Unimplemented_Feature ); #endif @@ -234,7 +233,7 @@ /* otherwise we extract the info from the CFF glyphstrings */ /* (instead of synthesizing a global value using the `OS/2' */ /* table) */ - if ( !ttface->vertical_info ) + if ( !cffface->vertical_info ) goto Missing_Table; for ( nn = 0; nn < count; nn++ ) @@ -242,11 +241,11 @@ FT_UShort ah; - ( (SFNT_Service)ttface->sfnt )->get_metrics( ttface, - 1, - start + nn, - &dummy, - &ah ); + ( (SFNT_Service)cffface->sfnt )->get_metrics( cffface, + 1, + start + nn, + &dummy, + &ah ); FT_TRACE5(( " idx %d: advance height %d font unit%s\n", start + nn, @@ -260,12 +259,12 @@ #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT /* no fast retrieval for blended MM fonts without HVAR table */ if ( ( FT_IS_NAMED_INSTANCE( face ) || FT_IS_VARIATION( face ) ) && - !( ttface->variation_support & TT_FACE_FLAG_VAR_HADVANCE ) ) + !( cffface->variation_support & TT_FACE_FLAG_VAR_HADVANCE ) ) return FT_THROW( Unimplemented_Feature ); #endif /* check whether we have data from the `hmtx' table at all */ - if ( !ttface->horizontal.number_Of_HMetrics ) + if ( !cffface->horizontal.number_Of_HMetrics ) goto Missing_Table; for ( nn = 0; nn < count; nn++ ) @@ -273,11 +272,11 @@ FT_UShort aw; - ( (SFNT_Service)ttface->sfnt )->get_metrics( ttface, - 0, - start + nn, - &dummy, - &aw ); + ( (SFNT_Service)cffface->sfnt )->get_metrics( cffface, + 0, + start + nn, + &dummy, + &aw ); FT_TRACE5(( " idx %d: advance width %d font unit%s\n", start + nn, @@ -313,13 +312,14 @@ * */ - static FT_Error - cff_get_glyph_name( CFF_Face face, + FT_CALLBACK_DEF( FT_Error ) + cff_get_glyph_name( FT_Face face, /* CFF_Face */ FT_UInt glyph_index, FT_Pointer buffer, FT_UInt buffer_max ) { - CFF_Font font = (CFF_Font)face->extra.data; + CFF_Face cffface = (CFF_Face)face; + CFF_Font font = (CFF_Font)cffface->extra.data; FT_String* gname; FT_UShort sid; FT_Error error; @@ -339,15 +339,12 @@ if ( service && service->get_name ) - return service->get_name( FT_FACE( face ), - glyph_index, - buffer, - buffer_max ); + return service->get_name( face, glyph_index, buffer, buffer_max ); else { FT_ERROR(( "cff_get_glyph_name:" - " cannot get glyph name from a CFF2 font\n" - " " + " cannot get glyph name from a CFF2 font\n" )); + FT_ERROR(( " " " without the `psnames' module\n" )); error = FT_THROW( Missing_Module ); goto Exit; @@ -357,8 +354,8 @@ if ( !font->psnames ) { FT_ERROR(( "cff_get_glyph_name:" - " cannot get glyph name from CFF & CEF fonts\n" - " " + " cannot get glyph name from CFF & CEF fonts\n" )); + FT_ERROR(( " " " without the `psnames' module\n" )); error = FT_THROW( Missing_Module ); goto Exit; @@ -367,7 +364,7 @@ /* first, locate the sid in the charset table */ sid = font->charset.sids[glyph_index]; - /* now, lookup the name itself */ + /* now, look up the name itself */ gname = cff_index_get_sid_string( font, sid ); if ( gname ) @@ -380,21 +377,19 @@ } - static FT_UInt - cff_get_name_index( CFF_Face face, + FT_CALLBACK_DEF( FT_UInt ) + cff_get_name_index( FT_Face face, /* CFF_Face */ const FT_String* glyph_name ) { - CFF_Font cff; - CFF_Charset charset; + CFF_Face cffface = (CFF_Face)face; + CFF_Font cff = (CFF_Font)cffface->extra.data; + CFF_Charset charset = &cff->charset; FT_Service_PsCMaps psnames; FT_String* name; FT_UShort sid; FT_UInt i; - cff = (CFF_FontRec *)face->extra.data; - charset = &cff->charset; - /* CFF2 table does not have glyph names; */ /* we need to use `post' table method */ if ( cff->version_major == 2 ) @@ -409,12 +404,12 @@ if ( service && service->name_index ) - return service->name_index( FT_FACE( face ), glyph_name ); + return service->name_index( face, glyph_name ); else { FT_ERROR(( "cff_get_name_index:" - " cannot get glyph index from a CFF2 font\n" - " " + " cannot get glyph index from a CFF2 font\n" )); + FT_ERROR(( " " " without the `psnames' module\n" )); return 0; } @@ -447,8 +442,8 @@ FT_DEFINE_SERVICE_GLYPHDICTREC( cff_service_glyph_dict, - (FT_GlyphDict_GetNameFunc) cff_get_glyph_name, /* get_name */ - (FT_GlyphDict_NameIndexFunc)cff_get_name_index /* name_index */ + cff_get_glyph_name, /* FT_GlyphDict_GetNameFunc get_name */ + cff_get_name_index /* FT_GlyphDict_NameIndexFunc name_index */ ) @@ -457,29 +452,36 @@ * */ - static FT_Int + FT_CALLBACK_DEF( FT_Int ) cff_ps_has_glyph_names( FT_Face face ) { return ( face->face_flags & FT_FACE_FLAG_GLYPH_NAMES ) > 0; } - static FT_Error - cff_ps_get_font_info( CFF_Face face, + FT_CALLBACK_DEF( FT_Error ) + cff_ps_get_font_info( FT_Face face, /* CFF_Face */ PS_FontInfoRec* afont_info ) { - CFF_Font cff = (CFF_Font)face->extra.data; - FT_Error error = FT_Err_Ok; + CFF_Face cffface = (CFF_Face)face; + CFF_Font cff = (CFF_Font)cffface->extra.data; + FT_Error error = FT_Err_Ok; + if ( cffface->is_cff2 ) + { + error = FT_THROW( Invalid_Argument ); + goto Fail; + } + if ( cff && !cff->font_info ) { CFF_FontRecDict dict = &cff->top_font.font_dict; - PS_FontInfoRec *font_info = NULL; - FT_Memory memory = face->root.memory; + FT_Memory memory = FT_FACE_MEMORY( face ); + PS_FontInfoRec* font_info = NULL; - if ( FT_ALLOC( font_info, sizeof ( *font_info ) ) ) + if ( FT_QNEW( font_info ) ) goto Fail; font_info->version = cff_index_get_sid_string( cff, @@ -508,23 +510,24 @@ } - static FT_Error - cff_ps_get_font_extra( CFF_Face face, + FT_CALLBACK_DEF( FT_Error ) + cff_ps_get_font_extra( FT_Face face, /* CFF_Face */ PS_FontExtraRec* afont_extra ) { - CFF_Font cff = (CFF_Font)face->extra.data; - FT_Error error = FT_Err_Ok; + CFF_Face cffface = (CFF_Face)face; + CFF_Font cff = (CFF_Font)cffface->extra.data; + FT_Error error = FT_Err_Ok; - if ( cff && cff->font_extra == NULL ) + if ( cff && !cff->font_extra ) { CFF_FontRecDict dict = &cff->top_font.font_dict; + FT_Memory memory = FT_FACE_MEMORY( face ); PS_FontExtraRec* font_extra = NULL; - FT_Memory memory = face->root.memory; FT_String* embedded_postscript; - if ( FT_ALLOC( font_extra, sizeof ( *font_extra ) ) ) + if ( FT_QNEW( font_extra ) ) goto Fail; font_extra->fs_type = 0U; @@ -589,13 +592,13 @@ FT_DEFINE_SERVICE_PSINFOREC( cff_service_ps_info, - (PS_GetFontInfoFunc) cff_ps_get_font_info, /* ps_get_font_info */ - (PS_GetFontExtraFunc) cff_ps_get_font_extra, /* ps_get_font_extra */ - (PS_HasGlyphNamesFunc) cff_ps_has_glyph_names, /* ps_has_glyph_names */ + cff_ps_get_font_info, /* PS_GetFontInfoFunc ps_get_font_info */ + cff_ps_get_font_extra, /* PS_GetFontExtraFunc ps_get_font_extra */ + cff_ps_has_glyph_names, /* PS_HasGlyphNamesFunc ps_has_glyph_names */ /* unsupported with CFF fonts */ - (PS_GetFontPrivateFunc)NULL, /* ps_get_font_private */ + NULL, /* PS_GetFontPrivateFunc ps_get_font_private */ /* not implemented */ - (PS_GetFontValueFunc) NULL /* ps_get_font_value */ + NULL /* PS_GetFontValueFunc ps_get_font_value */ ) @@ -604,17 +607,18 @@ * */ - static const char* - cff_get_ps_name( CFF_Face face ) + FT_CALLBACK_DEF( const char* ) + cff_get_ps_name( FT_Face face ) /* CFF_Face */ { - CFF_Font cff = (CFF_Font)face->extra.data; - SFNT_Service sfnt = (SFNT_Service)face->sfnt; + CFF_Face cffface = (CFF_Face)face; + CFF_Font cff = (CFF_Font)cffface->extra.data; + SFNT_Service sfnt = (SFNT_Service)cffface->sfnt; /* following the OpenType specification 1.7, we return the name stored */ /* in the `name' table for a CFF wrapped into an SFNT container */ - if ( FT_IS_SFNT( FT_FACE( face ) ) && sfnt ) + if ( FT_IS_SFNT( face ) && sfnt ) { FT_Library library = FT_FACE_LIBRARY( face ); FT_Module sfnt_module = FT_Get_Module( library, "sfnt" ); @@ -626,17 +630,17 @@ if ( service && service->get_ps_font_name ) - return service->get_ps_font_name( FT_FACE( face ) ); + return service->get_ps_font_name( face ); } - return (const char*)cff->font_name; + return cff ? (const char*)cff->font_name : NULL; } FT_DEFINE_SERVICE_PSFONTNAMEREC( cff_service_ps_name, - (FT_PsName_GetFunc)cff_get_ps_name /* get_ps_font_name */ + cff_get_ps_name /* FT_PsName_GetFunc get_ps_font_name */ ) @@ -650,7 +654,7 @@ * Otherwise call the service function in the sfnt module. * */ - static FT_Error + FT_CALLBACK_DEF( FT_Error ) cff_get_cmap_info( FT_CharMap charmap, TT_CMapInfo *cmap_info ) { @@ -684,7 +688,7 @@ FT_DEFINE_SERVICE_TTCMAPSREC( cff_service_get_cmap_info, - (TT_CMap_Info_GetFunc)cff_get_cmap_info /* get_cmap_info */ + cff_get_cmap_info /* TT_CMap_Info_GetFunc get_cmap_info */ ) @@ -692,14 +696,15 @@ * CID INFO SERVICE * */ - static FT_Error - cff_get_ros( CFF_Face face, + FT_CALLBACK_DEF( FT_Error ) + cff_get_ros( FT_Face face, /* FT_Face */ const char* *registry, const char* *ordering, FT_Int *supplement ) { - FT_Error error = FT_Err_Ok; - CFF_Font cff = (CFF_Font)face->extra.data; + FT_Error error = FT_Err_Ok; + CFF_Face cffface = (CFF_Face)face; + CFF_Font cff = (CFF_Font)cffface->extra.data; if ( cff ) @@ -738,7 +743,7 @@ { if ( dict->cid_supplement < FT_INT_MIN || dict->cid_supplement > FT_INT_MAX ) - FT_TRACE1(( "cff_get_ros: too large supplement %d is truncated\n", + FT_TRACE1(( "cff_get_ros: too large supplement %ld is truncated\n", dict->cid_supplement )); *supplement = (FT_Int)dict->cid_supplement; } @@ -749,12 +754,13 @@ } - static FT_Error - cff_get_is_cid( CFF_Face face, + FT_CALLBACK_DEF( FT_Error ) + cff_get_is_cid( FT_Face face, /* CFF_Face */ FT_Bool *is_cid ) { - FT_Error error = FT_Err_Ok; - CFF_Font cff = (CFF_Font)face->extra.data; + FT_Error error = FT_Err_Ok; + CFF_Face cffface = (CFF_Face)face; + CFF_Font cff = (CFF_Font)cffface->extra.data; *is_cid = 0; @@ -772,17 +778,16 @@ } - static FT_Error - cff_get_cid_from_glyph_index( CFF_Face face, + FT_CALLBACK_DEF( FT_Error ) + cff_get_cid_from_glyph_index( FT_Face face, /* CFF_Face */ FT_UInt glyph_index, FT_UInt *cid ) { - FT_Error error = FT_Err_Ok; - CFF_Font cff; + FT_Error error = FT_Err_Ok; + CFF_Face cffface = (CFF_Face)face; + CFF_Font cff = (CFF_Font)cffface->extra.data; - cff = (CFF_Font)face->extra.data; - if ( cff ) { FT_UInt c; @@ -815,12 +820,12 @@ FT_DEFINE_SERVICE_CIDREC( cff_service_cid_info, - (FT_CID_GetRegistryOrderingSupplementFunc) - cff_get_ros, /* get_ros */ - (FT_CID_GetIsInternallyCIDKeyedFunc) - cff_get_is_cid, /* get_is_cid */ - (FT_CID_GetCIDFromGlyphIndexFunc) - cff_get_cid_from_glyph_index /* get_cid_from_glyph_index */ + cff_get_ros, + /* FT_CID_GetRegistryOrderingSupplementFunc get_ros */ + cff_get_is_cid, + /* FT_CID_GetIsInternallyCIDKeyedFunc get_is_cid */ + cff_get_cid_from_glyph_index + /* FT_CID_GetCIDFromGlyphIndexFunc get_cid_from_glyph_index */ ) @@ -832,9 +837,9 @@ FT_DEFINE_SERVICE_PROPERTIESREC( cff_service_properties, - (FT_Properties_SetFunc)ps_property_set, /* set_property */ - (FT_Properties_GetFunc)ps_property_get ) /* get_property */ - + ps_property_set, /* FT_Properties_SetFunc set_property */ + ps_property_get /* FT_Properties_GetFunc get_property */ + ) #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT @@ -843,116 +848,231 @@ * */ - static FT_Error - cff_set_mm_blend( CFF_Face face, + FT_CALLBACK_DEF( FT_Error ) + cff_set_mm_blend( FT_Face face, /* CFF_Face */ FT_UInt num_coords, FT_Fixed* coords ) { - FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm; + CFF_Face cffface = (CFF_Face)face; + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)cffface->mm; - return mm->set_mm_blend( FT_FACE( face ), num_coords, coords ); + return mm->set_mm_blend( face, num_coords, coords ); } - static FT_Error - cff_get_mm_blend( CFF_Face face, + FT_CALLBACK_DEF( FT_Error ) + cff_get_mm_blend( FT_Face face, /* CFF_Face */ FT_UInt num_coords, FT_Fixed* coords ) { - FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm; + CFF_Face cffface = (CFF_Face)face; + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)cffface->mm; - return mm->get_mm_blend( FT_FACE( face ), num_coords, coords ); + return mm->get_mm_blend( face, num_coords, coords ); } - static FT_Error - cff_set_mm_weightvector( CFF_Face face, + FT_CALLBACK_DEF( FT_Error ) + cff_set_mm_weightvector( FT_Face face, /* CFF_Face */ FT_UInt len, FT_Fixed* weightvector ) { - FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm; + CFF_Face cffface = (CFF_Face)face; + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)cffface->mm; - return mm->set_mm_weightvector( FT_FACE( face ), len, weightvector ); + return mm->set_mm_weightvector( face, len, weightvector ); } - static FT_Error - cff_get_mm_weightvector( CFF_Face face, + FT_CALLBACK_DEF( FT_Error ) + cff_get_mm_weightvector( FT_Face face, /* CFF_Face */ FT_UInt* len, FT_Fixed* weightvector ) { - FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm; + CFF_Face cffface = (CFF_Face)face; + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)cffface->mm; - return mm->get_mm_weightvector( FT_FACE( face ), len, weightvector ); + return mm->get_mm_weightvector( face, len, weightvector ); } - static FT_Error - cff_get_mm_var( CFF_Face face, + FT_CALLBACK_DEF( void ) + cff_construct_ps_name( FT_Face face ) /* CFF_Face */ + { + CFF_Face cffface = (CFF_Face)face; + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)cffface->mm; + + + mm->construct_ps_name( face ); + } + + + FT_CALLBACK_DEF( FT_Error ) + cff_get_mm_var( FT_Face face, /* CFF_Face */ FT_MM_Var* *master ) { - FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm; + CFF_Face cffface = (CFF_Face)face; + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)cffface->mm; - return mm->get_mm_var( FT_FACE( face ), master ); + return mm->get_mm_var( face, master ); } - static FT_Error - cff_set_var_design( CFF_Face face, + FT_CALLBACK_DEF( FT_Error ) + cff_set_var_design( FT_Face face, /* CFF_Face */ FT_UInt num_coords, FT_Fixed* coords ) { - FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm; + CFF_Face cffface = (CFF_Face)face; + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)cffface->mm; - return mm->set_var_design( FT_FACE( face ), num_coords, coords ); + return mm->set_var_design( face, num_coords, coords ); } - static FT_Error - cff_get_var_design( CFF_Face face, + FT_CALLBACK_DEF( FT_Error ) + cff_get_var_design( FT_Face face, /* CFF_Face */ FT_UInt num_coords, FT_Fixed* coords ) { - FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm; + CFF_Face cffface = (CFF_Face)face; + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)cffface->mm; + + + return mm->get_var_design( face, num_coords, coords ); + } + + + FT_CALLBACK_DEF( FT_Error ) + cff_set_named_instance( FT_Face face, /* CFF_Face */ + FT_UInt instance_index ) + { + CFF_Face cffface = (CFF_Face)face; + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)cffface->mm; + + + return mm->set_named_instance( face, instance_index ); + } + + + FT_CALLBACK_DEF( FT_Error ) + cff_get_default_named_instance( FT_Face face, /* CFF_Face */ + FT_UInt *instance_index ) + { + CFF_Face cffface = (CFF_Face)face; + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)cffface->mm; - return mm->get_var_design( FT_FACE( face ), num_coords, coords ); + return mm->get_default_named_instance( face, instance_index ); } - static FT_Error - cff_set_instance( CFF_Face face, - FT_UInt instance_index ) + FT_CALLBACK_DEF( FT_Error ) + cff_load_item_variation_store( FT_Face face, /* CFF_Face */ + FT_ULong offset, + GX_ItemVarStore itemStore ) { - FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm; + CFF_Face cffface = (CFF_Face)face; + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)cffface->mm; - return mm->set_instance( FT_FACE( face ), instance_index ); + return mm->load_item_var_store( face, offset, itemStore ); } + FT_CALLBACK_DEF( FT_Error ) + cff_load_delta_set_index_mapping( FT_Face face, /* CFF_Face */ + FT_ULong offset, + GX_DeltaSetIdxMap map, + GX_ItemVarStore itemStore, + FT_ULong table_len ) + { + CFF_Face cffface = (CFF_Face)face; + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)cffface->mm; + + + return mm->load_delta_set_idx_map( face, offset, map, + itemStore, table_len ); + } + + + FT_CALLBACK_DEF( FT_Int ) + cff_get_item_delta( FT_Face face, /* CFF_Face */ + GX_ItemVarStore itemStore, + FT_UInt outerIndex, + FT_UInt innerIndex ) + { + CFF_Face cffface = (CFF_Face)face; + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)cffface->mm; + + + return mm->get_item_delta( face, itemStore, outerIndex, innerIndex ); + } + + + FT_CALLBACK_DEF( void ) + cff_done_item_variation_store( FT_Face face, /* CFF_Face */ + GX_ItemVarStore itemStore ) + { + CFF_Face cffface = (CFF_Face)face; + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)cffface->mm; + + + mm->done_item_var_store( face, itemStore ); + } + + + FT_CALLBACK_DEF( void ) + cff_done_delta_set_index_map( FT_Face face, /* CFF_Face */ + GX_DeltaSetIdxMap deltaSetIdxMap ) + { + CFF_Face cffface = (CFF_Face)face; + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)cffface->mm; + + + mm->done_delta_set_idx_map( face, deltaSetIdxMap ); + } + + + FT_DEFINE_SERVICE_MULTIMASTERSREC( cff_service_multi_masters, - (FT_Get_MM_Func) NULL, /* get_mm */ - (FT_Set_MM_Design_Func) NULL, /* set_mm_design */ - (FT_Set_MM_Blend_Func) cff_set_mm_blend, /* set_mm_blend */ - (FT_Get_MM_Blend_Func) cff_get_mm_blend, /* get_mm_blend */ - (FT_Get_MM_Var_Func) cff_get_mm_var, /* get_mm_var */ - (FT_Set_Var_Design_Func) cff_set_var_design, /* set_var_design */ - (FT_Get_Var_Design_Func) cff_get_var_design, /* get_var_design */ - (FT_Set_Instance_Func) cff_set_instance, /* set_instance */ - (FT_Set_MM_WeightVector_Func)cff_set_mm_weightvector, /* set_mm_weightvector */ - (FT_Get_MM_WeightVector_Func)cff_get_mm_weightvector, /* get_mm_weightvector */ - - (FT_Get_Var_Blend_Func) cff_get_var_blend, /* get_var_blend */ - (FT_Done_Blend_Func) cff_done_blend /* done_blend */ + NULL, /* FT_Get_MM_Func get_mm */ + NULL, /* FT_Set_MM_Design_Func set_mm_design */ + cff_set_mm_blend, /* FT_Set_MM_Blend_Func set_mm_blend */ + cff_get_mm_blend, /* FT_Get_MM_Blend_Func get_mm_blend */ + cff_get_mm_var, /* FT_Get_MM_Var_Func get_mm_var */ + cff_set_var_design, /* FT_Set_Var_Design_Func set_var_design */ + cff_get_var_design, /* FT_Get_Var_Design_Func get_var_design */ + cff_set_named_instance, + /* FT_Set_Named_Instance_Func set_named_instance */ + cff_get_default_named_instance, + /* FT_Get_Default_Named_Instance_Func get_default_named_instance */ + cff_set_mm_weightvector, + /* FT_Set_MM_WeightVector_Func set_mm_weightvector */ + cff_get_mm_weightvector, + /* FT_Get_MM_WeightVector_Func get_mm_weightvector */ + cff_construct_ps_name, + /* FT_Construct_PS_Name_Func construct_ps_name */ + cff_load_delta_set_index_mapping, + /* FT_Var_Load_Delta_Set_Idx_Map_Func load_delta_set_idx_map */ + cff_load_item_variation_store, + /* FT_Var_Load_Item_Var_Store_Func load_item_variation_store */ + cff_get_item_delta, + /* FT_Var_Get_Item_Delta_Func get_item_delta */ + cff_done_item_variation_store, + /* FT_Var_Done_Item_Var_Store_Func done_item_variation_store */ + cff_done_delta_set_index_map, + /* FT_Var_Done_Delta_Set_Idx_Map_Func done_delta_set_index_map */ + cff_get_var_blend, /* FT_Get_Var_Blend_Func get_var_blend */ + cff_done_blend /* FT_Done_Blend_Func done_blend */ ) @@ -961,41 +1081,46 @@ * */ - static FT_Error - cff_hadvance_adjust( CFF_Face face, + FT_CALLBACK_DEF( FT_Error ) + cff_hadvance_adjust( FT_Face face, /* CFF_Face */ FT_UInt gindex, FT_Int *avalue ) { - FT_Service_MetricsVariations var = (FT_Service_MetricsVariations)face->var; + CFF_Face cffface = (CFF_Face)face; + FT_Service_MetricsVariations + var = (FT_Service_MetricsVariations)cffface->tt_var; - return var->hadvance_adjust( FT_FACE( face ), gindex, avalue ); + return var->hadvance_adjust( face, gindex, avalue ); } - static void - cff_metrics_adjust( CFF_Face face ) + FT_CALLBACK_DEF( void ) + cff_metrics_adjust( FT_Face face ) /* CFF_Face */ { - FT_Service_MetricsVariations var = (FT_Service_MetricsVariations)face->var; + CFF_Face cffface = (CFF_Face)face; + FT_Service_MetricsVariations + var = (FT_Service_MetricsVariations)cffface->tt_var; - var->metrics_adjust( FT_FACE( face ) ); + var->metrics_adjust( face ); } FT_DEFINE_SERVICE_METRICSVARIATIONSREC( cff_service_metrics_variations, - (FT_HAdvance_Adjust_Func)cff_hadvance_adjust, /* hadvance_adjust */ - (FT_LSB_Adjust_Func) NULL, /* lsb_adjust */ - (FT_RSB_Adjust_Func) NULL, /* rsb_adjust */ + cff_hadvance_adjust, /* FT_HAdvance_Adjust_Func hadvance_adjust */ + NULL, /* FT_LSB_Adjust_Func lsb_adjust */ + NULL, /* FT_RSB_Adjust_Func rsb_adjust */ - (FT_VAdvance_Adjust_Func)NULL, /* vadvance_adjust */ - (FT_TSB_Adjust_Func) NULL, /* tsb_adjust */ - (FT_BSB_Adjust_Func) NULL, /* bsb_adjust */ - (FT_VOrg_Adjust_Func) NULL, /* vorg_adjust */ + NULL, /* FT_VAdvance_Adjust_Func vadvance_adjust */ + NULL, /* FT_TSB_Adjust_Func tsb_adjust */ + NULL, /* FT_BSB_Adjust_Func bsb_adjust */ + NULL, /* FT_VOrg_Adjust_Func vorg_adjust */ - (FT_Metrics_Adjust_Func) cff_metrics_adjust /* metrics_adjust */ + cff_metrics_adjust, /* FT_Metrics_Adjust_Func metrics_adjust */ + NULL /* FT_Size_Reset_Func size_reset */ ) #endif @@ -1008,11 +1133,11 @@ FT_DEFINE_SERVICE_CFFLOADREC( cff_service_cff_load, - (FT_Get_Standard_Encoding_Func)cff_get_standard_encoding, - (FT_Load_Private_Dict_Func) cff_load_private_dict, - (FT_FD_Select_Get_Func) cff_fd_select_get, - (FT_Blend_Check_Vector_Func) cff_blend_check_vector, - (FT_Blend_Build_Vector_Func) cff_blend_build_vector + cff_get_standard_encoding, /* FT_Get_Standard_Encoding_Func get_standard_encoding */ + cff_load_private_dict, /* FT_Load_Private_Dict_Func load_private_dict */ + cff_fd_select_get, /* FT_FD_Select_Get_Func fd_select_get */ + cff_blend_check_vector, /* FT_Blend_Check_Vector_Func blend_check_vector */ + cff_blend_build_vector /* FT_Blend_Build_Vector_Func blend_build_vector */ ) @@ -1028,8 +1153,7 @@ /*************************************************************************/ /*************************************************************************/ -#if !defined FT_CONFIG_OPTION_NO_GLYPH_NAMES && \ - defined TT_CONFIG_OPTION_GX_VAR_SUPPORT +#if defined TT_CONFIG_OPTION_GX_VAR_SUPPORT FT_DEFINE_SERVICEDESCREC10( cff_services, @@ -1044,7 +1168,7 @@ FT_SERVICE_ID_PROPERTIES, &cff_service_properties, FT_SERVICE_ID_CFF_LOAD, &cff_service_cff_load ) -#elif !defined FT_CONFIG_OPTION_NO_GLYPH_NAMES +#else FT_DEFINE_SERVICEDESCREC8( cff_services, @@ -1057,32 +1181,6 @@ FT_SERVICE_ID_PROPERTIES, &cff_service_properties, FT_SERVICE_ID_CFF_LOAD, &cff_service_cff_load ) -#elif defined TT_CONFIG_OPTION_GX_VAR_SUPPORT - FT_DEFINE_SERVICEDESCREC9( - cff_services, - - FT_SERVICE_ID_FONT_FORMAT, FT_FONT_FORMAT_CFF, - FT_SERVICE_ID_MULTI_MASTERS, &cff_service_multi_masters, - FT_SERVICE_ID_METRICS_VARIATIONS, &cff_service_metrics_var, - FT_SERVICE_ID_POSTSCRIPT_INFO, &cff_service_ps_info, - FT_SERVICE_ID_POSTSCRIPT_FONT_NAME, &cff_service_ps_name, - FT_SERVICE_ID_TT_CMAP, &cff_service_get_cmap_info, - FT_SERVICE_ID_CID, &cff_service_cid_info, - FT_SERVICE_ID_PROPERTIES, &cff_service_properties, - FT_SERVICE_ID_CFF_LOAD, &cff_service_cff_load - ) -#else - FT_DEFINE_SERVICEDESCREC7( - cff_services, - - FT_SERVICE_ID_FONT_FORMAT, FT_FONT_FORMAT_CFF, - FT_SERVICE_ID_POSTSCRIPT_INFO, &cff_service_ps_info, - FT_SERVICE_ID_POSTSCRIPT_FONT_NAME, &cff_service_ps_name, - FT_SERVICE_ID_TT_CMAP, &cff_service_get_cmap_info, - FT_SERVICE_ID_CID, &cff_service_cid_info, - FT_SERVICE_ID_PROPERTIES, &cff_service_properties, - FT_SERVICE_ID_CFF_LOAD, &cff_service_cff_load - ) #endif diff --git a/src/font/freetype-2.10.2/src/cff/cffdrivr.h b/3rdparty/freetype-2.13.2/src/cff/cffdrivr.h similarity index 89% rename from src/font/freetype-2.10.2/src/cff/cffdrivr.h rename to 3rdparty/freetype-2.13.2/src/cff/cffdrivr.h index 25471d511..ab1f147bb 100644 --- a/src/font/freetype-2.10.2/src/cff/cffdrivr.h +++ b/3rdparty/freetype-2.13.2/src/cff/cffdrivr.h @@ -4,7 +4,7 @@ * * High-level OpenType driver interface (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,8 +20,7 @@ #define CFFDRIVER_H_ -#include -#include FT_INTERNAL_DRIVER_H +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/src/cff/cfferrs.h b/3rdparty/freetype-2.13.2/src/cff/cfferrs.h similarity index 90% rename from src/font/freetype-2.10.2/src/cff/cfferrs.h rename to 3rdparty/freetype-2.13.2/src/cff/cfferrs.h index 32be8a763..bc9a3043f 100644 --- a/src/font/freetype-2.10.2/src/cff/cfferrs.h +++ b/3rdparty/freetype-2.13.2/src/cff/cfferrs.h @@ -4,7 +4,7 @@ * * CFF error codes (specification only). * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -25,7 +25,7 @@ #ifndef CFFERRS_H_ #define CFFERRS_H_ -#include FT_MODULE_ERRORS_H +#include #undef FTERRORS_H_ @@ -34,7 +34,7 @@ #define FT_ERR_BASE FT_Mod_Err_CFF -#include FT_ERRORS_H +#include #endif /* CFFERRS_H_ */ diff --git a/src/font/freetype-2.10.2/src/cff/cffgload.c b/3rdparty/freetype-2.13.2/src/cff/cffgload.c similarity index 87% rename from src/font/freetype-2.10.2/src/cff/cffgload.c rename to 3rdparty/freetype-2.13.2/src/cff/cffgload.c index 1c4e1979c..c483d1d1a 100644 --- a/src/font/freetype-2.10.2/src/cff/cffgload.c +++ b/3rdparty/freetype-2.13.2/src/cff/cffgload.c @@ -4,7 +4,7 @@ * * OpenType Glyph Loader (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,20 +16,27 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_STREAM_H -#include FT_INTERNAL_SFNT_H -#include FT_INTERNAL_CALC_H -#include FT_INTERNAL_POSTSCRIPT_AUX_H -#include FT_OUTLINE_H -#include FT_DRIVER_H +#include +#include +#include +#include +#include +#include +#include #include "cffload.h" #include "cffgload.h" #include "cfferrs.h" +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT +#define IS_DEFAULT_INSTANCE( _face ) \ + ( !( FT_IS_NAMED_INSTANCE( _face ) || \ + FT_IS_VARIATION( _face ) ) ) +#else +#define IS_DEFAULT_INSTANCE( _face ) 1 +#endif + /************************************************************************** * @@ -60,7 +67,7 @@ *pointer = (FT_Byte*)data.pointer; - *length = (FT_ULong)data.length; + *length = data.length; return error; } @@ -68,7 +75,7 @@ #endif /* FT_CONFIG_OPTION_INCREMENTAL */ { - CFF_Font cff = (CFF_Font)(face->extra.data); + CFF_Font cff = (CFF_Font)( face->extra.data ); return cff_index_access_element( &cff->charstrings_index, glyph_index, @@ -95,7 +102,7 @@ data.pointer = *pointer; - data.length = (FT_Int)length; + data.length = (FT_UInt)length; face->root.internal->incremental_interface->funcs->free_glyph_data( face->root.internal->incremental_interface->object, &data ); @@ -104,7 +111,7 @@ #endif /* FT_CONFIG_OPTION_INCREMENTAL */ { - CFF_Font cff = (CFF_Font)(face->extra.data); + CFF_Font cff = (CFF_Font)( face->extra.data ); cff_index_forget_element( &cff->charstrings_index, pointer ); @@ -207,8 +214,8 @@ PSAux_Service psaux = (PSAux_Service)face->psaux; const CFF_Decoder_Funcs decoder_funcs = psaux->cff_decoder_funcs; - FT_Matrix font_matrix; - FT_Vector font_offset; + FT_Matrix font_matrix; + FT_Vector font_offset; force_scaling = FALSE; @@ -256,8 +263,8 @@ if ( size->strike_index != 0xFFFFFFFFUL && - sfnt->load_eblc && - ( load_flags & FT_LOAD_NO_BITMAP ) == 0 ) + ( load_flags & FT_LOAD_NO_BITMAP ) == 0 && + IS_DEFAULT_INSTANCE( size->root.face ) ) { TT_SBit_MetricsRec metrics; @@ -347,6 +354,75 @@ if ( load_flags & FT_LOAD_SBITS_ONLY ) return FT_THROW( Invalid_Argument ); +#ifdef FT_CONFIG_OPTION_SVG + /* check for OT-SVG */ + if ( ( load_flags & FT_LOAD_NO_SVG ) == 0 && + ( load_flags & FT_LOAD_COLOR ) && + face->svg ) + { + /* + * We load the SVG document and try to grab the advances from the + * table. For the bearings we rely on the presetting hook to do that. + */ + + SFNT_Service sfnt = (SFNT_Service)face->sfnt; + + + if ( size && (size->root.metrics.x_ppem < 1 || + size->root.metrics.y_ppem < 1 ) ) + { + error = FT_THROW( Invalid_Size_Handle ); + return error; + } + + FT_TRACE3(( "Trying to load SVG glyph\n" )); + + error = sfnt->load_svg_doc( (FT_GlyphSlot)glyph, glyph_index ); + if ( !error ) + { + FT_Fixed x_scale = size->root.metrics.x_scale; + FT_Fixed y_scale = size->root.metrics.y_scale; + + FT_Short dummy; + FT_UShort advanceX; + FT_UShort advanceY; + + + FT_TRACE3(( "Successfully loaded SVG glyph\n" )); + + glyph->root.format = FT_GLYPH_FORMAT_SVG; + + /* + * If horizontal or vertical advances are not present in the table, + * this is a problem with the font since the standard requires them. + * However, we are graceful and calculate the values by ourselves + * for the vertical case. + */ + sfnt->get_metrics( face, + FALSE, + glyph_index, + &dummy, + &advanceX ); + sfnt->get_metrics( face, + TRUE, + glyph_index, + &dummy, + &advanceY ); + + glyph->root.linearHoriAdvance = advanceX; + glyph->root.linearVertAdvance = advanceY; + + glyph->root.metrics.horiAdvance = FT_MulFix( advanceX, x_scale ); + glyph->root.metrics.vertAdvance = FT_MulFix( advanceY, y_scale ); + + return error; + } + + FT_TRACE3(( "Failed to load SVG glyph\n" )); + } + +#endif /* FT_CONFIG_OPTION_SVG */ + /* if we have a CID subfont, use its matrix (which has already */ /* been multiplied with the root matrix) */ @@ -364,7 +440,6 @@ top_upm = (FT_Long)cff->top_font.font_dict.units_per_em; sub_upm = (FT_Long)cff->subfonts[fd_index]->font_dict.units_per_em; - font_matrix = cff->subfonts[fd_index]->font_dict.font_matrix; font_offset = cff->subfonts[fd_index]->font_dict.font_offset; @@ -399,7 +474,6 @@ PS_Driver driver = (PS_Driver)FT_FACE_DRIVER( face ); #endif - FT_Byte* charstring; FT_ULong charstring_len; @@ -416,13 +490,14 @@ decoder.builder.no_recurse = FT_BOOL( load_flags & FT_LOAD_NO_RECURSE ); - /* now load the unscaled outline */ - error = cff_get_glyph_data( face, glyph_index, - &charstring, &charstring_len ); + /* this function also checks for a valid subfont index */ + error = decoder_funcs->prepare( &decoder, size, glyph_index ); if ( error ) goto Glyph_Build_Finished; - error = decoder_funcs->prepare( &decoder, size, glyph_index ); + /* now load the unscaled outline */ + error = cff_get_glyph_data( face, glyph_index, + &charstring, &charstring_len ); if ( error ) goto Glyph_Build_Finished; @@ -665,8 +740,12 @@ metrics->horiBearingY = cbox.yMax; if ( has_vertical_info ) + { metrics->vertBearingX = metrics->horiBearingX - metrics->horiAdvance / 2; + metrics->vertBearingY = FT_MulFix( metrics->vertBearingY, + glyph->y_scale ); + } else { if ( load_flags & FT_LOAD_VERTICAL_LAYOUT ) diff --git a/src/font/freetype-2.10.2/src/cff/cffgload.h b/3rdparty/freetype-2.13.2/src/cff/cffgload.h similarity index 92% rename from src/font/freetype-2.10.2/src/cff/cffgload.h rename to 3rdparty/freetype-2.13.2/src/cff/cffgload.h index b4ad61a56..3b8cf236d 100644 --- a/src/font/freetype-2.10.2/src/cff/cffgload.h +++ b/3rdparty/freetype-2.13.2/src/cff/cffgload.h @@ -4,7 +4,7 @@ * * OpenType Glyph Loader (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,9 +20,8 @@ #define CFFGLOAD_H_ -#include -#include FT_FREETYPE_H -#include FT_INTERNAL_CFF_OBJECTS_TYPES_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/src/cff/cffload.c b/3rdparty/freetype-2.13.2/src/cff/cffload.c similarity index 93% rename from src/font/freetype-2.10.2/src/cff/cffload.c rename to 3rdparty/freetype-2.13.2/src/cff/cffload.c index 9f1d0e2e6..af79082e9 100644 --- a/src/font/freetype-2.10.2/src/cff/cffload.c +++ b/3rdparty/freetype-2.13.2/src/cff/cffload.c @@ -4,7 +4,7 @@ * * OpenType and CFF data/program tables loader (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,17 +16,16 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_STREAM_H -#include FT_TRUETYPE_TAGS_H -#include FT_TYPE1_TABLES_H -#include FT_INTERNAL_POSTSCRIPT_AUX_H +#include +#include +#include +#include +#include +#include #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT -#include FT_MULTIPLE_MASTERS_H -#include FT_SERVICE_MULTIPLE_MASTERS_H +#include +#include #endif #include "cffload.h" @@ -357,9 +356,9 @@ data_size = (FT_ULong)( idx->count + 1 ) * offsize; - if ( FT_NEW_ARRAY( idx->offsets, idx->count + 1 ) || - FT_STREAM_SEEK( idx->start + idx->hdr_size ) || - FT_FRAME_ENTER( data_size ) ) + if ( FT_QNEW_ARRAY( idx->offsets, idx->count + 1 ) || + FT_STREAM_SEEK( idx->start + idx->hdr_size ) || + FT_FRAME_ENTER( data_size ) ) goto Exit; poff = idx->offsets; @@ -401,7 +400,7 @@ /* Allocate a table containing pointers to an index's elements. */ /* The `pool' argument makes this function convert the index */ - /* entries to C-style strings (this is, NULL-terminated). */ + /* entries to C-style strings (that is, null-terminated). */ static FT_Error cff_index_get_pointers( CFF_Index idx, FT_Byte*** table, @@ -411,7 +410,7 @@ FT_Error error = FT_Err_Ok; FT_Memory memory = idx->stream->memory; - FT_Byte** t = NULL; + FT_Byte** tbl = NULL; FT_Byte* new_bytes = NULL; FT_ULong new_size; @@ -428,11 +427,11 @@ new_size = idx->data_size + idx->count; if ( idx->count > 0 && - !FT_NEW_ARRAY( t, idx->count + 1 ) && + !FT_QNEW_ARRAY( tbl, idx->count + 1 ) && ( !pool || !FT_ALLOC( new_bytes, new_size ) ) ) { FT_ULong n, cur_offset; - FT_ULong extra = 0; + FT_ULong extra = 0; FT_Byte* org_bytes = idx->bytes; @@ -443,15 +442,15 @@ if ( cur_offset != 0 ) { FT_TRACE0(( "cff_index_get_pointers:" - " invalid first offset value %d set to zero\n", + " invalid first offset value %ld set to zero\n", cur_offset )); cur_offset = 0; } if ( !pool ) - t[0] = org_bytes + cur_offset; + tbl[0] = org_bytes + cur_offset; else - t[0] = new_bytes + cur_offset; + tbl[0] = new_bytes + cur_offset; for ( n = 1; n <= idx->count; n++ ) { @@ -465,23 +464,25 @@ next_offset = idx->data_size; if ( !pool ) - t[n] = org_bytes + next_offset; + tbl[n] = org_bytes + next_offset; else { - t[n] = new_bytes + next_offset + extra; + tbl[n] = new_bytes + next_offset + extra; if ( next_offset != cur_offset ) { - FT_MEM_COPY( t[n - 1], org_bytes + cur_offset, t[n] - t[n - 1] ); - t[n][0] = '\0'; - t[n] += 1; + FT_MEM_COPY( tbl[n - 1], + org_bytes + cur_offset, + tbl[n] - tbl[n - 1] ); + tbl[n][0] = '\0'; + tbl[n] += 1; extra++; } } cur_offset = next_offset; } - *table = t; + *table = tbl; if ( pool ) *pool = new_bytes; @@ -490,6 +491,11 @@ } Exit: + if ( error && new_bytes ) + FT_FREE( new_bytes ); + if ( error && tbl ) + FT_FREE( tbl ); + return error; } @@ -553,8 +559,8 @@ idx->data_offset > stream->size - off2 + 1 ) { FT_ERROR(( "cff_index_access_element:" - " offset to next entry (%d)" - " exceeds the end of stream (%d)\n", + " offset to next entry (%ld)" + " exceeds the end of stream (%ld)\n", off2, stream->size - idx->data_offset + 1 )); off2 = stream->size - idx->data_offset + 1; } @@ -616,7 +622,7 @@ FT_Byte* bytes; FT_ULong byte_len; FT_Error error; - FT_String* name = 0; + FT_String* name = NULL; if ( !idx->stream ) /* CFF2 does not include a name index */ @@ -628,10 +634,9 @@ if ( error ) goto Exit; - if ( !FT_ALLOC( name, byte_len + 1 ) ) + if ( !FT_QALLOC( name, byte_len + 1 ) ) { - if ( byte_len ) - FT_MEM_COPY( name, bytes, byte_len ); + FT_MEM_COPY( name, bytes, byte_len ); name[byte_len] = 0; } cff_index_forget_element( idx, &bytes ); @@ -766,8 +771,7 @@ case 3: /* first, compare to the cache */ - if ( (FT_UInt)( glyph_index - fdselect->cache_first ) < - fdselect->cache_count ) + if ( glyph_index - fdselect->cache_first < fdselect->cache_count ) { fd = fdselect->cache_fd; break; @@ -830,7 +834,6 @@ { FT_Error error = FT_Err_Ok; FT_UInt i; - FT_Long j; FT_UShort max_cid = 0; @@ -848,9 +851,10 @@ /* When multiple GIDs map to the same CID, we choose the lowest */ /* GID. This is not described in any spec, but it matches the */ - /* behaviour of recent Acroread versions. */ - for ( j = (FT_Long)num_glyphs - 1; j >= 0; j-- ) - charset->cids[charset->sids[j]] = (FT_UShort)j; + /* behaviour of recent Acroread versions. The loop stops when */ + /* the unsigned index wraps around after reaching zero. */ + for ( i = num_glyphs - 1; i < num_glyphs; i-- ) + charset->cids[charset->sids[i]] = (FT_UShort)i; charset->max_cid = max_cid; charset->num_glyphs = num_glyphs; @@ -926,7 +930,7 @@ goto Exit; /* Allocate memory for sids. */ - if ( FT_NEW_ARRAY( charset->sids, num_glyphs ) ) + if ( FT_QNEW_ARRAY( charset->sids, num_glyphs ) ) goto Exit; /* assign the .notdef glyph */ @@ -978,7 +982,7 @@ if ( glyph_sid > 0xFFFFL - nleft ) { FT_ERROR(( "cff_charset_load: invalid SID range trimmed" - " nleft=%d -> %d\n", nleft, 0xFFFFL - glyph_sid )); + " nleft=%d -> %ld\n", nleft, 0xFFFFL - glyph_sid )); nleft = ( FT_UInt )( 0xFFFFL - glyph_sid ); } @@ -1012,14 +1016,14 @@ case 0: if ( num_glyphs > 229 ) { - FT_ERROR(( "cff_charset_load: implicit charset larger than\n" - "predefined charset (Adobe ISO-Latin)\n" )); + FT_ERROR(( "cff_charset_load: implicit charset larger than\n" )); + FT_ERROR(( "predefined charset (Adobe ISO-Latin)\n" )); error = FT_THROW( Invalid_File_Format ); goto Exit; } /* Allocate memory for sids. */ - if ( FT_NEW_ARRAY( charset->sids, num_glyphs ) ) + if ( FT_QNEW_ARRAY( charset->sids, num_glyphs ) ) goto Exit; /* Copy the predefined charset into the allocated memory. */ @@ -1030,14 +1034,14 @@ case 1: if ( num_glyphs > 166 ) { - FT_ERROR(( "cff_charset_load: implicit charset larger than\n" - "predefined charset (Adobe Expert)\n" )); + FT_ERROR(( "cff_charset_load: implicit charset larger than\n" )); + FT_ERROR(( "predefined charset (Adobe Expert)\n" )); error = FT_THROW( Invalid_File_Format ); goto Exit; } /* Allocate memory for sids. */ - if ( FT_NEW_ARRAY( charset->sids, num_glyphs ) ) + if ( FT_QNEW_ARRAY( charset->sids, num_glyphs ) ) goto Exit; /* Copy the predefined charset into the allocated memory. */ @@ -1048,14 +1052,14 @@ case 2: if ( num_glyphs > 87 ) { - FT_ERROR(( "cff_charset_load: implicit charset larger than\n" - "predefined charset (Adobe Expert Subset)\n" )); + FT_ERROR(( "cff_charset_load: implicit charset larger than\n" )); + FT_ERROR(( "predefined charset (Adobe Expert Subset)\n" )); error = FT_THROW( Invalid_File_Format ); goto Exit; } /* Allocate memory for sids. */ - if ( FT_NEW_ARRAY( charset->sids, num_glyphs ) ) + if ( FT_QNEW_ARRAY( charset->sids, num_glyphs ) ) goto Exit; /* Copy the predefined charset into the allocated memory. */ @@ -1081,7 +1085,6 @@ FT_FREE( charset->cids ); charset->format = 0; charset->offset = 0; - charset->sids = 0; } return error; @@ -1135,6 +1138,8 @@ { FT_UInt vsOffset; FT_UInt format; + FT_UInt dataCount; + FT_UInt regionCount; FT_ULong regionListOffset; @@ -1157,16 +1162,16 @@ } /* read top level fields */ - if ( FT_READ_ULONG( regionListOffset ) || - FT_READ_USHORT( vstore->dataCount ) ) + if ( FT_READ_ULONG( regionListOffset ) || + FT_READ_USHORT( dataCount ) ) goto Exit; /* make temporary copy of item variation data offsets; */ /* we'll parse region list first, then come back */ - if ( FT_NEW_ARRAY( dataOffsetArray, vstore->dataCount ) ) + if ( FT_QNEW_ARRAY( dataOffsetArray, dataCount ) ) goto Exit; - for ( i = 0; i < vstore->dataCount; i++ ) + for ( i = 0; i < dataCount; i++ ) { if ( FT_READ_ULONG( dataOffsetArray[i] ) ) goto Exit; @@ -1175,20 +1180,24 @@ /* parse regionList and axisLists */ if ( FT_STREAM_SEEK( vsOffset + regionListOffset ) || FT_READ_USHORT( vstore->axisCount ) || - FT_READ_USHORT( vstore->regionCount ) ) + FT_READ_USHORT( regionCount ) ) goto Exit; - if ( FT_NEW_ARRAY( vstore->varRegionList, vstore->regionCount ) ) + vstore->regionCount = 0; + if ( FT_QNEW_ARRAY( vstore->varRegionList, regionCount ) ) goto Exit; - for ( i = 0; i < vstore->regionCount; i++ ) + for ( i = 0; i < regionCount; i++ ) { CFF_VarRegion* region = &vstore->varRegionList[i]; - if ( FT_NEW_ARRAY( region->axisList, vstore->axisCount ) ) + if ( FT_QNEW_ARRAY( region->axisList, vstore->axisCount ) ) goto Exit; + /* keep track of how many axisList to deallocate on error */ + vstore->regionCount++; + for ( j = 0; j < vstore->axisCount; j++ ) { CFF_AxisCoords* axis = ®ion->axisList[j]; @@ -1208,10 +1217,11 @@ } /* use dataOffsetArray now to parse varData items */ - if ( FT_NEW_ARRAY( vstore->varData, vstore->dataCount ) ) + vstore->dataCount = 0; + if ( FT_QNEW_ARRAY( vstore->varData, dataCount ) ) goto Exit; - for ( i = 0; i < vstore->dataCount; i++ ) + for ( i = 0; i < dataCount; i++ ) { CFF_VarData* data = &vstore->varData[i]; @@ -1230,9 +1240,12 @@ if ( FT_READ_USHORT( data->regionIdxCount ) ) goto Exit; - if ( FT_NEW_ARRAY( data->regionIndices, data->regionIdxCount ) ) + if ( FT_QNEW_ARRAY( data->regionIndices, data->regionIdxCount ) ) goto Exit; + /* keep track of how many regionIndices to deallocate on error */ + vstore->dataCount++; + for ( j = 0; j < data->regionIdxCount; j++ ) { if ( FT_READ_USHORT( data->regionIndices[j] ) ) @@ -1275,7 +1288,7 @@ /* Blended values are written to a different buffer, */ /* using reserved operator 255. */ /* */ - /* Blend calculation is done in 16.16 fixed point. */ + /* Blend calculation is done in 16.16 fixed-point. */ FT_LOCAL_DEF( FT_Error ) cff_blend_doBlend( CFF_SubFont subFont, CFF_Parser parser, @@ -1316,9 +1329,9 @@ /* increase or allocate `blend_stack' and reset `blend_top'; */ /* prepare to append `numBlends' values to the buffer */ - if ( FT_REALLOC( subFont->blend_stack, - subFont->blend_alloc, - subFont->blend_alloc + size ) ) + if ( FT_QREALLOC( subFont->blend_stack, + subFont->blend_alloc, + subFont->blend_alloc + size ) ) goto Exit; subFont->blend_top = subFont->blend_stack + subFont->blend_used; @@ -1348,19 +1361,20 @@ for ( i = 0; i < numBlends; i++ ) { const FT_Int32* weight = &blend->BV[1]; - FT_UInt32 sum; + FT_Fixed sum; /* convert inputs to 16.16 fixed point */ - sum = cff_parse_num( parser, &parser->stack[i + base] ) * 0x10000; + sum = cff_parse_fixed( parser, &parser->stack[i + base] ); for ( j = 1; j < blend->lenBV; j++ ) - sum += cff_parse_num( parser, &parser->stack[delta++] ) * *weight++; + sum += FT_MulFix( cff_parse_fixed( parser, &parser->stack[delta++] ), + *weight++ ); /* point parser stack to new value on blend_stack */ parser->stack[i + base] = subFont->blend_top; - /* Push blended result as Type 2 5-byte fixed point number. This */ + /* Push blended result as Type 2 5-byte fixed-point number. This */ /* will not conflict with actual DICTs because 255 is a reserved */ /* opcode in both CFF and CFF2 DICTs. See `cff_parse_num' for */ /* decode of this, which rounds to an integer. */ @@ -1431,9 +1445,7 @@ /* prepare buffer for the blend vector */ len = varData->regionIdxCount + 1; /* add 1 for default component */ - if ( FT_REALLOC( blend->BV, - blend->lenBV * sizeof( *blend->BV ), - len * sizeof( *blend->BV ) ) ) + if ( FT_QRENEW_ARRAY( blend->BV, blend->lenBV, len ) ) goto Exit; blend->lenBV = len; @@ -1450,10 +1462,8 @@ if ( master == 0 ) { blend->BV[master] = FT_FIXED_ONE; - FT_TRACE4(( " build blend vector len %d\n" - " [ %f ", - len, - blend->BV[master] / 65536.0 )); + FT_TRACE4(( " build blend vector len %d\n", len )); + FT_TRACE4(( " [ %f ", blend->BV[master] / 65536.0 )); continue; } @@ -1537,9 +1547,7 @@ if ( lenNDV != 0 ) { /* user has set a normalized vector */ - if ( FT_REALLOC( blend->lastNDV, - blend->lenNDV * sizeof ( *NDV ), - lenNDV * sizeof ( *NDV ) ) ) + if ( FT_QRENEW_ARRAY( blend->lastNDV, blend->lenNDV, lenNDV ) ) goto Exit; FT_MEM_COPY( blend->lastNDV, @@ -1582,16 +1590,17 @@ #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT FT_LOCAL_DEF( FT_Error ) - cff_get_var_blend( CFF_Face face, + cff_get_var_blend( FT_Face face, /* CFF_Face */ FT_UInt *num_coords, FT_Fixed* *coords, FT_Fixed* *normalizedcoords, FT_MM_Var* *mm_var ) { - FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm; + CFF_Face cffface = (CFF_Face)face; + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)cffface->mm; - return mm->get_var_blend( FT_FACE( face ), + return mm->get_var_blend( face, num_coords, coords, normalizedcoords, @@ -1600,13 +1609,14 @@ FT_LOCAL_DEF( void ) - cff_done_blend( CFF_Face face ) + cff_done_blend( FT_Face face ) /* CFF_Face */ { - FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm; + CFF_Face cffface = (CFF_Face)face; + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)cffface->mm; - if (mm) - mm->done_blend( FT_FACE( face ) ); + if ( mm ) + mm->done_blend( face ); } #endif /* TT_CONFIG_OPTION_GX_VAR_SUPPORT */ @@ -1643,13 +1653,6 @@ goto Exit; } - /* Zero out the code to gid/sid mappings. */ - for ( j = 0; j < 256; j++ ) - { - encoding->sids [j] = 0; - encoding->codes[j] = 0; - } - /* Note: The encoding table in a CFF font is indexed by glyph index; */ /* the first encoded glyph index is 1. Hence, we read the character */ /* code (`glyph_code') at index j and make the assignment: */ @@ -1664,6 +1667,10 @@ if ( offset > 1 ) { + /* Zero out the code to gid/sid mappings. */ + FT_ARRAY_ZERO( encoding->sids, 256 ); + FT_ARRAY_ZERO( encoding->codes, 256 ); + encoding->offset = base_offset + offset; /* we need to parse the table to determine its size */ @@ -1821,7 +1828,8 @@ /* Construct code to GID mapping from code to SID mapping */ /* and charset. */ - encoding->count = 0; + encoding->offset = offset; /* used in cff_face_init */ + encoding->count = 0; error = cff_charset_compute_cids( charset, num_glyphs, stream->memory ); @@ -1945,7 +1953,7 @@ if ( priv->blue_shift > 1000 || priv->blue_shift < 0 ) { FT_TRACE2(( "cff_load_private_dict:" - " setting unlikely BlueShift value %d to default (7)\n", + " setting unlikely BlueShift value %ld to default (7)\n", priv->blue_shift )); priv->blue_shift = 7; } @@ -1953,7 +1961,7 @@ if ( priv->blue_fuzz > 1000 || priv->blue_fuzz < 0 ) { FT_TRACE2(( "cff_load_private_dict:" - " setting unlikely BlueFuzz value %d to default (1)\n", + " setting unlikely BlueFuzz value %ld to default (1)\n", priv->blue_fuzz )); priv->blue_fuzz = 1; } @@ -2004,7 +2012,7 @@ /* Top and Font DICTs are not allowed to have blend operators. */ error = cff_parser_init( &parser, code, - &subfont->font_dict, + top, font->library, stackSize, 0, @@ -2357,8 +2365,8 @@ if ( font->name_index.count > 1 ) { FT_ERROR(( "cff_font_load:" - " invalid CFF font with multiple subfonts\n" - " " + " invalid CFF font with multiple subfonts\n" )); + FT_ERROR(( " " " in SFNT wrapper\n" )); error = FT_THROW( Invalid_File_Format ); goto Exit; diff --git a/src/font/freetype-2.10.2/src/cff/cffload.h b/3rdparty/freetype-2.13.2/src/cff/cffload.h similarity index 93% rename from src/font/freetype-2.10.2/src/cff/cffload.h rename to 3rdparty/freetype-2.13.2/src/cff/cffload.h index 1b7971293..b5286b0c8 100644 --- a/src/font/freetype-2.10.2/src/cff/cffload.h +++ b/3rdparty/freetype-2.13.2/src/cff/cffload.h @@ -4,7 +4,7 @@ * * OpenType & CFF data/program tables loader (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,10 +20,9 @@ #define CFFLOAD_H_ -#include -#include FT_INTERNAL_CFF_TYPES_H +#include #include "cffparse.h" -#include FT_INTERNAL_CFF_OBJECTS_TYPES_H /* for CFF_Face */ +#include /* for CFF_Face */ FT_BEGIN_HEADER @@ -106,14 +105,14 @@ FT_BEGIN_HEADER #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT FT_LOCAL( FT_Error ) - cff_get_var_blend( CFF_Face face, + cff_get_var_blend( FT_Face face, FT_UInt *num_coords, FT_Fixed* *coords, FT_Fixed* *normalizedcoords, FT_MM_Var* *mm_var ); FT_LOCAL( void ) - cff_done_blend( CFF_Face face ); + cff_done_blend( FT_Face face ); #endif diff --git a/src/font/freetype-2.10.2/src/cff/cffobjs.c b/3rdparty/freetype-2.13.2/src/cff/cffobjs.c similarity index 92% rename from src/font/freetype-2.10.2/src/cff/cffobjs.c rename to 3rdparty/freetype-2.13.2/src/cff/cffobjs.c index 78c3cb3c2..6d08620c4 100644 --- a/src/font/freetype-2.10.2/src/cff/cffobjs.c +++ b/3rdparty/freetype-2.13.2/src/cff/cffobjs.c @@ -4,7 +4,7 @@ * * OpenType objects manager (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,32 +16,31 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_CALC_H -#include FT_INTERNAL_STREAM_H -#include FT_ERRORS_H -#include FT_TRUETYPE_IDS_H -#include FT_TRUETYPE_TAGS_H -#include FT_INTERNAL_SFNT_H -#include FT_DRIVER_H +#include +#include +#include +#include +#include +#include +#include +#include #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT -#include FT_MULTIPLE_MASTERS_H -#include FT_SERVICE_MULTIPLE_MASTERS_H -#include FT_SERVICE_METRICS_VARIATIONS_H +#include +#include +#include #endif -#include FT_INTERNAL_CFF_OBJECTS_TYPES_H +#include #include "cffobjs.h" #include "cffload.h" #include "cffcmap.h" #include "cfferrs.h" -#include FT_INTERNAL_POSTSCRIPT_AUX_H -#include FT_SERVICE_CFF_TABLE_LOAD_H +#include +#include /************************************************************************** @@ -70,8 +69,8 @@ FT_Module module; - module = FT_Get_Module( size->root.face->driver->root.library, - "pshinter" ); + module = FT_Get_Module( font->library, "pshinter" ); + return ( module && pshinter && pshinter->get_globals_funcs ) ? pshinter->get_globals_funcs( module ) : 0; @@ -167,46 +166,54 @@ FT_Error error = FT_Err_Ok; PSH_Globals_Funcs funcs = cff_size_get_globals_funcs( size ); + FT_Memory memory = cffsize->face->memory; + CFF_Internal internal = NULL; + CFF_Face face = (CFF_Face)cffsize->face; + CFF_Font font = (CFF_Font)face->extra.data; - if ( funcs ) - { - CFF_Face face = (CFF_Face)cffsize->face; - CFF_Font font = (CFF_Font)face->extra.data; - CFF_Internal internal = NULL; + PS_PrivateRec priv; - PS_PrivateRec priv; - FT_Memory memory = cffsize->face->memory; + FT_UInt i; - FT_UInt i; + if ( !funcs ) + goto Exit; + if ( FT_NEW( internal ) ) + goto Exit; - if ( FT_NEW( internal ) ) - goto Exit; + cff_make_private_dict( &font->top_font, &priv ); + error = funcs->create( memory, &priv, &internal->topfont ); + if ( error ) + goto Exit; + + for ( i = font->num_subfonts; i > 0; i-- ) + { + CFF_SubFont sub = font->subfonts[i - 1]; - cff_make_private_dict( &font->top_font, &priv ); - error = funcs->create( cffsize->face->memory, &priv, - &internal->topfont ); + + cff_make_private_dict( sub, &priv ); + error = funcs->create( memory, &priv, &internal->subfonts[i - 1] ); if ( error ) goto Exit; + } - for ( i = font->num_subfonts; i > 0; i-- ) - { - CFF_SubFont sub = font->subfonts[i - 1]; + cffsize->internal->module_data = internal; + size->strike_index = 0xFFFFFFFFUL; - cff_make_private_dict( sub, &priv ); - error = funcs->create( cffsize->face->memory, &priv, - &internal->subfonts[i - 1] ); - if ( error ) - goto Exit; + Exit: + if ( error ) + { + if ( internal ) + { + for ( i = font->num_subfonts; i > 0; i-- ) + FT_FREE( internal->subfonts[i - 1] ); + FT_FREE( internal->topfont ); } - cffsize->internal->module_data = internal; + FT_FREE( internal ); } - size->strike_index = 0xFFFFFFFFUL; - - Exit: return error; } @@ -274,6 +281,8 @@ cff_size_request( FT_Size size, FT_Size_Request req ) { + FT_Error error; + CFF_Size cffsize = (CFF_Size)size; PSH_Globals_Funcs funcs; @@ -295,7 +304,9 @@ #endif /* TT_CONFIG_OPTION_EMBEDDED_BITMAPS */ - FT_Request_Metrics( size->face, req ); + error = FT_Request_Metrics( size->face, req ); + if ( error ) + goto Exit; funcs = cff_size_get_globals_funcs( cffsize ); @@ -336,7 +347,8 @@ } } - return FT_Err_Ok; + Exit: + return error; } @@ -349,7 +361,8 @@ FT_LOCAL_DEF( void ) cff_slot_done( FT_GlyphSlot slot ) { - slot->internal->glyph_hints = NULL; + if ( slot->internal ) + slot->internal->glyph_hints = NULL; } @@ -366,8 +379,7 @@ FT_Module module; - module = FT_Get_Module( slot->face->driver->root.library, - "pshinter" ); + module = FT_Get_Module( slot->library, "pshinter" ); if ( module ) { T2_Hints_Funcs funcs; @@ -396,9 +408,7 @@ FT_String* result; - (void)FT_STRDUP( result, source ); - - FT_UNUSED( error ); + FT_MEM_STRDUP( result, source ); return result; } @@ -649,8 +659,8 @@ if ( dict->cid_registry == 0xFFFFU && !psnames ) { FT_ERROR(( "cff_face_init:" - " cannot open CFF & CEF fonts\n" - " " + " cannot open CFF & CEF fonts\n" )); + FT_ERROR(( " " " without the `psnames' module\n" )); error = FT_THROW( Missing_Module ); goto Exit; @@ -674,13 +684,13 @@ /* In Multiple Master CFFs, two SIDs hold the Normalize Design */ /* Vector (NDV) and Convert Design Vector (CDV) charstrings, */ - /* which may contain NULL bytes in the middle of the data, too. */ + /* which may contain null bytes in the middle of the data, too. */ /* We thus access `cff->strings' directly. */ for ( idx = 1; idx < cff->num_strings; idx++ ) { FT_Byte* s1 = cff->strings[idx - 1]; FT_Byte* s2 = cff->strings[idx]; - FT_PtrDist s1len = s2 - s1 - 1; /* without the final NULL byte */ + FT_PtrDist s1len = s2 - s1 - 1; /* without the final null byte */ FT_PtrDist l; @@ -709,22 +719,15 @@ #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT { - FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm; - FT_Service_MetricsVariations var = (FT_Service_MetricsVariations)face->var; - FT_UInt instance_index = (FT_UInt)face_index >> 16; if ( FT_HAS_MULTIPLE_MASTERS( cffface ) && - mm && instance_index > 0 ) { - error = mm->set_instance( cffface, instance_index ); + error = FT_Set_Named_Instance( cffface, instance_index ); if ( error ) goto Exit; - - if ( var ) - var->metrics_adjust( cffface ); } } #endif /* TT_CONFIG_OPTION_GX_VAR_SUPPORT */ @@ -940,7 +943,8 @@ style_name = cff_strcpy( memory, fullp ); /* remove the style part from the family name (if present) */ - remove_style( cffface->family_name, style_name ); + if ( style_name ) + remove_style( cffface->family_name, style_name ); } break; } @@ -1017,12 +1021,10 @@ cffface->style_flags = flags; } -#ifndef FT_CONFIG_OPTION_NO_GLYPH_NAMES /* CID-keyed CFF or CFF2 fonts don't have glyph names -- the SFNT */ /* loader has unset this flag because of the 3.0 `post' table. */ if ( dict->cid_registry == 0xFFFFU && !cff2 ) cffface->face_flags |= FT_FACE_FLAG_GLYPH_NAMES; -#endif if ( dict->cid_registry != 0xFFFFU && pure_cff ) cffface->face_flags |= FT_FACE_FLAG_CID_KEYED; @@ -1038,11 +1040,11 @@ { FT_CharMapRec cmaprec; FT_CharMap cmap; - FT_UInt nn; + FT_Int nn; CFF_Encoding encoding = &cff->encoding; - for ( nn = 0; nn < (FT_UInt)cffface->num_charmaps; nn++ ) + for ( nn = 0; nn < cffface->num_charmaps; nn++ ) { cmap = cffface->charmaps[nn]; @@ -1067,7 +1069,7 @@ cmaprec.encoding_id = TT_MS_ID_UNICODE_CS; cmaprec.encoding = FT_ENCODING_UNICODE; - nn = (FT_UInt)cffface->num_charmaps; + nn = cffface->num_charmaps; error = FT_CMap_New( &cff_cmap_unicode_class_rec, NULL, &cmaprec, NULL ); @@ -1078,7 +1080,7 @@ error = FT_Err_Ok; /* if no Unicode charmap was previously selected, select this one */ - if ( !cffface->charmap && nn != (FT_UInt)cffface->num_charmaps ) + if ( !cffface->charmap && nn != cffface->num_charmaps ) cffface->charmap = cffface->charmaps[nn]; Skip_Unicode: @@ -1148,7 +1150,7 @@ } #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT - cff_done_blend( face ); + cff_done_blend( cffface ); face->blend = NULL; #endif } @@ -1163,11 +1165,7 @@ /* set default property values, cf. `ftcffdrv.h' */ -#ifdef CFF_CONFIG_OPTION_OLD_ENGINE - driver->hinting_engine = FT_HINTING_FREETYPE; -#else driver->hinting_engine = FT_HINTING_ADOBE; -#endif driver->no_stem_darkening = TRUE; diff --git a/src/font/freetype-2.10.2/src/cff/cffobjs.h b/3rdparty/freetype-2.13.2/src/cff/cffobjs.h similarity index 97% rename from src/font/freetype-2.10.2/src/cff/cffobjs.h rename to 3rdparty/freetype-2.13.2/src/cff/cffobjs.h index 6f12b95db..8f05f6132 100644 --- a/src/font/freetype-2.10.2/src/cff/cffobjs.h +++ b/3rdparty/freetype-2.13.2/src/cff/cffobjs.h @@ -4,7 +4,7 @@ * * OpenType objects manager (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,7 +20,6 @@ #define CFFOBJS_H_ -#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/src/cff/cffparse.c b/3rdparty/freetype-2.13.2/src/cff/cffparse.c similarity index 85% rename from src/font/freetype-2.10.2/src/cff/cffparse.c rename to 3rdparty/freetype-2.13.2/src/cff/cffparse.c index 0d3bf3459..3b076704c 100644 --- a/src/font/freetype-2.10.2/src/cff/cffparse.c +++ b/3rdparty/freetype-2.13.2/src/cff/cffparse.c @@ -4,7 +4,7 @@ * * CFF token stream parser (body) * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,13 +16,12 @@ */ -#include #include "cffparse.h" -#include FT_INTERNAL_STREAM_H -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_CALC_H -#include FT_INTERNAL_POSTSCRIPT_AUX_H -#include FT_LIST_H +#include +#include +#include +#include +#include #include "cfferrs.h" #include "cffload.h" @@ -63,11 +62,8 @@ parser->num_axes = num_axes; /* allocate the stack buffer */ - if ( FT_NEW_ARRAY( parser->stack, stackSize ) ) - { - FT_FREE( parser->stack ); + if ( FT_QNEW_ARRAY( parser->stack, stackSize ) ) goto Exit; - } parser->stackSize = stackSize; parser->top = parser->stack; /* empty stack */ @@ -77,23 +73,6 @@ } -#ifdef CFF_CONFIG_OPTION_OLD_ENGINE - static void - finalize_t2_strings( FT_Memory memory, - void* data, - void* user ) - { - CFF_T2_String t2 = (CFF_T2_String)data; - - - FT_UNUSED( user ); - - memory->free( memory, t2->start ); - memory->free( memory, data ); - } -#endif /* CFF_CONFIG_OPTION_OLD_ENGINE */ - - FT_LOCAL_DEF( void ) cff_parser_done( CFF_Parser parser ) { @@ -103,63 +82,19 @@ FT_FREE( parser->stack ); #ifdef CFF_CONFIG_OPTION_OLD_ENGINE - FT_List_Finalize( &parser->t2_strings, - finalize_t2_strings, - memory, - NULL ); + FT_List_Finalize( &parser->t2_strings, NULL, memory, NULL ); #endif } - /* Assuming `first >= last'. */ - - static FT_Error - cff_parser_within_limits( CFF_Parser parser, - FT_Byte* first, - FT_Byte* last ) - { -#ifndef CFF_CONFIG_OPTION_OLD_ENGINE - - /* Fast path for regular FreeType builds with the "new" engine; */ - /* `first >= parser->start' can be assumed. */ - - FT_UNUSED( first ); - - return last < parser->limit ? FT_Err_Ok : FT_THROW( Invalid_Argument ); - -#else /* CFF_CONFIG_OPTION_OLD_ENGINE */ - - FT_ListNode node; - - - if ( first >= parser->start && - last < parser->limit ) - return FT_Err_Ok; - - node = parser->t2_strings.head; - - while ( node ) - { - CFF_T2_String t2 = (CFF_T2_String)node->data; - - - if ( first >= t2->start && - last < t2->limit ) - return FT_Err_Ok; - - node = node->next; - } - - return FT_THROW( Invalid_Argument ); - -#endif /* CFF_CONFIG_OPTION_OLD_ENGINE */ - } - + /* The parser limit checks in the next two functions are supposed */ + /* to detect the immediate crossing of the stream boundary. They */ + /* shall not be triggered from the distant t2_strings buffers. */ /* read an integer */ static FT_Long - cff_parse_integer( CFF_Parser parser, - FT_Byte* start ) + cff_parse_integer( FT_Byte* start, + FT_Byte* limit ) { FT_Byte* p = start; FT_Int v = *p++; @@ -168,14 +103,14 @@ if ( v == 28 ) { - if ( cff_parser_within_limits( parser, p, p + 1 ) ) + if ( p + 2 > limit && limit >= p ) goto Bad; val = (FT_Short)( ( (FT_UShort)p[0] << 8 ) | p[1] ); } else if ( v == 29 ) { - if ( cff_parser_within_limits( parser, p, p + 3 ) ) + if ( p + 4 > limit && limit >= p ) goto Bad; val = (FT_Long)( ( (FT_ULong)p[0] << 24 ) | @@ -189,14 +124,14 @@ } else if ( v < 251 ) { - if ( cff_parser_within_limits( parser, p, p ) ) + if ( p + 1 > limit && limit >= p ) goto Bad; val = ( v - 247 ) * 256 + p[0] + 108; } else { - if ( cff_parser_within_limits( parser, p, p ) ) + if ( p + 1 > limit && limit >= p ) goto Bad; val = -( v - 251 ) * 256 - p[0] - 108; @@ -245,10 +180,10 @@ /* read a real */ static FT_Fixed - cff_parse_real( CFF_Parser parser, - FT_Byte* start, - FT_Long power_ten, - FT_Long* scaling ) + cff_parse_real( FT_Byte* start, + FT_Byte* limit, + FT_Long power_ten, + FT_Long* scaling ) { FT_Byte* p = start; FT_Int nib; @@ -283,7 +218,7 @@ p++; /* Make sure we don't read past the end. */ - if ( cff_parser_within_limits( parser, p, p ) ) + if ( p + 1 > limit && limit >= p ) goto Bad; } @@ -320,7 +255,7 @@ p++; /* Make sure we don't read past the end. */ - if ( cff_parser_within_limits( parser, p, p ) ) + if ( p + 1 > limit && limit >= p ) goto Bad; } @@ -359,7 +294,7 @@ p++; /* Make sure we don't read past the end. */ - if ( cff_parser_within_limits( parser, p, p ) ) + if ( p + 1 > limit && limit >= p ) goto Bad; } @@ -526,12 +461,12 @@ if ( **d == 30 ) { /* binary-coded decimal is truncated to integer */ - return cff_parse_real( parser, *d, 0, NULL ) >> 16; + return cff_parse_real( *d, parser->limit, 0, NULL ) >> 16; } else if ( **d == 255 ) { - /* 16.16 fixed point is used internally for CFF2 blend results. */ + /* 16.16 fixed-point is used internally for CFF2 blend results. */ /* Since these are trusted values, a limit check is not needed. */ /* After the 255, 4 bytes give the number. */ @@ -552,7 +487,7 @@ } else - return cff_parse_integer( parser, *d ); + return cff_parse_integer( *d, parser->limit ); } @@ -563,15 +498,33 @@ FT_Long scaling ) { if ( **d == 30 ) - return cff_parse_real( parser, *d, scaling, NULL ); + return cff_parse_real( *d, parser->limit, scaling, NULL ); + else if ( **d == 255 ) + { + FT_Fixed val = ( ( ( (FT_UInt32)*( d[0] + 1 ) << 24 ) | + ( (FT_UInt32)*( d[0] + 2 ) << 16 ) | + ( (FT_UInt32)*( d[0] + 3 ) << 8 ) | + (FT_UInt32)*( d[0] + 4 ) ) ); + + if ( scaling ) + { + if ( FT_ABS( val ) > power_ten_limits[scaling] ) + { + FT_TRACE4(( "!!!OVERFLOW:!!!" )); + return val > 0 ? 0x7FFFFFFFL : -0x7FFFFFFFL; + } + val *= power_tens[scaling]; + } + return val; + } else { - FT_Long val = cff_parse_integer( parser, *d ); + FT_Long val = cff_parse_integer( *d, parser->limit ); if ( scaling ) { - if ( FT_ABS( val ) > power_ten_limits[scaling] ) + if ( ( FT_ABS( val ) << 16 ) > power_ten_limits[scaling] ) { val = val > 0 ? 0x7FFFFFFFL : -0x7FFFFFFFL; goto Overflow; @@ -601,7 +554,7 @@ /* read a floating point number, either integer or real */ - static FT_Fixed + FT_LOCAL_DEF( FT_Fixed ) cff_parse_fixed( CFF_Parser parser, FT_Byte** d ) { @@ -631,14 +584,14 @@ FT_ASSERT( scaling ); if ( **d == 30 ) - return cff_parse_real( parser, *d, 0, scaling ); + return cff_parse_real( *d, parser->limit, 0, scaling ); else { FT_Long number; FT_Int integer_length; - number = cff_parse_integer( parser, d[0] ); + number = cff_parse_integer( *d, parser->limit ); if ( number > 0x7FFFL ) { @@ -687,7 +640,7 @@ dict->has_font_matrix = TRUE; - /* We expect a well-formed font matrix, this is, the matrix elements */ + /* We expect a well-formed font matrix, that is, the matrix elements */ /* `xx' and `yy' are of approximately the same magnitude. To avoid */ /* loss of precision, we use the magnitude of the largest matrix */ /* element to scale all other elements. The scaling factor is then */ @@ -714,9 +667,10 @@ ( max_scaling - min_scaling ) > 9 ) { FT_TRACE1(( "cff_parse_font_matrix:" - " strange scaling values (minimum %d, maximum %d),\n" - " " - " using default matrix\n", min_scaling, max_scaling )); + " strange scaling values (minimum %ld, maximum %ld),\n", + min_scaling, max_scaling )); + FT_TRACE1(( " " + " using default matrix\n" )); goto Unlikely; } @@ -758,12 +712,12 @@ *upm = (FT_ULong)power_tens[-max_scaling]; FT_TRACE4(( " [%f %f %f %f %f %f]\n", - (double)matrix->xx / *upm / 65536, - (double)matrix->xy / *upm / 65536, - (double)matrix->yx / *upm / 65536, - (double)matrix->yy / *upm / 65536, - (double)offset->x / *upm / 65536, - (double)offset->y / *upm / 65536 )); + (double)matrix->xx / (double)*upm / 65536, + (double)matrix->xy / (double)*upm / 65536, + (double)matrix->yx / (double)*upm / 65536, + (double)matrix->yy / (double)*upm / 65536, + (double)offset->x / (double)*upm / 65536, + (double)offset->y / (double)*upm / 65536 )); if ( !FT_Matrix_Check( matrix ) ) { @@ -811,7 +765,7 @@ bbox->yMax = FT_RoundFix( cff_parse_fixed( parser, data ) ); error = FT_Err_Ok; - FT_TRACE4(( " [%d %d %d %d]\n", + FT_TRACE4(( " [%ld %ld %ld %ld]\n", bbox->xMin / 65536, bbox->yMin / 65536, bbox->xMax / 65536, @@ -934,11 +888,11 @@ FT_TRACE1(( "cff_parse_cid_ros: real supplement is rounded\n" )); dict->cid_supplement = cff_parse_num( parser, data ); if ( dict->cid_supplement < 0 ) - FT_TRACE1(( "cff_parse_cid_ros: negative supplement %d is found\n", + FT_TRACE1(( "cff_parse_cid_ros: negative supplement %ld is found\n", dict->cid_supplement )); error = FT_Err_Ok; - FT_TRACE4(( " %d %d %d\n", + FT_TRACE4(( " %d %d %ld\n", dict->cid_registry, dict->cid_ordering, dict->cid_supplement )); @@ -1264,11 +1218,8 @@ FT_Byte* charstring_base; FT_ULong charstring_len; - FT_Fixed* stack; - FT_ListNode node; - CFF_T2_String t2; - size_t t2_size; - FT_Byte* q; + FT_Fixed* stack; + FT_Byte* q = NULL; charstring_base = ++p; @@ -1309,39 +1260,18 @@ /* Now copy the stack data in the temporary decoder object, */ /* converting it back to charstring number representations */ /* (this is ugly, I know). */ + /* The maximum required size is 5 bytes per stack element. */ + if ( FT_QALLOC( q, (FT_Long)( 2 * sizeof ( FT_ListNode ) ) + + 5 * ( decoder.top - decoder.stack ) ) ) + goto Exit; - node = (FT_ListNode)memory->alloc( memory, - sizeof ( FT_ListNodeRec ) ); - if ( !node ) - goto Out_Of_Memory_Error; - - FT_List_Add( &parser->t2_strings, node ); - - t2 = (CFF_T2_String)memory->alloc( memory, - sizeof ( CFF_T2_StringRec ) ); - if ( !t2 ) - goto Out_Of_Memory_Error; - - node->data = t2; - - /* `5' is the conservative upper bound of required bytes per stack */ - /* element. */ - - t2_size = 5 * ( decoder.top - decoder.stack ); - - q = (FT_Byte*)memory->alloc( memory, t2_size ); - if ( !q ) - goto Out_Of_Memory_Error; - - t2->start = q; - t2->limit = q + t2_size; + FT_List_Add( &parser->t2_strings, (FT_ListNode)q ); - stack = decoder.stack; + q += 2 * sizeof ( FT_ListNode ); - while ( stack < decoder.top ) + for ( stack = decoder.stack; stack < decoder.top; stack++ ) { - FT_ULong num; - FT_Bool neg; + FT_Long num = *stack; if ( (FT_UInt)( parser->top - parser->stack ) >= parser->stackSize ) @@ -1349,69 +1279,37 @@ *parser->top++ = q; - if ( *stack < 0 ) - { - num = (FT_ULong)NEG_LONG( *stack ); - neg = 1; - } - else - { - num = (FT_ULong)*stack; - neg = 0; - } - if ( num & 0xFFFFU ) { - if ( neg ) - num = (FT_ULong)-num; - *q++ = 255; - *q++ = ( num & 0xFF000000U ) >> 24; - *q++ = ( num & 0x00FF0000U ) >> 16; - *q++ = ( num & 0x0000FF00U ) >> 8; - *q++ = num & 0x000000FFU; + *q++ = (FT_Byte)( ( num >> 24 ) & 0xFF ); + *q++ = (FT_Byte)( ( num >> 16 ) & 0xFF ); + *q++ = (FT_Byte)( ( num >> 8 ) & 0xFF ); + *q++ = (FT_Byte)( ( num ) & 0xFF ); } else { num >>= 16; - if ( neg ) + if ( -107 <= num && num <= 107 ) + *q++ = (FT_Byte)( num + 139 ); + else if ( 108 <= num && num <= 1131 ) { - if ( num <= 107 ) - *q++ = (FT_Byte)( 139 - num ); - else if ( num <= 1131 ) - { - *q++ = (FT_Byte)( ( ( num - 108 ) >> 8 ) + 251 ); - *q++ = (FT_Byte)( ( num - 108 ) & 0xFF ); - } - else - { - num = (FT_ULong)-num; - - *q++ = 28; - *q++ = (FT_Byte)( num >> 8 ); - *q++ = (FT_Byte)( num & 0xFF ); - } + *q++ = (FT_Byte)( ( ( num - 108 ) >> 8 ) + 247 ); + *q++ = (FT_Byte)( ( num - 108 ) & 0xFF ); + } + else if ( -1131 <= num && num <= -108 ) + { + *q++ = (FT_Byte)( ( ( -num - 108 ) >> 8 ) + 251 ); + *q++ = (FT_Byte)( ( -num - 108) & 0xFF ); } else { - if ( num <= 107 ) - *q++ = (FT_Byte)( num + 139 ); - else if ( num <= 1131 ) - { - *q++ = (FT_Byte)( ( ( num - 108 ) >> 8 ) + 247 ); - *q++ = (FT_Byte)( ( num - 108 ) & 0xFF ); - } - else - { - *q++ = 28; - *q++ = (FT_Byte)( num >> 8 ); - *q++ = (FT_Byte)( num & 0xFF ); - } + *q++ = 28; + *q++ = (FT_Byte)( num >> 8 ); + *q++ = (FT_Byte)( num & 0xFF ); } } - - stack++; } } #endif /* CFF_CONFIG_OPTION_OLD_ENGINE */ @@ -1516,6 +1414,7 @@ case cff_kind_fixed_thousand: FT_TRACE4(( " %f\n", (double)val / 65536 / 1000 )); + break; default: ; /* never reached */ @@ -1597,12 +1496,6 @@ Exit: return error; -#ifdef CFF_CONFIG_OPTION_OLD_ENGINE - Out_Of_Memory_Error: - error = FT_THROW( Out_Of_Memory ); - goto Exit; -#endif - Stack_Overflow: error = FT_THROW( Invalid_Argument ); goto Exit; diff --git a/src/font/freetype-2.10.2/src/cff/cffparse.h b/3rdparty/freetype-2.13.2/src/cff/cffparse.h similarity index 91% rename from src/font/freetype-2.10.2/src/cff/cffparse.h rename to 3rdparty/freetype-2.13.2/src/cff/cffparse.h index 887110a74..418caacc6 100644 --- a/src/font/freetype-2.10.2/src/cff/cffparse.h +++ b/3rdparty/freetype-2.13.2/src/cff/cffparse.h @@ -4,7 +4,7 @@ * * CFF token stream parser (specification) * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,9 +20,8 @@ #define CFFPARSE_H_ -#include -#include FT_INTERNAL_CFF_TYPES_H -#include FT_INTERNAL_OBJECTS_H +#include +#include FT_BEGIN_HEADER @@ -77,6 +76,10 @@ FT_BEGIN_HEADER cff_parse_num( CFF_Parser parser, FT_Byte** d ); + FT_LOCAL( FT_Fixed ) + cff_parse_fixed( CFF_Parser parser, + FT_Byte** d ); + FT_LOCAL( FT_Error ) cff_parser_init( CFF_Parser parser, FT_UInt code, @@ -134,15 +137,6 @@ FT_BEGIN_HEADER FT_END_HEADER -#ifdef CFF_CONFIG_OPTION_OLD_ENGINE - typedef struct CFF_T2_String_ - { - FT_Byte* start; - FT_Byte* limit; - - } CFF_T2_StringRec, *CFF_T2_String; -#endif /* CFF_CONFIG_OPTION_OLD_ENGINE */ - #endif /* CFFPARSE_H_ */ diff --git a/src/font/freetype-2.10.2/src/cff/cfftoken.h b/3rdparty/freetype-2.13.2/src/cff/cfftoken.h similarity index 99% rename from src/font/freetype-2.10.2/src/cff/cfftoken.h rename to 3rdparty/freetype-2.13.2/src/cff/cfftoken.h index 4c6a53eec..b61cb0e66 100644 --- a/src/font/freetype-2.10.2/src/cff/cfftoken.h +++ b/3rdparty/freetype-2.13.2/src/cff/cfftoken.h @@ -4,7 +4,7 @@ * * CFF token definitions (specification only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, diff --git a/src/font/freetype-2.10.2/src/cff/module.mk b/3rdparty/freetype-2.13.2/src/cff/module.mk similarity index 95% rename from src/font/freetype-2.10.2/src/cff/module.mk rename to 3rdparty/freetype-2.13.2/src/cff/module.mk index bd728c6a3..b881d049f 100644 --- a/src/font/freetype-2.10.2/src/cff/module.mk +++ b/3rdparty/freetype-2.13.2/src/cff/module.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 1996-2020 by +# Copyright (C) 1996-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, diff --git a/src/font/freetype-2.10.2/src/cff/rules.mk b/3rdparty/freetype-2.13.2/src/cff/rules.mk similarity index 98% rename from src/font/freetype-2.10.2/src/cff/rules.mk rename to 3rdparty/freetype-2.13.2/src/cff/rules.mk index 70bb92d50..629424adf 100644 --- a/src/font/freetype-2.10.2/src/cff/rules.mk +++ b/3rdparty/freetype-2.13.2/src/cff/rules.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 1996-2020 by +# Copyright (C) 1996-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, diff --git a/src/font/freetype-2.10.2/src/pshinter/module.mk b/3rdparty/freetype-2.13.2/src/pshinter/module.mk similarity index 95% rename from src/font/freetype-2.10.2/src/pshinter/module.mk rename to 3rdparty/freetype-2.13.2/src/pshinter/module.mk index b440d2e76..dbc137dca 100644 --- a/src/font/freetype-2.10.2/src/pshinter/module.mk +++ b/3rdparty/freetype-2.13.2/src/pshinter/module.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 1996-2020 by +# Copyright (C) 1996-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, diff --git a/src/font/freetype-2.10.2/src/pshinter/pshalgo.c b/3rdparty/freetype-2.13.2/src/pshinter/pshalgo.c similarity index 94% rename from src/font/freetype-2.10.2/src/pshinter/pshalgo.c rename to 3rdparty/freetype-2.13.2/src/pshinter/pshalgo.c index 57dfa3da9..4f622e1e4 100644 --- a/src/font/freetype-2.10.2/src/pshinter/pshalgo.c +++ b/3rdparty/freetype-2.13.2/src/pshinter/pshalgo.c @@ -4,7 +4,7 @@ * * PostScript hinting algorithm (body). * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used @@ -16,10 +16,9 @@ */ -#include -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_CALC_H +#include +#include +#include #include "pshalgo.h" #include "pshnterr.h" @@ -183,13 +182,13 @@ count = hints->num_hints; /* allocate our tables */ - if ( FT_NEW_ARRAY( table->sort, 2 * count ) || - FT_NEW_ARRAY( table->hints, count ) || - FT_NEW_ARRAY( table->zones, 2 * count + 1 ) ) + if ( FT_QNEW_ARRAY( table->sort, 2 * count ) || + FT_QNEW_ARRAY( table->hints, count ) || + FT_QNEW_ARRAY( table->zones, 2 * count + 1 ) ) goto Exit; table->max_hints = count; - table->sort_global = table->sort + count; + table->sort_global = FT_OFFSET( table->sort, count ); table->num_hints = 0; table->num_zones = 0; table->zone = NULL; @@ -306,17 +305,18 @@ /* now, sort the hints; they are guaranteed to not overlap */ /* so we can compare their "org_pos" field directly */ { - FT_Int i1, i2; + FT_UInt i1, i2; PSH_Hint hint1, hint2; PSH_Hint* sort = table->sort; /* a simple bubble sort will do, since in 99% of cases, the hints */ /* will be already sorted -- and the sort will be linear */ - for ( i1 = 1; i1 < (FT_Int)count; i1++ ) + for ( i1 = 1; i1 < count; i1++ ) { hint1 = sort[i1]; - for ( i2 = i1 - 1; i2 >= 0; i2-- ) + /* this loop stops when i2 wraps around after reaching 0 */ + for ( i2 = i1 - 1; i2 < i1; i2-- ) { hint2 = sort[i2]; @@ -516,7 +516,7 @@ if ( !psh_hint_is_fitted( parent ) ) psh_hint_align( parent, globals, dimension, glyph ); - /* keep original relation between hints, this is, use the */ + /* keep original relation between hints, that is, use the */ /* scaled distance between the centers of the hints to */ /* compute the new position */ par_org_center = parent->org_pos + ( parent->org_len >> 1 ); @@ -870,7 +870,7 @@ return; } -#endif /* DEBUG_HINTER*/ +#endif /* DEBUG_HINTER */ hint = table->hints; count = table->max_hints; @@ -1050,12 +1050,12 @@ } - static int + static PSH_Dir psh_compute_dir( FT_Pos dx, FT_Pos dy ) { - FT_Pos ax, ay; - int result = PSH_DIR_NONE; + FT_Pos ax, ay; + PSH_Dir result = PSH_DIR_NONE; ax = FT_ABS( dx ); @@ -1167,8 +1167,8 @@ memory = glyph->memory = globals->memory; /* allocate and setup points + contours arrays */ - if ( FT_NEW_ARRAY( glyph->points, outline->n_points ) || - FT_NEW_ARRAY( glyph->contours, outline->n_contours ) ) + if ( FT_QNEW_ARRAY( glyph->points, outline->n_points ) || + FT_QNEW_ARRAY( glyph->contours, outline->n_contours ) ) goto Exit; glyph->num_points = (FT_UInt)outline->n_points; @@ -1228,28 +1228,29 @@ FT_Pos dxi, dyi, dxo, dyo; + point->flags = 0; if ( !( outline->tags[n] & FT_CURVE_TAG_ON ) ) - point->flags = PSH_POINT_OFF; + psh_point_set_off( point ); dxi = vec[n].x - vec[n_prev].x; dyi = vec[n].y - vec[n_prev].y; - point->dir_in = (FT_Char)psh_compute_dir( dxi, dyi ); + point->dir_in = psh_compute_dir( dxi, dyi ); dxo = vec[n_next].x - vec[n].x; dyo = vec[n_next].y - vec[n].y; - point->dir_out = (FT_Char)psh_compute_dir( dxo, dyo ); + point->dir_out = psh_compute_dir( dxo, dyo ); /* detect smooth points */ - if ( point->flags & PSH_POINT_OFF ) - point->flags |= PSH_POINT_SMOOTH; + if ( psh_point_is_off( point ) ) + psh_point_set_smooth( point ); else if ( point->dir_in == point->dir_out ) { if ( point->dir_out != PSH_DIR_NONE || psh_corner_is_flat( dxi, dyi, dxo, dyo ) ) - point->flags |= PSH_POINT_SMOOTH; + psh_point_set_smooth( point ); } } } @@ -1404,16 +1405,13 @@ } - /* major_dir is the direction for points on the bottom/left of the stem; */ - /* Points on the top/right of the stem will have a direction of */ - /* -major_dir. */ - + /* the min and max are based on contour orientation and fill rule */ static void psh_hint_table_find_strong_points( PSH_Hint_Table table, PSH_Point point, FT_UInt count, FT_Int threshold, - FT_Int major_dir ) + PSH_Dir major_dir ) { PSH_Hint* sort = table->sort; FT_UInt num_hints = table->num_hints; @@ -1421,59 +1419,53 @@ for ( ; count > 0; count--, point++ ) { - FT_Int point_dir = 0; - FT_Pos org_u = point->org_u; + PSH_Dir point_dir; + FT_Pos org_u = point->org_u; if ( psh_point_is_strong( point ) ) continue; - if ( PSH_DIR_COMPARE( point->dir_in, major_dir ) ) - point_dir = point->dir_in; - - else if ( PSH_DIR_COMPARE( point->dir_out, major_dir ) ) - point_dir = point->dir_out; + point_dir = + (PSH_Dir)( ( point->dir_in | point->dir_out ) & major_dir ); - if ( point_dir ) + if ( point_dir & ( PSH_DIR_DOWN | PSH_DIR_RIGHT ) ) { - if ( point_dir == major_dir ) - { - FT_UInt nn; + FT_UInt nn; - for ( nn = 0; nn < num_hints; nn++ ) - { - PSH_Hint hint = sort[nn]; - FT_Pos d = org_u - hint->org_pos; + for ( nn = 0; nn < num_hints; nn++ ) + { + PSH_Hint hint = sort[nn]; + FT_Pos d = org_u - hint->org_pos; - if ( d < threshold && -d < threshold ) - { - psh_point_set_strong( point ); - point->flags2 |= PSH_POINT_EDGE_MIN; - point->hint = hint; - break; - } + if ( d < threshold && -d < threshold ) + { + psh_point_set_strong( point ); + point->flags2 |= PSH_POINT_EDGE_MIN; + point->hint = hint; + break; } } - else if ( point_dir == -major_dir ) - { - FT_UInt nn; + } + else if ( point_dir & ( PSH_DIR_UP | PSH_DIR_LEFT ) ) + { + FT_UInt nn; - for ( nn = 0; nn < num_hints; nn++ ) - { - PSH_Hint hint = sort[nn]; - FT_Pos d = org_u - hint->org_pos - hint->org_len; + for ( nn = 0; nn < num_hints; nn++ ) + { + PSH_Hint hint = sort[nn]; + FT_Pos d = org_u - hint->org_pos - hint->org_len; - if ( d < threshold && -d < threshold ) - { - psh_point_set_strong( point ); - point->flags2 |= PSH_POINT_EDGE_MAX; - point->hint = hint; - break; - } + if ( d < threshold && -d < threshold ) + { + psh_point_set_strong( point ); + point->flags2 |= PSH_POINT_EDGE_MAX; + point->hint = hint; + break; } } } @@ -1556,8 +1548,9 @@ /* the accepted shift for strong points in fractional pixels */ #define PSH_STRONG_THRESHOLD 32 - /* the maximum shift value in font units */ -#define PSH_STRONG_THRESHOLD_MAXIMUM 30 + /* the maximum shift value in font units tuned to distinguish */ + /* between stems and serifs in URW+ font collection */ +#define PSH_STRONG_THRESHOLD_MAXIMUM 12 /* find strong points in a glyph */ @@ -1572,7 +1565,7 @@ PS_Mask mask = table->hint_masks->masks; FT_UInt num_masks = table->hint_masks->num_masks; FT_UInt first = 0; - FT_Int major_dir = ( dimension == 0 ) ? PSH_DIR_VERTICAL + PSH_Dir major_dir = ( dimension == 0 ) ? PSH_DIR_VERTICAL : PSH_DIR_HORIZONTAL; PSH_Dimension dim = &glyph->globals->dimension[dimension]; FT_Fixed scale = dim->scale_mult; @@ -1657,8 +1650,8 @@ /* check tangents */ - if ( !PSH_DIR_COMPARE( point->dir_in, PSH_DIR_HORIZONTAL ) && - !PSH_DIR_COMPARE( point->dir_out, PSH_DIR_HORIZONTAL ) ) + if ( !( point->dir_in & PSH_DIR_HORIZONTAL ) && + !( point->dir_out & PSH_DIR_HORIZONTAL ) ) continue; /* skip strong points */ @@ -1806,7 +1799,7 @@ FT_Error error; - if ( FT_NEW_ARRAY( strongs, num_strongs ) ) + if ( FT_QNEW_ARRAY( strongs, num_strongs ) ) return; } @@ -2119,14 +2112,17 @@ FT_Fixed old_x_scale = x_scale; FT_Fixed old_y_scale = y_scale; - FT_Fixed scaled; - FT_Fixed fitted; + FT_Fixed scaled = 0; + FT_Fixed fitted = 0; FT_Bool rescale = FALSE; - scaled = FT_MulFix( globals->blues.normal_top.zones->org_ref, y_scale ); - fitted = FT_PIX_ROUND( scaled ); + if ( globals->blues.normal_top.count ) + { + scaled = FT_MulFix( globals->blues.normal_top.zones->org_ref, y_scale ); + fitted = FT_PIX_ROUND( scaled ); + } if ( fitted != 0 && scaled != fitted ) { diff --git a/src/font/freetype-2.10.2/src/pshinter/pshalgo.h b/3rdparty/freetype-2.13.2/src/pshinter/pshalgo.h similarity index 91% rename from src/font/freetype-2.10.2/src/pshinter/pshalgo.h rename to 3rdparty/freetype-2.13.2/src/pshinter/pshalgo.h index 5367a5d16..3f0ba28a6 100644 --- a/src/font/freetype-2.10.2/src/pshinter/pshalgo.h +++ b/3rdparty/freetype-2.13.2/src/pshinter/pshalgo.h @@ -4,7 +4,7 @@ * * PostScript hinting algorithm (specification). * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -93,21 +93,17 @@ FT_BEGIN_HEADER typedef struct PSH_PointRec_* PSH_Point; typedef struct PSH_ContourRec_* PSH_Contour; - enum + typedef enum PSH_Dir_ { - PSH_DIR_NONE = 4, - PSH_DIR_UP = -1, - PSH_DIR_DOWN = 1, - PSH_DIR_LEFT = -2, - PSH_DIR_RIGHT = 2 - }; + PSH_DIR_NONE = 0, + PSH_DIR_UP = 1, + PSH_DIR_DOWN = 2, + PSH_DIR_VERTICAL = 1 | 2, + PSH_DIR_LEFT = 4, + PSH_DIR_RIGHT = 8, + PSH_DIR_HORIZONTAL = 4 | 8 -#define PSH_DIR_HORIZONTAL 2 -#define PSH_DIR_VERTICAL 1 - -#define PSH_DIR_COMPARE( d1, d2 ) ( (d1) == (d2) || (d1) == -(d2) ) -#define PSH_DIR_IS_HORIZONTAL( d ) PSH_DIR_COMPARE( d, PSH_DIR_HORIZONTAL ) -#define PSH_DIR_IS_VERTICAL( d ) PSH_DIR_COMPARE( d, PSH_DIR_VERTICAL ) + } PSH_Dir; /* the following bit-flags are computed once by the glyph */ @@ -160,8 +156,8 @@ FT_BEGIN_HEADER PSH_Contour contour; FT_UInt flags; FT_UInt flags2; - FT_Char dir_in; - FT_Char dir_out; + PSH_Dir dir_in; + PSH_Dir dir_out; PSH_Hint hint; FT_Pos org_u; FT_Pos org_v; @@ -199,10 +195,6 @@ FT_BEGIN_HEADER PSH_Globals globals; PSH_Hint_TableRec hint_tables[2]; - FT_Bool vertical; - FT_Int major_dir; - FT_Int minor_dir; - FT_Bool do_horz_hints; FT_Bool do_vert_hints; FT_Bool do_horz_snapping; diff --git a/src/font/freetype-2.10.2/src/pshinter/pshglob.c b/3rdparty/freetype-2.13.2/src/pshinter/pshglob.c similarity index 99% rename from src/font/freetype-2.10.2/src/pshinter/pshglob.c rename to 3rdparty/freetype-2.13.2/src/pshinter/pshglob.c index d9f835f99..d4c5eb32b 100644 --- a/src/font/freetype-2.10.2/src/pshinter/pshglob.c +++ b/3rdparty/freetype-2.13.2/src/pshinter/pshglob.c @@ -5,7 +5,7 @@ * PostScript hinter global hinting management (body). * Inspired by the new auto-hinter module. * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used @@ -17,10 +17,9 @@ */ -#include -#include FT_FREETYPE_H -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_CALC_H +#include +#include +#include #include "pshglob.h" #ifdef DEBUG_HINTER @@ -651,7 +650,7 @@ FT_Error error; - if ( !FT_NEW( globals ) ) + if ( !FT_QNEW( globals ) ) { FT_UInt count; FT_Short* read; diff --git a/src/font/freetype-2.10.2/src/pshinter/pshglob.h b/3rdparty/freetype-2.13.2/src/pshinter/pshglob.h similarity index 97% rename from src/font/freetype-2.10.2/src/pshinter/pshglob.h rename to 3rdparty/freetype-2.13.2/src/pshinter/pshglob.h index cd2f3122f..579eb2148 100644 --- a/src/font/freetype-2.10.2/src/pshinter/pshglob.h +++ b/3rdparty/freetype-2.13.2/src/pshinter/pshglob.h @@ -4,7 +4,7 @@ * * PostScript hinter global hinting management. * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,8 +20,8 @@ #define PSHGLOB_H_ -#include FT_FREETYPE_H -#include FT_INTERNAL_POSTSCRIPT_HINTS_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/src/pshinter/pshinter.c b/3rdparty/freetype-2.13.2/src/pshinter/pshinter.c similarity index 92% rename from src/font/freetype-2.10.2/src/pshinter/pshinter.c rename to 3rdparty/freetype-2.13.2/src/pshinter/pshinter.c index 6009db518..54ed41096 100644 --- a/src/font/freetype-2.10.2/src/pshinter/pshinter.c +++ b/3rdparty/freetype-2.13.2/src/pshinter/pshinter.c @@ -4,7 +4,7 @@ * * FreeType PostScript Hinting module * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -17,7 +17,6 @@ #define FT_MAKE_OPTION_SINGLE_OBJECT -#include #include "pshalgo.c" #include "pshglob.c" diff --git a/src/font/freetype-2.10.2/src/pshinter/pshmod.c b/3rdparty/freetype-2.13.2/src/pshinter/pshmod.c similarity index 88% rename from src/font/freetype-2.10.2/src/pshinter/pshmod.c rename to 3rdparty/freetype-2.13.2/src/pshinter/pshmod.c index 686859b3e..974a99e01 100644 --- a/src/font/freetype-2.10.2/src/pshinter/pshmod.c +++ b/3rdparty/freetype-2.13.2/src/pshinter/pshmod.c @@ -4,7 +4,7 @@ * * FreeType PostScript hinter module implementation (body). * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,10 +16,10 @@ */ -#include -#include FT_INTERNAL_OBJECTS_H +#include #include "pshrec.h" #include "pshalgo.h" +#include "pshmod.h" /* the Postscript Hinter module structure */ @@ -37,8 +37,11 @@ /* finalize module */ FT_CALLBACK_DEF( void ) - ps_hinter_done( PS_Hinter_Module module ) + ps_hinter_done( FT_Module module_ ) /* PS_Hinter_Module */ { + PS_Hinter_Module module = (PS_Hinter_Module)module_; + + module->t1_funcs.hints = NULL; module->t2_funcs.hints = NULL; @@ -48,8 +51,10 @@ /* initialize module, create hints recorder and the interface */ FT_CALLBACK_DEF( FT_Error ) - ps_hinter_init( PS_Hinter_Module module ) + ps_hinter_init( FT_Module module_ ) /* PS_Hinter_Module */ { + PS_Hinter_Module module = (PS_Hinter_Module)module_; + FT_Memory memory = module->root.memory; void* ph = &module->ps_hints; diff --git a/src/font/freetype-2.10.2/src/pshinter/pshmod.h b/3rdparty/freetype-2.13.2/src/pshinter/pshmod.h similarity index 90% rename from src/font/freetype-2.10.2/src/pshinter/pshmod.h rename to 3rdparty/freetype-2.13.2/src/pshinter/pshmod.h index c44112e9d..4bd781a35 100644 --- a/src/font/freetype-2.10.2/src/pshinter/pshmod.h +++ b/3rdparty/freetype-2.13.2/src/pshinter/pshmod.h @@ -4,7 +4,7 @@ * * PostScript hinter module interface (specification). * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,8 +20,7 @@ #define PSHMOD_H_ -#include -#include FT_MODULE_H +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/src/pshinter/pshnterr.h b/3rdparty/freetype-2.13.2/src/pshinter/pshnterr.h similarity index 90% rename from src/font/freetype-2.10.2/src/pshinter/pshnterr.h rename to 3rdparty/freetype-2.13.2/src/pshinter/pshnterr.h index c4e9f42d2..97624952d 100644 --- a/src/font/freetype-2.10.2/src/pshinter/pshnterr.h +++ b/3rdparty/freetype-2.13.2/src/pshinter/pshnterr.h @@ -4,7 +4,7 @@ * * PS Hinter error codes (specification only). * - * Copyright (C) 2003-2020 by + * Copyright (C) 2003-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -25,7 +25,7 @@ #ifndef PSHNTERR_H_ #define PSHNTERR_H_ -#include FT_MODULE_ERRORS_H +#include #undef FTERRORS_H_ @@ -33,7 +33,7 @@ #define FT_ERR_PREFIX PSH_Err_ #define FT_ERR_BASE FT_Mod_Err_PShinter -#include FT_ERRORS_H +#include #endif /* PSHNTERR_H_ */ diff --git a/src/font/freetype-2.10.2/src/pshinter/pshrec.c b/3rdparty/freetype-2.13.2/src/pshinter/pshrec.c similarity index 88% rename from src/font/freetype-2.10.2/src/pshinter/pshrec.c rename to 3rdparty/freetype-2.13.2/src/pshinter/pshrec.c index a81c6f712..680e6d013 100644 --- a/src/font/freetype-2.10.2/src/pshinter/pshrec.c +++ b/3rdparty/freetype-2.13.2/src/pshinter/pshrec.c @@ -4,7 +4,7 @@ * * FreeType PostScript hints recorder (body). * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,11 +16,10 @@ */ -#include -#include FT_FREETYPE_H -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_CALC_H +#include +#include +#include +#include #include "pshrec.h" #include "pshalgo.h" @@ -64,16 +63,14 @@ { FT_UInt old_max = table->max_hints; FT_UInt new_max = count; - FT_Error error = FT_Err_Ok; + FT_Error error; - if ( new_max > old_max ) - { - /* try to grow the table */ - new_max = FT_PAD_CEIL( new_max, 8 ); - if ( !FT_RENEW_ARRAY( table->hints, old_max, new_max ) ) - table->max_hints = new_max; - } + /* try to grow the table */ + new_max = FT_PAD_CEIL( new_max, 8 ); + if ( !FT_QRENEW_ARRAY( table->hints, old_max, new_max ) ) + table->max_hints = new_max; + return error; } @@ -91,17 +88,14 @@ count = table->num_hints; count++; - if ( count >= table->max_hints ) + if ( count > table->max_hints ) { error = ps_hint_table_ensure( table, count, memory ); if ( error ) goto Exit; } - hint = table->hints + count - 1; - hint->pos = 0; - hint->len = 0; - hint->flags = 0; + hint = table->hints + count - 1; /* initialized upstream */ table->num_hints = count; @@ -137,14 +131,15 @@ FT_UInt count, FT_Memory memory ) { - FT_UInt old_max = ( mask->max_bits + 7 ) >> 3; - FT_UInt new_max = ( count + 7 ) >> 3; + FT_UInt old_max = mask->max_bits >> 3; + FT_UInt new_max = ( count + 7 ) >> 3; FT_Error error = FT_Err_Ok; if ( new_max > old_max ) { new_max = FT_PAD_CEIL( new_max, 8 ); + /* added bytes are zeroed here */ if ( !FT_RENEW_ARRAY( mask->bytes, old_max, new_max ) ) mask->max_bits = new_max * 8; } @@ -155,31 +150,15 @@ /* test a bit value in a given mask */ static FT_Int ps_mask_test_bit( PS_Mask mask, - FT_Int idx ) + FT_UInt idx ) { - if ( (FT_UInt)idx >= mask->num_bits ) + if ( idx >= mask->num_bits ) return 0; return mask->bytes[idx >> 3] & ( 0x80 >> ( idx & 7 ) ); } - /* clear a given bit */ - static void - ps_mask_clear_bit( PS_Mask mask, - FT_UInt idx ) - { - FT_Byte* p; - - - if ( idx >= mask->num_bits ) - return; - - p = mask->bytes + ( idx >> 3 ); - p[0] = (FT_Byte)( p[0] & ~( 0x80 >> ( idx & 7 ) ) ); - } - - /* set a given bit, possibly grow the mask */ static FT_Error ps_mask_set_bit( PS_Mask mask, @@ -270,6 +249,10 @@ mask = table->masks + count - 1; mask->num_bits = 0; mask->end_point = 0; + /* reused mask must be cleared */ + if ( mask->max_bits ) + FT_MEM_ZERO( mask->bytes, mask->max_bits >> 3 ); + table->num_masks = count; Exit: @@ -427,7 +410,7 @@ PS_Mask mask2 = table->masks + index2; FT_UInt count1 = mask1->num_bits; FT_UInt count2 = mask2->num_bits; - FT_Int delta; + FT_UInt delta; if ( count2 > 0 ) @@ -438,15 +421,14 @@ /* if "count2" is greater than "count1", we need to grow the */ - /* first bitset, and clear the highest bits */ + /* first bitset */ if ( count2 > count1 ) { error = ps_mask_ensure( mask1, count2, memory ); if ( error ) goto Exit; - for ( pos = count1; pos < count2; pos++ ) - ps_mask_clear_bit( mask1, pos ); + mask1->num_bits = count2; } /* merge (unite) the bitsets */ @@ -468,7 +450,7 @@ mask2->end_point = 0; /* number of masks to move */ - delta = (FT_Int)( table->num_masks - 1 - index2 ); + delta = table->num_masks - 1 - index2; if ( delta > 0 ) { /* move to end of table for reuse */ @@ -477,7 +459,7 @@ ft_memmove( mask2, mask2 + 1, - (FT_UInt)delta * sizeof ( PS_MaskRec ) ); + delta * sizeof ( PS_MaskRec ) ); mask2[delta] = dummy; } @@ -500,23 +482,18 @@ ps_mask_table_merge_all( PS_Mask_Table table, FT_Memory memory ) { - FT_Int index1, index2; + FT_UInt index1, index2; FT_Error error = FT_Err_Ok; - /* both loops go down to 0, thus FT_Int for index1 and index2 */ - for ( index1 = (FT_Int)table->num_masks - 1; index1 > 0; index1-- ) + /* the loops stop when unsigned indices wrap around after 0 */ + for ( index1 = table->num_masks - 1; index1 < table->num_masks; index1-- ) { - for ( index2 = index1 - 1; index2 >= 0; index2-- ) + for ( index2 = index1 - 1; index2 < index1; index2-- ) { - if ( ps_mask_table_test_intersect( table, - (FT_UInt)index1, - (FT_UInt)index2 ) ) + if ( ps_mask_table_test_intersect( table, index1, index2 ) ) { - error = ps_mask_table_merge( table, - (FT_UInt)index2, - (FT_UInt)index1, - memory ); + error = ps_mask_table_merge( table, index2, index1, memory ); if ( error ) goto Exit; @@ -653,7 +630,7 @@ FT_Int pos, FT_Int len, FT_Memory memory, - FT_Int *aindex ) + FT_UInt *aindex ) { FT_Error error = FT_Err_Ok; FT_UInt flags = 0; @@ -671,9 +648,6 @@ len = 0; } - if ( aindex ) - *aindex = -1; - /* now, lookup stem in the current hints table */ { PS_Mask mask; @@ -710,7 +684,7 @@ goto Exit; if ( aindex ) - *aindex = (FT_Int)idx; + *aindex = idx; } Exit: @@ -721,9 +695,9 @@ /* add a "hstem3/vstem3" counter to our dimension table */ static FT_Error ps_dimension_add_counter( PS_Dimension dim, - FT_Int hint1, - FT_Int hint2, - FT_Int hint3, + FT_UInt hint1, + FT_UInt hint2, + FT_UInt hint3, FT_Memory memory ) { FT_Error error = FT_Err_Ok; @@ -750,26 +724,17 @@ } /* now, set the bits for our hints in the counter mask */ - if ( hint1 >= 0 ) - { - error = ps_mask_set_bit( counter, (FT_UInt)hint1, memory ); - if ( error ) - goto Exit; - } + error = ps_mask_set_bit( counter, hint1, memory ); + if ( error ) + goto Exit; - if ( hint2 >= 0 ) - { - error = ps_mask_set_bit( counter, (FT_UInt)hint2, memory ); - if ( error ) - goto Exit; - } + error = ps_mask_set_bit( counter, hint2, memory ); + if ( error ) + goto Exit; - if ( hint3 >= 0 ) - { - error = ps_mask_set_bit( counter, (FT_UInt)hint3, memory ); - if ( error ) - goto Exit; - } + error = ps_mask_set_bit( counter, hint3, memory ); + if ( error ) + goto Exit; Exit: return error; @@ -800,7 +765,7 @@ /* destroy hints */ - FT_LOCAL( void ) + FT_LOCAL_DEF( void ) ps_hints_done( PS_Hints hints ) { FT_Memory memory = hints->memory; @@ -814,7 +779,7 @@ } - FT_LOCAL( void ) + FT_LOCAL_DEF( void ) ps_hints_init( PS_Hints hints, FT_Memory memory ) { @@ -875,7 +840,7 @@ if ( error ) { FT_ERROR(( "ps_hints_stem: could not add stem" - " (%d,%d) to hints table\n", stems[0], stems[1] )); + " (%ld,%ld) to hints table\n", stems[0], stems[1] )); hints->error = error; return; @@ -886,10 +851,11 @@ /* add one Type1 counter stem to the current hints table */ static void - ps_hints_t1stem3( PS_Hints hints, + ps_hints_t1stem3( T1_Hints hints_, /* PS_Hints */ FT_UInt dimension, FT_Fixed* stems ) { + PS_Hints hints = (PS_Hints)hints_; FT_Error error = FT_Err_Ok; @@ -898,7 +864,7 @@ PS_Dimension dim; FT_Memory memory = hints->memory; FT_Int count; - FT_Int idx[3]; + FT_UInt idx[3]; /* limit "dimension" to 0..1 */ @@ -949,9 +915,10 @@ /* reset hints (only with Type 1 hints) */ static void - ps_hints_t1reset( PS_Hints hints, + ps_hints_t1reset( T1_Hints hints_, /* PS_Hints */ FT_UInt end_point ) { + PS_Hints hints = (PS_Hints)hints_; FT_Error error = FT_Err_Ok; @@ -988,11 +955,12 @@ /* Type2 "hintmask" operator, add a new hintmask to each direction */ static void - ps_hints_t2mask( PS_Hints hints, + ps_hints_t2mask( T2_Hints hints_, /* PS_Hints */ FT_UInt end_point, FT_UInt bit_count, const FT_Byte* bytes ) { + PS_Hints hints = (PS_Hints)hints_; FT_Error error; @@ -1034,10 +1002,11 @@ static void - ps_hints_t2counter( PS_Hints hints, + ps_hints_t2counter( T2_Hints hints_, /* PS_Hints */ FT_UInt bit_count, const FT_Byte* bytes ) { + PS_Hints hints = (PS_Hints)hints_; FT_Error error; @@ -1122,6 +1091,13 @@ ps_hints_open( (PS_Hints)hints, PS_HINT_TYPE_1 ); } + static FT_Error + t1_hints_close( T1_Hints hints, + FT_UInt end_point ) + { + return ps_hints_close( (PS_Hints)hints, end_point ); + } + static void t1_hints_stem( T1_Hints hints, FT_UInt dimension, @@ -1137,17 +1113,27 @@ } + static FT_Error + t1_hints_apply( T1_Hints hints, + FT_Outline* outline, + PSH_Globals globals, + FT_Render_Mode hint_mode ) + { + return ps_hints_apply( (PS_Hints)hints, outline, globals, hint_mode ); + } + + FT_LOCAL_DEF( void ) t1_hints_funcs_init( T1_Hints_FuncsRec* funcs ) { FT_ZERO( funcs ); funcs->open = (T1_Hints_OpenFunc) t1_hints_open; - funcs->close = (T1_Hints_CloseFunc) ps_hints_close; + funcs->close = (T1_Hints_CloseFunc) t1_hints_close; funcs->stem = (T1_Hints_SetStemFunc) t1_hints_stem; funcs->stem3 = (T1_Hints_SetStem3Func)ps_hints_t1stem3; funcs->reset = (T1_Hints_ResetFunc) ps_hints_t1reset; - funcs->apply = (T1_Hints_ApplyFunc) ps_hints_apply; + funcs->apply = (T1_Hints_ApplyFunc) t1_hints_apply; } @@ -1166,6 +1152,14 @@ } + static FT_Error + t2_hints_close( T2_Hints hints, + FT_UInt end_point ) + { + return ps_hints_close( (PS_Hints)hints, end_point ); + } + + static void t2_hints_stems( T2_Hints hints, FT_UInt dimension, @@ -1203,17 +1197,27 @@ } + static FT_Error + t2_hints_apply( T2_Hints hints, + FT_Outline* outline, + PSH_Globals globals, + FT_Render_Mode hint_mode ) + { + return ps_hints_apply( (PS_Hints)hints, outline, globals, hint_mode ); + } + + FT_LOCAL_DEF( void ) t2_hints_funcs_init( T2_Hints_FuncsRec* funcs ) { FT_ZERO( funcs ); - funcs->open = (T2_Hints_OpenFunc) t2_hints_open; - funcs->close = (T2_Hints_CloseFunc) ps_hints_close; - funcs->stems = (T2_Hints_StemsFunc) t2_hints_stems; - funcs->hintmask= (T2_Hints_MaskFunc) ps_hints_t2mask; - funcs->counter = (T2_Hints_CounterFunc)ps_hints_t2counter; - funcs->apply = (T2_Hints_ApplyFunc) ps_hints_apply; + funcs->open = (T2_Hints_OpenFunc) t2_hints_open; + funcs->close = (T2_Hints_CloseFunc) t2_hints_close; + funcs->stems = (T2_Hints_StemsFunc) t2_hints_stems; + funcs->hintmask = (T2_Hints_MaskFunc) ps_hints_t2mask; + funcs->counter = (T2_Hints_CounterFunc)ps_hints_t2counter; + funcs->apply = (T2_Hints_ApplyFunc) t2_hints_apply; } diff --git a/src/font/freetype-2.10.2/src/pshinter/pshrec.h b/3rdparty/freetype-2.13.2/src/pshinter/pshrec.h similarity index 97% rename from src/font/freetype-2.10.2/src/pshinter/pshrec.h rename to 3rdparty/freetype-2.13.2/src/pshinter/pshrec.h index a8bc5aeec..0b2484af1 100644 --- a/src/font/freetype-2.10.2/src/pshinter/pshrec.h +++ b/3rdparty/freetype-2.13.2/src/pshinter/pshrec.h @@ -4,7 +4,7 @@ * * Postscript (Type1/Type2) hints recorder (specification). * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -32,8 +32,7 @@ #define PSHREC_H_ -#include -#include FT_INTERNAL_POSTSCRIPT_HINTS_H +#include #include "pshglob.h" diff --git a/src/font/freetype-2.10.2/src/pshinter/rules.mk b/3rdparty/freetype-2.13.2/src/pshinter/rules.mk similarity index 98% rename from src/font/freetype-2.10.2/src/pshinter/rules.mk rename to 3rdparty/freetype-2.13.2/src/pshinter/rules.mk index c845c255c..50058e882 100644 --- a/src/font/freetype-2.10.2/src/pshinter/rules.mk +++ b/3rdparty/freetype-2.13.2/src/pshinter/rules.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 2001-2020 by +# Copyright (C) 2001-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, diff --git a/src/font/freetype-2.10.2/src/psnames/module.mk b/3rdparty/freetype-2.13.2/src/psnames/module.mk similarity index 95% rename from src/font/freetype-2.10.2/src/psnames/module.mk rename to 3rdparty/freetype-2.13.2/src/psnames/module.mk index 675bb3713..1ee0ef8f7 100644 --- a/src/font/freetype-2.10.2/src/psnames/module.mk +++ b/3rdparty/freetype-2.13.2/src/psnames/module.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 1996-2020 by +# Copyright (C) 1996-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, diff --git a/src/font/freetype-2.10.2/src/psnames/psmodule.c b/3rdparty/freetype-2.13.2/src/psnames/psmodule.c similarity index 83% rename from src/font/freetype-2.10.2/src/psnames/psmodule.c rename to 3rdparty/freetype-2.13.2/src/psnames/psmodule.c index bb3ff0702..8203a0465 100644 --- a/src/font/freetype-2.10.2/src/psnames/psmodule.c +++ b/3rdparty/freetype-2.13.2/src/psnames/psmodule.c @@ -4,7 +4,7 @@ * * psnames module implementation (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,10 +16,9 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_OBJECTS_H -#include FT_SERVICE_POSTSCRIPT_CMAPS_H +#include +#include +#include #include "psmodule.h" @@ -58,7 +57,7 @@ /* the name, as in `A.swash' or `e.final'; in this case, the */ /* VARIANT_BIT is set in the return value. */ /* */ - static FT_UInt32 + FT_CALLBACK_DEF( FT_UInt32 ) ps_unicode_value( const char* glyph_name ) { /* If the name begins with `uni', then the glyph name may be a */ @@ -156,31 +155,30 @@ /* Look for a non-initial dot in the glyph name in order to */ /* find variants like `A.swash', `e.final', etc. */ { - const char* p = glyph_name; - const char* dot = NULL; + FT_UInt32 value = 0; + const char* p = glyph_name; + + for ( ; *p && *p != '.'; p++ ) + ; - for ( ; *p; p++ ) + /* now look up the glyph in the Adobe Glyph List; */ + /* `.notdef', `.null' and the empty name are short cut */ + if ( p > glyph_name ) { - if ( *p == '.' && p > glyph_name ) - { - dot = p; - break; - } + value = (FT_UInt32)ft_get_adobe_glyph_index( glyph_name, p ); + + if ( *p == '.' ) + value |= (FT_UInt32)VARIANT_BIT; } - /* now look up the glyph in the Adobe Glyph List */ - if ( !dot ) - return (FT_UInt32)ft_get_adobe_glyph_index( glyph_name, p ); - else - return (FT_UInt32)( ft_get_adobe_glyph_index( glyph_name, dot ) | - VARIANT_BIT ); + return value; } } /* ft_qsort callback to sort the unicode map */ - FT_CALLBACK_DEF( int ) + FT_COMPARE_DEF( int ) compare_uni_maps( const void* a, const void* b ) { @@ -311,7 +309,7 @@ /* Build a table that maps Unicode values to glyph indices. */ - static FT_Error + FT_CALLBACK_DEF( FT_Error ) ps_unicodes_init( FT_Memory memory, PS_Unicodes table, FT_UInt num_glyphs, @@ -327,9 +325,8 @@ /* we first allocate the table */ table->num_maps = 0; - table->maps = NULL; - if ( !FT_NEW_ARRAY( table->maps, num_glyphs + EXTRA_GLYPH_LIST_SIZE ) ) + if ( !FT_QNEW_ARRAY( table->maps, num_glyphs + EXTRA_GLYPH_LIST_SIZE ) ) { FT_UInt n; FT_UInt count; @@ -344,7 +341,7 @@ const char* gname = get_glyph_name( glyph_data, n ); - if ( gname ) + if ( gname && *gname ) { ps_check_extra_glyph_name( gname, n, extra_glyphs, extra_glyph_list_states ); @@ -392,9 +389,9 @@ /* Reallocate if the number of used entries is much smaller. */ if ( count < num_glyphs / 2 ) { - (void)FT_RENEW_ARRAY( table->maps, - num_glyphs + EXTRA_GLYPH_LIST_SIZE, - count ); + FT_MEM_QRENEW_ARRAY( table->maps, + num_glyphs + EXTRA_GLYPH_LIST_SIZE, + count ); error = FT_Err_Ok; } @@ -411,25 +408,22 @@ } - static FT_UInt + FT_CALLBACK_DEF( FT_UInt ) ps_unicodes_char_index( PS_Unicodes table, FT_UInt32 unicode ) { - PS_UniMap *min, *max, *mid, *result = NULL; + PS_UniMap *result = NULL; + PS_UniMap *min = table->maps; + PS_UniMap *max = min + table->num_maps; + PS_UniMap *mid = min + ( ( max - min ) >> 1 ); /* Perform a binary search on the table. */ - - min = table->maps; - max = min + table->num_maps - 1; - - while ( min <= max ) + while ( min < max ) { FT_UInt32 base_glyph; - mid = min + ( ( max - min ) >> 1 ); - if ( mid->unicode == unicode ) { result = mid; @@ -441,13 +435,15 @@ if ( base_glyph == unicode ) result = mid; /* remember match but continue search for base glyph */ - if ( min == max ) - break; - if ( base_glyph < unicode ) min = mid + 1; else - max = mid - 1; + max = mid; + + /* reasonable prediction in a continuous block */ + mid += unicode - base_glyph; + if ( mid >= max || mid < min ) + mid = min + ( ( max - min ) >> 1 ); } if ( result ) @@ -457,7 +453,7 @@ } - static FT_UInt32 + FT_CALLBACK_DEF( FT_UInt ) ps_unicodes_char_next( PS_Unicodes table, FT_UInt32 *unicode ) { @@ -468,14 +464,13 @@ { FT_UInt min = 0; FT_UInt max = table->num_maps; - FT_UInt mid; + FT_UInt mid = min + ( ( max - min ) >> 1 ); PS_UniMap* map; FT_UInt32 base_glyph; while ( min < max ) { - mid = min + ( ( max - min ) >> 1 ); map = table->maps + mid; if ( map->unicode == char_code ) @@ -493,6 +488,11 @@ min = mid + 1; else max = mid; + + /* reasonable prediction in a continuous block */ + mid += char_code - base_glyph; + if ( mid >= max || mid < min ) + mid = min + ( max - min ) / 2; } if ( result ) @@ -518,7 +518,7 @@ #endif /* FT_CONFIG_OPTION_ADOBE_GLYPH_LIST */ - static const char* + FT_CALLBACK_DEF( const char* ) ps_get_macintosh_name( FT_UInt name_index ) { if ( name_index >= FT_NUM_MAC_NAMES ) @@ -528,7 +528,7 @@ } - static const char* + FT_CALLBACK_DEF( const char* ) ps_get_standard_strings( FT_UInt sid ) { if ( sid >= FT_NUM_SID_NAMES ) @@ -543,13 +543,13 @@ FT_DEFINE_SERVICE_PSCMAPSREC( pscmaps_interface, - (PS_Unicode_ValueFunc) ps_unicode_value, /* unicode_value */ - (PS_Unicodes_InitFunc) ps_unicodes_init, /* unicodes_init */ - (PS_Unicodes_CharIndexFunc)ps_unicodes_char_index, /* unicodes_char_index */ - (PS_Unicodes_CharNextFunc) ps_unicodes_char_next, /* unicodes_char_next */ + ps_unicode_value, /* PS_Unicode_ValueFunc unicode_value */ + ps_unicodes_init, /* PS_Unicodes_InitFunc unicodes_init */ + ps_unicodes_char_index, /* PS_Unicodes_CharIndexFunc unicodes_char_index */ + ps_unicodes_char_next, /* PS_Unicodes_CharNextFunc unicodes_char_next */ - (PS_Macintosh_NameFunc) ps_get_macintosh_name, /* macintosh_name */ - (PS_Adobe_Std_StringsFunc) ps_get_standard_strings, /* adobe_std_strings */ + ps_get_macintosh_name, /* PS_Macintosh_NameFunc macintosh_name */ + ps_get_standard_strings, /* PS_Adobe_Std_StringsFunc adobe_std_strings */ t1_standard_encoding, /* adobe_std_encoding */ t1_expert_encoding /* adobe_expert_encoding */ @@ -560,13 +560,13 @@ FT_DEFINE_SERVICE_PSCMAPSREC( pscmaps_interface, - NULL, /* unicode_value */ - NULL, /* unicodes_init */ - NULL, /* unicodes_char_index */ - NULL, /* unicodes_char_next */ + NULL, /* PS_Unicode_ValueFunc unicode_value */ + NULL, /* PS_Unicodes_InitFunc unicodes_init */ + NULL, /* PS_Unicodes_CharIndexFunc unicodes_char_index */ + NULL, /* PS_Unicodes_CharNextFunc unicodes_char_next */ - (PS_Macintosh_NameFunc) ps_get_macintosh_name, /* macintosh_name */ - (PS_Adobe_Std_StringsFunc) ps_get_standard_strings, /* adobe_std_strings */ + ps_get_macintosh_name, /* PS_Macintosh_NameFunc macintosh_name */ + ps_get_standard_strings, /* PS_Adobe_Std_StringsFunc adobe_std_strings */ t1_standard_encoding, /* adobe_std_encoding */ t1_expert_encoding /* adobe_expert_encoding */ @@ -612,9 +612,9 @@ PUT_PS_NAMES_SERVICE( (void*)&pscmaps_interface ), /* module specific interface */ - (FT_Module_Constructor)NULL, /* module_init */ - (FT_Module_Destructor) NULL, /* module_done */ - (FT_Module_Requester) PUT_PS_NAMES_SERVICE( psnames_get_service ) /* get_interface */ + NULL, /* FT_Module_Constructor module_init */ + NULL, /* FT_Module_Destructor module_done */ + PUT_PS_NAMES_SERVICE( psnames_get_service ) /* FT_Module_Requester get_interface */ ) diff --git a/src/font/freetype-2.10.2/src/psnames/psmodule.h b/3rdparty/freetype-2.13.2/src/psnames/psmodule.h similarity index 90% rename from src/font/freetype-2.10.2/src/psnames/psmodule.h rename to 3rdparty/freetype-2.13.2/src/psnames/psmodule.h index 955f699f3..0904700bf 100644 --- a/src/font/freetype-2.10.2/src/psnames/psmodule.h +++ b/3rdparty/freetype-2.13.2/src/psnames/psmodule.h @@ -4,7 +4,7 @@ * * High-level psnames module interface (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,8 +20,7 @@ #define PSMODULE_H_ -#include -#include FT_MODULE_H +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/src/psnames/psnamerr.h b/3rdparty/freetype-2.13.2/src/psnames/psnamerr.h similarity index 90% rename from src/font/freetype-2.10.2/src/psnames/psnamerr.h rename to 3rdparty/freetype-2.13.2/src/psnames/psnamerr.h index fb9058e61..0073f8228 100644 --- a/src/font/freetype-2.10.2/src/psnames/psnamerr.h +++ b/3rdparty/freetype-2.13.2/src/psnames/psnamerr.h @@ -4,7 +4,7 @@ * * PS names module error codes (specification only). * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -26,7 +26,7 @@ #ifndef PSNAMERR_H_ #define PSNAMERR_H_ -#include FT_MODULE_ERRORS_H +#include #undef FTERRORS_H_ @@ -34,7 +34,7 @@ #define FT_ERR_PREFIX PSnames_Err_ #define FT_ERR_BASE FT_Mod_Err_PSnames -#include FT_ERRORS_H +#include #endif /* PSNAMERR_H_ */ diff --git a/src/font/freetype-2.10.2/src/psnames/psnames.c b/3rdparty/freetype-2.13.2/src/psnames/psnames.c similarity index 91% rename from src/font/freetype-2.10.2/src/psnames/psnames.c rename to 3rdparty/freetype-2.13.2/src/psnames/psnames.c index 5ac3897d2..93ed9332f 100644 --- a/src/font/freetype-2.10.2/src/psnames/psnames.c +++ b/3rdparty/freetype-2.13.2/src/psnames/psnames.c @@ -4,7 +4,7 @@ * * FreeType psnames module component (body only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -17,7 +17,6 @@ #define FT_MAKE_OPTION_SINGLE_OBJECT -#include #include "psmodule.c" diff --git a/src/font/freetype-2.10.2/src/psnames/pstables.h b/3rdparty/freetype-2.13.2/src/psnames/pstables.h similarity index 99% rename from src/font/freetype-2.10.2/src/psnames/pstables.h rename to 3rdparty/freetype-2.13.2/src/psnames/pstables.h index c215f16ff..7f92cce60 100644 --- a/src/font/freetype-2.10.2/src/psnames/pstables.h +++ b/3rdparty/freetype-2.13.2/src/psnames/pstables.h @@ -4,7 +4,7 @@ * * PostScript glyph names. * - * Copyright (C) 2005-2020 by + * Copyright (C) 2005-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, diff --git a/src/font/freetype-2.10.2/src/psnames/rules.mk b/3rdparty/freetype-2.13.2/src/psnames/rules.mk similarity index 98% rename from src/font/freetype-2.10.2/src/psnames/rules.mk rename to 3rdparty/freetype-2.13.2/src/psnames/rules.mk index 14cdda3ad..8d7c58068 100644 --- a/src/font/freetype-2.10.2/src/psnames/rules.mk +++ b/3rdparty/freetype-2.13.2/src/psnames/rules.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 1996-2020 by +# Copyright (C) 1996-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, diff --git a/src/font/freetype-2.10.2/src/raster/ftmisc.h b/3rdparty/freetype-2.13.2/src/raster/ftmisc.h similarity index 92% rename from src/font/freetype-2.10.2/src/raster/ftmisc.h rename to 3rdparty/freetype-2.13.2/src/raster/ftmisc.h index 6efe4a9a5..33dbfd631 100644 --- a/src/font/freetype-2.10.2/src/raster/ftmisc.h +++ b/3rdparty/freetype-2.13.2/src/raster/ftmisc.h @@ -5,7 +5,7 @@ * Miscellaneous macros for stand-alone rasterizer (specification * only). * - * Copyright (C) 2005-2020 by + * Copyright (C) 2005-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used @@ -47,11 +47,8 @@ typedef signed long FT_F26Dot6; typedef int FT_Error; -#define FT_MAKE_TAG( _x1, _x2, _x3, _x4 ) \ - ( ( (FT_ULong)_x1 << 24 ) | \ - ( (FT_ULong)_x2 << 16 ) | \ - ( (FT_ULong)_x3 << 8 ) | \ - (FT_ULong)_x4 ) + +#define FT_STATIC_BYTE_CAST( type, var ) (type)(FT_Byte)(var) /* from include/freetype/ftsystem.h */ diff --git a/src/font/freetype-2.10.2/src/raster/ftraster.c b/3rdparty/freetype-2.13.2/src/raster/ftraster.c similarity index 88% rename from src/font/freetype-2.10.2/src/raster/ftraster.c rename to 3rdparty/freetype-2.13.2/src/raster/ftraster.c index 35655a634..192ca0701 100644 --- a/src/font/freetype-2.10.2/src/raster/ftraster.c +++ b/3rdparty/freetype-2.13.2/src/raster/ftraster.c @@ -4,7 +4,7 @@ * * The FreeType glyph rasterizer (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -62,10 +62,9 @@ #else /* !STANDALONE_ */ -#include #include "ftraster.h" -#include FT_INTERNAL_CALC_H /* for FT_MulDiv and FT_MulDiv_No_Round */ -#include FT_OUTLINE_H /* for FT_Outline_Get_CBox */ +#include /* for FT_MulDiv and FT_MulDiv_No_Round */ +#include /* for FT_Outline_Get_CBox */ #endif /* !STANDALONE_ */ @@ -150,9 +149,6 @@ /*************************************************************************/ /*************************************************************************/ - /* define DEBUG_RASTER if you want to compile a debugging version */ -/* #define DEBUG_RASTER */ - /*************************************************************************/ /*************************************************************************/ @@ -201,12 +197,13 @@ #define FT_THROW( e ) FT_ERR_CAT( Raster_Err_, e ) #endif -#define Raster_Err_None 0 -#define Raster_Err_Not_Ini -1 -#define Raster_Err_Overflow -2 -#define Raster_Err_Neg_Height -3 -#define Raster_Err_Invalid -4 -#define Raster_Err_Unsupported -5 +#define Raster_Err_Ok 0 +#define Raster_Err_Invalid_Outline -1 +#define Raster_Err_Cannot_Render_Glyph -2 +#define Raster_Err_Invalid_Argument -3 +#define Raster_Err_Raster_Overflow -4 +#define Raster_Err_Raster_Uninitialized -5 +#define Raster_Err_Raster_Negative_Height -6 #define ft_memset memset @@ -226,18 +223,11 @@ #else /* !STANDALONE_ */ -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_DEBUG_H /* for FT_TRACE, FT_ERROR, and FT_THROW */ +#include +#include /* for FT_TRACE, FT_ERROR, and FT_THROW */ #include "rasterrs.h" -#define Raster_Err_None FT_Err_Ok -#define Raster_Err_Not_Ini Raster_Err_Raster_Uninitialized -#define Raster_Err_Overflow Raster_Err_Raster_Overflow -#define Raster_Err_Neg_Height Raster_Err_Raster_Negative_Height -#define Raster_Err_Invalid Raster_Err_Invalid_Outline -#define Raster_Err_Unsupported Raster_Err_Cannot_Render_Glyph - #endif /* !STANDALONE_ */ @@ -376,16 +366,6 @@ typedef PProfile* PProfileList; - /* Simple record used to implement a stack of bands, required */ - /* by the sub-banding mechanism */ - typedef struct black_TBand_ - { - Short y_min; /* band's minimum */ - Short y_max; /* band's maximum */ - - } black_TBand; - - #define AlignProfileSize \ ( ( sizeof ( TProfile ) + sizeof ( Alignment ) - 1 ) / sizeof ( Long ) ) @@ -427,8 +407,8 @@ /* prototypes used for sweep function dispatch */ typedef void - Function_Sweep_Init( RAS_ARGS Short* min, - Short* max ); + Function_Sweep_Init( RAS_ARGS Short min, + Short max ); typedef void Function_Sweep_Span( RAS_ARGS Short y, @@ -460,6 +440,11 @@ #define IS_TOP_OVERSHOOT( x ) \ (Bool)( x - FLOOR( x ) >= ras.precision_half ) + /* Smart dropout rounding to find which pixel is closer to span ends. */ + /* To mimick Windows, symmetric cases break down indepenently of the */ + /* precision. */ +#define SMART( p, q ) FLOOR( ( (p) + (q) + ras.precision * 63 / 64 ) >> 1 ) + #if FT_RENDER_POOL_SIZE > 2048 #define FT_MAX_BLACK_POOL ( FT_RENDER_POOL_SIZE / sizeof ( Long ) ) #else @@ -488,10 +473,11 @@ Int numTurns; /* number of Y-turns in outline */ - TPoint* arc; /* current Bezier arc pointer */ + Byte dropOutControl; /* current drop_out control method */ UShort bWidth; /* target bitmap width */ PByte bOrigin; /* target bitmap bottom-left origin */ + PByte bLine; /* target bitmap current line */ Long lastX, lastY; Long minY, maxY; @@ -513,9 +499,6 @@ FT_Bitmap target; /* description of target bit/pixmap */ FT_Outline outline; - Long traceOfs; /* current offset in target bitmap */ - Short traceIncr; /* sweep's increment in target bitmap */ - /* dispatch variables */ Function_Sweep_Init* Proc_Sweep_Init; @@ -523,18 +506,6 @@ Function_Sweep_Span* Proc_Sweep_Drop; Function_Sweep_Step* Proc_Sweep_Step; - Byte dropOutControl; /* current drop_out control method */ - - Bool second_pass; /* indicates whether a horizontal pass */ - /* should be performed to control */ - /* drop-out accurately when calling */ - /* Render_Glyph. */ - - TPoint arcs[3 * MaxBezier + 1]; /* The Bezier stack */ - - black_TBand band_stack[16]; /* band stack used for sub-banding */ - Int band_top; /* band stack top */ - }; @@ -656,7 +627,7 @@ if ( ras.top >= ras.maxBuff ) { - ras.error = FT_THROW( Overflow ); + ras.error = FT_THROW( Raster_Overflow ); return FAILURE; } @@ -674,18 +645,18 @@ if ( overshoot ) ras.cProfile->flags |= Overshoot_Bottom; - FT_TRACE6(( " new ascending profile = %p\n", ras.cProfile )); + FT_TRACE6(( " new ascending profile = %p\n", (void *)ras.cProfile )); break; case Descending_State: if ( overshoot ) ras.cProfile->flags |= Overshoot_Top; - FT_TRACE6(( " new descending profile = %p\n", ras.cProfile )); + FT_TRACE6(( " new descending profile = %p\n", (void *)ras.cProfile )); break; default: FT_ERROR(( "New_Profile: invalid profile direction\n" )); - ras.error = FT_THROW( Invalid ); + ras.error = FT_THROW( Invalid_Outline ); return FAILURE; } @@ -727,7 +698,7 @@ if ( h < 0 ) { FT_ERROR(( "End_Profile: negative height encountered\n" )); - ras.error = FT_THROW( Neg_Height ); + ras.error = FT_THROW( Raster_Negative_Height ); return FAILURE; } @@ -737,7 +708,7 @@ FT_TRACE6(( " ending profile %p, start = %ld, height = %ld\n", - ras.cProfile, ras.cProfile->start, h )); + (void *)ras.cProfile, ras.cProfile->start, h )); ras.cProfile->height = h; if ( overshoot ) @@ -763,7 +734,7 @@ if ( ras.top >= ras.maxBuff ) { FT_TRACE1(( "overflow in End_Profile\n" )); - ras.error = FT_THROW( Overflow ); + ras.error = FT_THROW( Raster_Overflow ); return FAILURE; } @@ -818,7 +789,7 @@ ras.maxBuff--; if ( ras.maxBuff <= ras.top ) { - ras.error = FT_THROW( Overflow ); + ras.error = FT_THROW( Raster_Overflow ); return FAILURE; } ras.numTurns++; @@ -1082,7 +1053,7 @@ size = e2 - e1 + 1; if ( ras.top + size >= ras.maxBuff ) { - ras.error = FT_THROW( Overflow ); + ras.error = FT_THROW( Raster_Overflow ); return FAILURE; } @@ -1205,6 +1176,7 @@ */ static Bool Bezier_Up( RAS_ARGS Int degree, + TPoint* arc, TSplitter splitter, Long miny, Long maxy ) @@ -1212,13 +1184,11 @@ Long y1, y2, e, e2, e0; Short f1; - TPoint* arc; TPoint* start_arc; PLong top; - arc = ras.arc; y1 = arc[degree].y; y2 = arc[0].y; top = ras.top; @@ -1267,7 +1237,7 @@ if ( ( top + TRUNC( e2 - e ) + 1 ) >= ras.maxBuff ) { ras.top = top; - ras.error = FT_THROW( Overflow ); + ras.error = FT_THROW( Raster_Overflow ); return FAILURE; } @@ -1310,7 +1280,6 @@ Fin: ras.top = top; - ras.arc -= degree; return SUCCESS; } @@ -1342,11 +1311,11 @@ */ static Bool Bezier_Down( RAS_ARGS Int degree, + TPoint* arc, TSplitter splitter, Long miny, Long maxy ) { - TPoint* arc = ras.arc; Bool result, fresh; @@ -1358,7 +1327,7 @@ fresh = ras.fresh; - result = Bezier_Up( RAS_VARS degree, splitter, -maxy, -miny ); + result = Bezier_Up( RAS_VARS degree, arc, splitter, -maxy, -miny ); if ( fresh && !ras.fresh ) ras.cProfile->start = -ras.cProfile->start; @@ -1499,22 +1468,24 @@ { Long y1, y2, y3, x3, ymin, ymax; TStates state_bez; + TPoint arcs[2 * MaxBezier + 1]; /* The Bezier stack */ + TPoint* arc; /* current Bezier arc pointer */ - ras.arc = ras.arcs; - ras.arc[2].x = ras.lastX; - ras.arc[2].y = ras.lastY; - ras.arc[1].x = cx; - ras.arc[1].y = cy; - ras.arc[0].x = x; - ras.arc[0].y = y; + arc = arcs; + arc[2].x = ras.lastX; + arc[2].y = ras.lastY; + arc[1].x = cx; + arc[1].y = cy; + arc[0].x = x; + arc[0].y = y; do { - y1 = ras.arc[2].y; - y2 = ras.arc[1].y; - y3 = ras.arc[0].y; - x3 = ras.arc[0].x; + y1 = arc[2].y; + y2 = arc[1].y; + y3 = arc[0].y; + x3 = arc[0].x; /* first, categorize the Bezier arc */ @@ -1532,13 +1503,13 @@ if ( y2 < ymin || y2 > ymax ) { /* this arc has no given direction, split it! */ - Split_Conic( ras.arc ); - ras.arc += 2; + Split_Conic( arc ); + arc += 2; } else if ( y1 == y3 ) { /* this arc is flat, ignore it and pop it from the Bezier stack */ - ras.arc -= 2; + arc -= 2; } else { @@ -1565,15 +1536,18 @@ /* now call the appropriate routine */ if ( state_bez == Ascending_State ) { - if ( Bezier_Up( RAS_VARS 2, Split_Conic, ras.minY, ras.maxY ) ) + if ( Bezier_Up( RAS_VARS 2, arc, Split_Conic, + ras.minY, ras.maxY ) ) goto Fail; } else - if ( Bezier_Down( RAS_VARS 2, Split_Conic, ras.minY, ras.maxY ) ) + if ( Bezier_Down( RAS_VARS 2, arc, Split_Conic, + ras.minY, ras.maxY ) ) goto Fail; + arc -= 2; } - } while ( ras.arc >= ras.arcs ); + } while ( arc >= arcs ); ras.lastX = x3; ras.lastY = y3; @@ -1628,25 +1602,27 @@ { Long y1, y2, y3, y4, x4, ymin1, ymax1, ymin2, ymax2; TStates state_bez; + TPoint arcs[3 * MaxBezier + 1]; /* The Bezier stack */ + TPoint* arc; /* current Bezier arc pointer */ - ras.arc = ras.arcs; - ras.arc[3].x = ras.lastX; - ras.arc[3].y = ras.lastY; - ras.arc[2].x = cx1; - ras.arc[2].y = cy1; - ras.arc[1].x = cx2; - ras.arc[1].y = cy2; - ras.arc[0].x = x; - ras.arc[0].y = y; + arc = arcs; + arc[3].x = ras.lastX; + arc[3].y = ras.lastY; + arc[2].x = cx1; + arc[2].y = cy1; + arc[1].x = cx2; + arc[1].y = cy2; + arc[0].x = x; + arc[0].y = y; do { - y1 = ras.arc[3].y; - y2 = ras.arc[2].y; - y3 = ras.arc[1].y; - y4 = ras.arc[0].y; - x4 = ras.arc[0].x; + y1 = arc[3].y; + y2 = arc[2].y; + y3 = arc[1].y; + y4 = arc[0].y; + x4 = arc[0].x; /* first, categorize the Bezier arc */ @@ -1675,13 +1651,13 @@ if ( ymin2 < ymin1 || ymax2 > ymax1 ) { /* this arc has no given direction, split it! */ - Split_Cubic( ras.arc ); - ras.arc += 3; + Split_Cubic( arc ); + arc += 3; } else if ( y1 == y4 ) { /* this arc is flat, ignore it and pop it from the Bezier stack */ - ras.arc -= 3; + arc -= 3; } else { @@ -1707,15 +1683,18 @@ /* compute intersections */ if ( state_bez == Ascending_State ) { - if ( Bezier_Up( RAS_VARS 3, Split_Cubic, ras.minY, ras.maxY ) ) + if ( Bezier_Up( RAS_VARS 3, arc, Split_Cubic, + ras.minY, ras.maxY ) ) goto Fail; } else - if ( Bezier_Down( RAS_VARS 3, Split_Cubic, ras.minY, ras.maxY ) ) + if ( Bezier_Down( RAS_VARS 3, arc, Split_Cubic, + ras.minY, ras.maxY ) ) goto Fail; + arc -= 3; } - } while ( ras.arc >= ras.arcs ); + } while ( arc >= arcs ); ras.lastX = x4; ras.lastY = y4; @@ -1763,9 +1742,9 @@ * SUCCESS on success, FAILURE on error. */ static Bool - Decompose_Curve( RAS_ARGS UShort first, - UShort last, - Int flipped ) + Decompose_Curve( RAS_ARGS Int first, + Int last, + Int flipped ) { FT_Vector v_last; FT_Vector v_control; @@ -1963,7 +1942,7 @@ return SUCCESS; Invalid_Outline: - ras.error = FT_THROW( Invalid ); + ras.error = FT_THROW( Invalid_Outline ); Fail: return FAILURE; @@ -1990,8 +1969,8 @@ static Bool Convert_Glyph( RAS_ARGS Int flipped ) { - Int i; - UInt start; + Int i; + Int first, last; ras.fProfile = NULL; @@ -2006,8 +1985,7 @@ ras.cProfile->offset = ras.top; ras.num_Profs = 0; - start = 0; - + last = -1; for ( i = 0; i < ras.outline.n_contours; i++ ) { PProfile lastProfile; @@ -2017,12 +1995,11 @@ ras.state = Unknown_State; ras.gProfile = NULL; - if ( Decompose_Curve( RAS_VARS (UShort)start, - (UShort)ras.outline.contours[i], - flipped ) ) - return FAILURE; + first = last + 1; + last = ras.outline.contours[i]; - start = (UShort)ras.outline.contours[i] + 1; + if ( Decompose_Curve( RAS_VARS first, last, flipped ) ) + return FAILURE; /* we must now check whether the extreme arcs join or not */ if ( FRAC( ras.lastY ) == 0 && @@ -2116,8 +2093,8 @@ * Removes an old profile from a linked list. */ static void - DelOld( PProfileList list, - PProfile profile ) + DelOld( PProfileList list, + const PProfile profile ) { PProfile *old, current; @@ -2210,16 +2187,13 @@ */ static void - Vertical_Sweep_Init( RAS_ARGS Short* min, - Short* max ) + Vertical_Sweep_Init( RAS_ARGS Short min, + Short max ) { - Long pitch = ras.target.pitch; - FT_UNUSED( max ); - ras.traceIncr = (Short)-pitch; - ras.traceOfs = -*min * pitch; + ras.bLine = ras.bOrigin - min * ras.target.pitch; } @@ -2230,8 +2204,7 @@ PProfile left, PProfile right ) { - Long e1, e2; - Byte* target; + Long e1, e2; Int dropOutControl = left->flags & 7; @@ -2242,11 +2215,10 @@ /* in high-precision mode, we need 12 digits after the comma to */ /* represent multiples of 1/(1<<12) = 1/4096 */ - FT_TRACE7(( " y=%d x=[%.12f;%.12f], drop-out=%d", + FT_TRACE7(( " y=%d x=[% .12f;% .12f]", y, - x1 / (double)ras.precision, - x2 / (double)ras.precision, - dropOutControl )); + (double)x1 / (double)ras.precision, + (double)x2 / (double)ras.precision )); /* Drop-out control */ @@ -2265,6 +2237,8 @@ if ( e2 >= 0 && e1 < ras.bWidth ) { + Byte* target; + Int c1, c2; Byte f1, f2; @@ -2274,7 +2248,7 @@ if ( e2 >= ras.bWidth ) e2 = ras.bWidth - 1; - FT_TRACE7(( " -> x=[%d;%d]", e1, e2 )); + FT_TRACE7(( " -> x=[%ld;%ld]", e1, e2 )); c1 = (Short)( e1 >> 3 ); c2 = (Short)( e2 >> 3 ); @@ -2282,7 +2256,7 @@ f1 = (Byte) ( 0xFF >> ( e1 & 7 ) ); f2 = (Byte) ~( 0x7F >> ( e2 & 7 ) ); - target = ras.bOrigin + ras.traceOfs + c1; + target = ras.bLine + c1; c2 -= c1; if ( c2 > 0 ) @@ -2293,7 +2267,7 @@ /* This is due to the fact that, in the vast majority of cases, */ /* the span length in bytes is relatively small. */ while ( --c2 > 0 ) - *(++target) = 0xFF; + *( ++target ) = 0xFF; target[1] |= f2; } @@ -2316,10 +2290,10 @@ Short c1, f1; - FT_TRACE7(( " y=%d x=[%.12f;%.12f]", + FT_TRACE7(( " y=%d x=[% .12f;% .12f]", y, - x1 / (double)ras.precision, - x2 / (double)ras.precision )); + (double)x1 / (double)ras.precision, + (double)x2 / (double)ras.precision )); /* Drop-out control */ @@ -2353,8 +2327,6 @@ Int dropOutControl = left->flags & 7; - FT_TRACE7(( ", drop-out=%d", dropOutControl )); - if ( e1 == e2 + ras.precision ) { switch ( dropOutControl ) @@ -2364,7 +2336,7 @@ break; case 4: /* smart drop-outs including stubs */ - pxl = FLOOR( ( x1 + x2 - 1 ) / 2 + ras.precision_half ); + pxl = SMART( x1, x2 ); break; case 1: /* simple drop-outs excluding stubs */ @@ -2413,7 +2385,7 @@ if ( dropOutControl == 1 ) pxl = e2; else - pxl = FLOOR( ( x1 + x2 - 1 ) / 2 + ras.precision_half ); + pxl = SMART( x1, x2 ); break; default: /* modes 2, 3, 6, 7 */ @@ -2436,8 +2408,8 @@ c1 = (Short)( e1 >> 3 ); f1 = (Short)( e1 & 7 ); - if ( e1 >= 0 && e1 < ras.bWidth && - ras.bOrigin[ras.traceOfs + c1] & ( 0x80 >> f1 ) ) + if ( e1 >= 0 && e1 < ras.bWidth && + ras.bLine[c1] & ( 0x80 >> f1 ) ) goto Exit; } else @@ -2448,23 +2420,23 @@ if ( e1 >= 0 && e1 < ras.bWidth ) { - FT_TRACE7(( " -> x=%d (drop-out)", e1 )); + FT_TRACE7(( " -> x=%ld", e1 )); c1 = (Short)( e1 >> 3 ); f1 = (Short)( e1 & 7 ); - ras.bOrigin[ras.traceOfs + c1] |= (char)( 0x80 >> f1 ); + ras.bLine[c1] |= (char)( 0x80 >> f1 ); } Exit: - FT_TRACE7(( "\n" )); + FT_TRACE7(( " dropout=%d\n", left->flags & 7 )); } static void Vertical_Sweep_Step( RAS_ARG ) { - ras.traceOfs += ras.traceIncr; + ras.bLine -= ras.target.pitch; } @@ -2478,8 +2450,8 @@ */ static void - Horizontal_Sweep_Init( RAS_ARGS Short* min, - Short* max ) + Horizontal_Sweep_Init( RAS_ARGS Short min, + Short max ) { /* nothing, really */ FT_UNUSED_RASTER; @@ -2495,44 +2467,68 @@ PProfile left, PProfile right ) { + Long e1, e2; + FT_UNUSED( left ); FT_UNUSED( right ); - if ( x2 - x1 < ras.precision ) - { - Long e1, e2; + FT_TRACE7(( " x=%d y=[% .12f;% .12f]", + y, + (double)x1 / (double)ras.precision, + (double)x2 / (double)ras.precision )); + /* We should not need this procedure but the vertical sweep */ + /* mishandles horizontal lines through pixel centers. So we */ + /* have to check perfectly aligned span edges here. */ + /* */ + /* XXX: Can we handle horizontal lines better and drop this? */ - FT_TRACE7(( " x=%d y=[%.12f;%.12f]", - y, - x1 / (double)ras.precision, - x2 / (double)ras.precision )); + e1 = CEILING( x1 ); - e1 = CEILING( x1 ); - e2 = FLOOR ( x2 ); + if ( x1 == e1 ) + { + e1 = TRUNC( e1 ); - if ( e1 == e2 ) + if ( e1 >= 0 && (ULong)e1 < ras.target.rows ) { - e1 = TRUNC( e1 ); - - if ( e1 >= 0 && (ULong)e1 < ras.target.rows ) - { - Byte f1; - PByte bits; + Byte f1; + PByte bits; - FT_TRACE7(( " -> y=%d (drop-out)", e1 )); + bits = ras.bOrigin + ( y >> 3 ) - e1 * ras.target.pitch; + f1 = (Byte)( 0x80 >> ( y & 7 ) ); - bits = ras.bOrigin + ( y >> 3 ) - e1 * ras.target.pitch; - f1 = (Byte)( 0x80 >> ( y & 7 ) ); + FT_TRACE7(( bits[0] & f1 ? " redundant" + : " -> y=%ld edge", e1 )); - bits[0] |= f1; - } + bits[0] |= f1; } + } + + e2 = FLOOR ( x2 ); + + if ( x2 == e2 ) + { + e2 = TRUNC( e2 ); + + if ( e2 >= 0 && (ULong)e2 < ras.target.rows ) + { + Byte f1; + PByte bits; + - FT_TRACE7(( "\n" )); + bits = ras.bOrigin + ( y >> 3 ) - e2 * ras.target.pitch; + f1 = (Byte)( 0x80 >> ( y & 7 ) ); + + FT_TRACE7(( bits[0] & f1 ? " redundant" + : " -> y=%ld edge", e2 )); + + bits[0] |= f1; + } } + + FT_TRACE7(( "\n" )); } @@ -2548,10 +2544,10 @@ Byte f1; - FT_TRACE7(( " x=%d y=[%.12f;%.12f]", + FT_TRACE7(( " x=%d y=[% .12f;% .12f]", y, - x1 / (double)ras.precision, - x2 / (double)ras.precision )); + (double)x1 / (double)ras.precision, + (double)x2 / (double)ras.precision )); /* During the horizontal sweep, we only take care of drop-outs */ @@ -2574,8 +2570,6 @@ Int dropOutControl = left->flags & 7; - FT_TRACE7(( ", dropout=%d", dropOutControl )); - if ( e1 == e2 + ras.precision ) { switch ( dropOutControl ) @@ -2585,7 +2579,7 @@ break; case 4: /* smart drop-outs including stubs */ - pxl = FLOOR( ( x1 + x2 - 1 ) / 2 + ras.precision_half ); + pxl = SMART( x1, x2 ); break; case 1: /* simple drop-outs excluding stubs */ @@ -2609,7 +2603,7 @@ if ( dropOutControl == 1 ) pxl = e2; else - pxl = FLOOR( ( x1 + x2 - 1 ) / 2 + ras.precision_half ); + pxl = SMART( x1, x2 ); break; default: /* modes 2, 3, 6, 7 */ @@ -2645,7 +2639,7 @@ if ( e1 >= 0 && (ULong)e1 < ras.target.rows ) { - FT_TRACE7(( " -> y=%d (drop-out)", e1 )); + FT_TRACE7(( " -> y=%ld", e1 )); bits = ras.bOrigin + ( y >> 3 ) - e1 * ras.target.pitch; f1 = (Byte)( 0x80 >> ( y & 7 ) ); @@ -2654,7 +2648,7 @@ } Exit: - FT_TRACE7(( "\n" )); + FT_TRACE7(( " dropout=%d\n", left->flags & 7 )); } @@ -2721,13 +2715,13 @@ /* check the Y-turns */ if ( ras.numTurns == 0 ) { - ras.error = FT_THROW( Invalid ); + ras.error = FT_THROW( Invalid_Outline ); return FAILURE; } /* now initialize the sweep */ - ras.Proc_Sweep_Init( RAS_VARS &min_Y, &max_Y ); + ras.Proc_Sweep_Init( RAS_VARS min_Y, max_Y ); /* then compute the distance of each profile from min_Y */ @@ -2954,11 +2948,11 @@ FT_Outline_Get_CBox( const FT_Outline* outline, FT_BBox *acbox ) { - Long xMin, yMin, xMax, yMax; - - if ( outline && acbox ) { + Long xMin, yMin, xMax, yMax; + + if ( outline->n_points == 0 ) { xMin = 0; @@ -3016,63 +3010,54 @@ * Renderer error code. */ static int - Render_Single_Pass( RAS_ARGS Bool flipped ) + Render_Single_Pass( RAS_ARGS Bool flipped, + Int y_min, + Int y_max ) { - Short i, j, k; + Int y_mid; + Int band_top = 0; + Int band_stack[32]; /* enough to bisect 32-bit int bands */ - while ( ras.band_top >= 0 ) + while ( 1 ) { - ras.maxY = (Long)ras.band_stack[ras.band_top].y_max * ras.precision; - ras.minY = (Long)ras.band_stack[ras.band_top].y_min * ras.precision; + ras.minY = (Long)y_min * ras.precision; + ras.maxY = (Long)y_max * ras.precision; ras.top = ras.buff; - ras.error = Raster_Err_None; + ras.error = Raster_Err_Ok; if ( Convert_Glyph( RAS_VARS flipped ) ) { - if ( ras.error != Raster_Err_Overflow ) - return FAILURE; - - ras.error = Raster_Err_None; + if ( ras.error != Raster_Err_Raster_Overflow ) + return ras.error; /* sub-banding */ -#ifdef DEBUG_RASTER - ClearBand( RAS_VARS TRUNC( ras.minY ), TRUNC( ras.maxY ) ); -#endif - - i = ras.band_stack[ras.band_top].y_min; - j = ras.band_stack[ras.band_top].y_max; - - k = (Short)( ( i + j ) / 2 ); + if ( y_min == y_max ) + return ras.error; /* still Raster_Overflow */ - if ( ras.band_top >= 7 || k < i ) - { - ras.band_top = 0; - ras.error = FT_THROW( Invalid ); + y_mid = ( y_min + y_max ) >> 1; - return ras.error; - } - - ras.band_stack[ras.band_top + 1].y_min = k; - ras.band_stack[ras.band_top + 1].y_max = j; - - ras.band_stack[ras.band_top].y_max = (Short)( k - 1 ); - - ras.band_top++; + band_stack[band_top++] = y_min; + y_min = y_mid + 1; } else { if ( ras.fProfile ) if ( Draw_Sweep( RAS_VAR ) ) return ras.error; - ras.band_top--; + + if ( --band_top < 0 ) + break; + + y_max = y_min - 1; + y_min = band_stack[band_top]; } } - return SUCCESS; + return Raster_Err_Ok; } @@ -3109,9 +3094,6 @@ ras.dropOutControl += 1; } - ras.second_pass = (Bool)( !( ras.outline.flags & - FT_OUTLINE_SINGLE_PASS ) ); - /* Vertical Sweep */ FT_TRACE7(( "Vertical pass (ftraster)\n" )); @@ -3120,21 +3102,18 @@ ras.Proc_Sweep_Drop = Vertical_Sweep_Drop; ras.Proc_Sweep_Step = Vertical_Sweep_Step; - ras.band_top = 0; - ras.band_stack[0].y_min = 0; - ras.band_stack[0].y_max = (Short)( ras.target.rows - 1 ); - ras.bWidth = (UShort)ras.target.width; ras.bOrigin = (Byte*)ras.target.buffer; if ( ras.target.pitch > 0 ) ras.bOrigin += (Long)( ras.target.rows - 1 ) * ras.target.pitch; - if ( ( error = Render_Single_Pass( RAS_VARS 0 ) ) != 0 ) + error = Render_Single_Pass( RAS_VARS 0, 0, (Int)ras.target.rows - 1 ); + if ( error ) return error; /* Horizontal Sweep */ - if ( ras.second_pass && ras.dropOutControl != 2 ) + if ( !( ras.outline.flags & FT_OUTLINE_SINGLE_PASS ) ) { FT_TRACE7(( "Horizontal pass (ftraster)\n" )); @@ -3143,22 +3122,12 @@ ras.Proc_Sweep_Drop = Horizontal_Sweep_Drop; ras.Proc_Sweep_Step = Horizontal_Sweep_Step; - ras.band_top = 0; - ras.band_stack[0].y_min = 0; - ras.band_stack[0].y_max = (Short)( ras.target.width - 1 ); - - if ( ( error = Render_Single_Pass( RAS_VARS 1 ) ) != 0 ) + error = Render_Single_Pass( RAS_VARS 1, 0, (Int)ras.target.width - 1 ); + if ( error ) return error; } - return Raster_Err_None; - } - - - static void - ft_black_init( black_PRaster raster ) - { - FT_UNUSED( raster ); + return Raster_Err_Ok; } @@ -3179,7 +3148,6 @@ *araster = (FT_Raster)&the_raster; FT_ZERO( &the_raster ); - ft_black_init( &the_raster ); return 0; } @@ -3197,30 +3165,30 @@ static int - ft_black_new( FT_Memory memory, - black_PRaster *araster ) + ft_black_new( void* memory_, /* FT_Memory */ + FT_Raster *araster_ ) /* black_PRaster */ { + FT_Memory memory = (FT_Memory)memory_; + black_PRaster *araster = (black_PRaster*)araster_; + FT_Error error; black_PRaster raster = NULL; - *araster = 0; if ( !FT_NEW( raster ) ) - { raster->memory = memory; - ft_black_init( raster ); - *araster = raster; - } + *araster = raster; return error; } static void - ft_black_done( black_PRaster raster ) + ft_black_done( FT_Raster raster_ ) /* black_PRaster */ { - FT_Memory memory = (FT_Memory)raster->memory; + black_PRaster raster = (black_PRaster)raster_; + FT_Memory memory = (FT_Memory)raster->memory; FT_FREE( raster ); @@ -3269,38 +3237,36 @@ if ( !raster ) - return FT_THROW( Not_Ini ); + return FT_THROW( Raster_Uninitialized ); if ( !outline ) - return FT_THROW( Invalid ); + return FT_THROW( Invalid_Outline ); /* return immediately if the outline is empty */ if ( outline->n_points == 0 || outline->n_contours <= 0 ) - return Raster_Err_None; + return Raster_Err_Ok; if ( !outline->contours || !outline->points ) - return FT_THROW( Invalid ); + return FT_THROW( Invalid_Outline ); if ( outline->n_points != outline->contours[outline->n_contours - 1] + 1 ) - return FT_THROW( Invalid ); + return FT_THROW( Invalid_Outline ); /* this version of the raster does not support direct rendering, sorry */ - if ( params->flags & FT_RASTER_FLAG_DIRECT ) - return FT_THROW( Unsupported ); - - if ( params->flags & FT_RASTER_FLAG_AA ) - return FT_THROW( Unsupported ); + if ( params->flags & FT_RASTER_FLAG_DIRECT || + params->flags & FT_RASTER_FLAG_AA ) + return FT_THROW( Cannot_Render_Glyph ); if ( !target_map ) - return FT_THROW( Invalid ); + return FT_THROW( Invalid_Argument ); /* nothing to do */ if ( !target_map->width || !target_map->rows ) - return Raster_Err_None; + return Raster_Err_Ok; if ( !target_map->buffer ) - return FT_THROW( Invalid ); + return FT_THROW( Invalid_Argument ); ras.outline = *outline; ras.target = *target_map; @@ -3317,11 +3283,11 @@ FT_GLYPH_FORMAT_OUTLINE, - (FT_Raster_New_Func) ft_black_new, /* raster_new */ - (FT_Raster_Reset_Func) ft_black_reset, /* raster_reset */ - (FT_Raster_Set_Mode_Func)ft_black_set_mode, /* raster_set_mode */ - (FT_Raster_Render_Func) ft_black_render, /* raster_render */ - (FT_Raster_Done_Func) ft_black_done /* raster_done */ + ft_black_new, /* FT_Raster_New_Func raster_new */ + ft_black_reset, /* FT_Raster_Reset_Func raster_reset */ + ft_black_set_mode, /* FT_Raster_Set_Mode_Func raster_set_mode */ + ft_black_render, /* FT_Raster_Render_Func raster_render */ + ft_black_done /* FT_Raster_Done_Func raster_done */ ) diff --git a/src/font/freetype-2.10.2/src/raster/ftraster.h b/3rdparty/freetype-2.13.2/src/raster/ftraster.h similarity index 90% rename from src/font/freetype-2.10.2/src/raster/ftraster.h rename to 3rdparty/freetype-2.13.2/src/raster/ftraster.h index 833d30f23..b511b3a99 100644 --- a/src/font/freetype-2.10.2/src/raster/ftraster.h +++ b/3rdparty/freetype-2.13.2/src/raster/ftraster.h @@ -4,7 +4,7 @@ * * The FreeType glyph rasterizer (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used @@ -22,8 +22,9 @@ #include #include FT_CONFIG_CONFIG_H -#include FT_IMAGE_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/src/raster/ftrend1.c b/3rdparty/freetype-2.13.2/src/raster/ftrend1.c similarity index 85% rename from src/font/freetype-2.10.2/src/raster/ftrend1.c rename to 3rdparty/freetype-2.13.2/src/raster/ftrend1.c index 944279a8d..6d442b1ff 100644 --- a/src/font/freetype-2.10.2/src/raster/ftrend1.c +++ b/3rdparty/freetype-2.13.2/src/raster/ftrend1.c @@ -4,7 +4,7 @@ * * The FreeType glyph rasterizer interface (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,10 +16,9 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_OBJECTS_H -#include FT_OUTLINE_H +#include +#include +#include #include "ftrend1.h" #include "ftraster.h" @@ -28,8 +27,11 @@ /* initialize renderer -- init its raster */ static FT_Error - ft_raster1_init( FT_Renderer render ) + ft_raster1_init( FT_Module module ) /* FT_Renderer */ { + FT_Renderer render = (FT_Renderer)module; + + render->clazz->raster_class->raster_reset( render->raster, NULL, 0 ); return FT_Err_Ok; @@ -189,18 +191,18 @@ NULL, /* module specific interface */ - (FT_Module_Constructor)ft_raster1_init, /* module_init */ - (FT_Module_Destructor) NULL, /* module_done */ - (FT_Module_Requester) NULL, /* get_interface */ + ft_raster1_init, /* FT_Module_Constructor module_init */ + NULL, /* FT_Module_Destructor module_done */ + NULL, /* FT_Module_Requester get_interface */ FT_GLYPH_FORMAT_OUTLINE, - (FT_Renderer_RenderFunc) ft_raster1_render, /* render_glyph */ - (FT_Renderer_TransformFunc)ft_raster1_transform, /* transform_glyph */ - (FT_Renderer_GetCBoxFunc) ft_raster1_get_cbox, /* get_glyph_cbox */ - (FT_Renderer_SetModeFunc) ft_raster1_set_mode, /* set_mode */ + ft_raster1_render, /* FT_Renderer_RenderFunc render_glyph */ + ft_raster1_transform, /* FT_Renderer_TransformFunc transform_glyph */ + ft_raster1_get_cbox, /* FT_Renderer_GetCBoxFunc get_glyph_cbox */ + ft_raster1_set_mode, /* FT_Renderer_SetModeFunc set_mode */ - (FT_Raster_Funcs*)&ft_standard_raster /* raster_class */ + &ft_standard_raster /* FT_Raster_Funcs* raster_class */ ) diff --git a/src/font/freetype-2.10.2/src/raster/ftrend1.h b/3rdparty/freetype-2.13.2/src/raster/ftrend1.h similarity index 90% rename from src/font/freetype-2.10.2/src/raster/ftrend1.h rename to 3rdparty/freetype-2.13.2/src/raster/ftrend1.h index dc972b1bc..cec35c852 100644 --- a/src/font/freetype-2.10.2/src/raster/ftrend1.h +++ b/3rdparty/freetype-2.13.2/src/raster/ftrend1.h @@ -4,7 +4,7 @@ * * The FreeType glyph rasterizer interface (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,8 +20,7 @@ #define FTREND1_H_ -#include -#include FT_RENDER_H +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/src/raster/module.mk b/3rdparty/freetype-2.13.2/src/raster/module.mk similarity index 95% rename from src/font/freetype-2.10.2/src/raster/module.mk rename to 3rdparty/freetype-2.13.2/src/raster/module.mk index 3600732b1..6ad1aa77b 100644 --- a/src/font/freetype-2.10.2/src/raster/module.mk +++ b/3rdparty/freetype-2.13.2/src/raster/module.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 1996-2020 by +# Copyright (C) 1996-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, diff --git a/src/font/freetype-2.10.2/src/raster/raster.c b/3rdparty/freetype-2.13.2/src/raster/raster.c similarity index 92% rename from src/font/freetype-2.10.2/src/raster/raster.c rename to 3rdparty/freetype-2.13.2/src/raster/raster.c index 08431c850..82f474547 100644 --- a/src/font/freetype-2.10.2/src/raster/raster.c +++ b/3rdparty/freetype-2.13.2/src/raster/raster.c @@ -4,7 +4,7 @@ * * FreeType monochrome rasterer module component (body only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -17,7 +17,6 @@ #define FT_MAKE_OPTION_SINGLE_OBJECT -#include #include "ftraster.c" #include "ftrend1.c" diff --git a/src/font/freetype-2.10.2/src/raster/rasterrs.h b/3rdparty/freetype-2.13.2/src/raster/rasterrs.h similarity index 90% rename from src/font/freetype-2.10.2/src/raster/rasterrs.h rename to 3rdparty/freetype-2.13.2/src/raster/rasterrs.h index 379e1d3e8..989d8b44b 100644 --- a/src/font/freetype-2.10.2/src/raster/rasterrs.h +++ b/3rdparty/freetype-2.13.2/src/raster/rasterrs.h @@ -4,7 +4,7 @@ * * monochrome renderer error codes (specification only). * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -26,7 +26,7 @@ #ifndef RASTERRS_H_ #define RASTERRS_H_ -#include FT_MODULE_ERRORS_H +#include #undef FTERRORS_H_ @@ -34,7 +34,7 @@ #define FT_ERR_PREFIX Raster_Err_ #define FT_ERR_BASE FT_Mod_Err_Raster -#include FT_ERRORS_H +#include #endif /* RASTERRS_H_ */ diff --git a/src/font/freetype-2.10.2/src/raster/rules.mk b/3rdparty/freetype-2.13.2/src/raster/rules.mk similarity index 98% rename from src/font/freetype-2.10.2/src/raster/rules.mk rename to 3rdparty/freetype-2.13.2/src/raster/rules.mk index 3e949d774..031b85fb9 100644 --- a/src/font/freetype-2.10.2/src/raster/rules.mk +++ b/3rdparty/freetype-2.13.2/src/raster/rules.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 1996-2020 by +# Copyright (C) 1996-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, diff --git a/src/font/freetype-2.10.2/src/sfnt/module.mk b/3rdparty/freetype-2.13.2/src/sfnt/module.mk similarity index 95% rename from src/font/freetype-2.10.2/src/sfnt/module.mk rename to 3rdparty/freetype-2.13.2/src/sfnt/module.mk index 0f459d842..4491a1b22 100644 --- a/src/font/freetype-2.10.2/src/sfnt/module.mk +++ b/3rdparty/freetype-2.13.2/src/sfnt/module.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 1996-2020 by +# Copyright (C) 1996-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, diff --git a/src/font/freetype-2.10.2/src/sfnt/pngshim.c b/3rdparty/freetype-2.13.2/src/sfnt/pngshim.c similarity index 92% rename from src/font/freetype-2.10.2/src/sfnt/pngshim.c rename to 3rdparty/freetype-2.13.2/src/sfnt/pngshim.c index 523b30a74..33712162e 100644 --- a/src/font/freetype-2.10.2/src/sfnt/pngshim.c +++ b/3rdparty/freetype-2.13.2/src/sfnt/pngshim.c @@ -4,7 +4,7 @@ * * PNG Bitmap glyph support. * - * Copyright (C) 2013-2020 by + * Copyright (C) 2013-2023 by * Google, Inc. * Written by Stuart Gill and Behdad Esfahbod. * @@ -17,10 +17,9 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_STREAM_H -#include FT_TRUETYPE_TAGS_H +#include +#include +#include #include FT_CONFIG_STANDARD_LIBRARY_H @@ -61,7 +60,12 @@ /* predates clang; the `__BYTE_ORDER__' preprocessor symbol was */ /* introduced in gcc 4.6 and clang 3.2, respectively. */ /* `__builtin_shuffle' for gcc was introduced in gcc 4.7.0. */ -#if ( ( defined( __GNUC__ ) && \ + /* */ + /* Intel compilers do not currently support __builtin_shuffle; */ + + /* The Intel check must be first. */ +#if !defined( __INTEL_COMPILER ) && \ + ( ( defined( __GNUC__ ) && \ ( ( __GNUC__ >= 5 ) || \ ( ( __GNUC__ == 4 ) && ( __GNUC_MINOR__ >= 7 ) ) ) ) || \ ( defined( __clang__ ) && \ @@ -235,7 +239,7 @@ *e = FT_THROW( Invalid_Stream_Read ); png_error( png, NULL ); - return; + /* return; (never reached) */ } ft_memcpy( data, stream->cursor, length ); @@ -266,7 +270,10 @@ int bitdepth, color_type, interlace; FT_Int i; - png_byte* *rows = NULL; /* pacify compiler */ + + /* `rows` gets modified within a 'setjmp' scope; */ + /* we thus need the `volatile` keyword. */ + png_byte* *volatile rows = NULL; if ( x_offset < 0 || @@ -328,6 +335,13 @@ if ( populate_map_and_metrics ) { + /* reject too large bitmaps similarly to the rasterizer */ + if ( imgHeight > 0x7FFF || imgWidth > 0x7FFF ) + { + error = FT_THROW( Array_Too_Large ); + goto DestroyExit; + } + metrics->width = (FT_UShort)imgWidth; metrics->height = (FT_UShort)imgHeight; @@ -336,13 +350,6 @@ map->pixel_mode = FT_PIXEL_MODE_BGRA; map->pitch = (int)( map->width * 4 ); map->num_grays = 256; - - /* reject too large bitmaps similarly to the rasterizer */ - if ( map->rows > 0x7FFF || map->width > 0x7FFF ) - { - error = FT_THROW( Array_Too_Large ); - goto DestroyExit; - } } /* convert palette/gray image to rgb */ @@ -360,7 +367,7 @@ } /* transform transparency to alpha */ - if ( png_get_valid(png, info, PNG_INFO_tRNS ) ) + if ( png_get_valid( png, info, PNG_INFO_tRNS ) ) png_set_tRNS_to_alpha( png ); if ( bitdepth == 16 ) @@ -380,7 +387,7 @@ png_set_filler( png, 0xFF, PNG_FILLER_AFTER ); /* recheck header after setting EXPAND options */ - png_read_update_info(png, info ); + png_read_update_info( png, info ); png_get_IHDR( png, info, &imgWidth, &imgHeight, &bitdepth, &color_type, &interlace, @@ -399,9 +406,7 @@ switch ( color_type ) { - default: - /* Shouldn't happen, but fall through. */ - + default: /* Shouldn't happen, but ... */ case PNG_COLOR_TYPE_RGB_ALPHA: png_set_read_user_transform_fn( png, premultiply_data ); break; @@ -423,7 +428,7 @@ goto DestroyExit; } - if ( FT_NEW_ARRAY( rows, imgHeight ) ) + if ( FT_QNEW_ARRAY( rows, imgHeight ) ) { error = FT_THROW( Out_Of_Memory ); goto DestroyExit; @@ -434,11 +439,11 @@ png_read_image( png, rows ); - FT_FREE( rows ); - png_read_end( png, info ); DestroyExit: + /* even if reading fails with longjmp, rows must be freed */ + FT_FREE( rows ); png_destroy_read_struct( &png, &info, NULL ); FT_Stream_Close( &stream ); @@ -449,7 +454,7 @@ #else /* !(TT_CONFIG_OPTION_EMBEDDED_BITMAPS && FT_CONFIG_OPTION_USE_PNG) */ /* ANSI C doesn't like empty source files */ - typedef int _pngshim_dummy; + typedef int pngshim_dummy_; #endif /* !(TT_CONFIG_OPTION_EMBEDDED_BITMAPS && FT_CONFIG_OPTION_USE_PNG) */ diff --git a/src/font/freetype-2.10.2/src/sfnt/pngshim.h b/3rdparty/freetype-2.13.2/src/sfnt/pngshim.h similarity index 95% rename from src/font/freetype-2.10.2/src/sfnt/pngshim.h rename to 3rdparty/freetype-2.13.2/src/sfnt/pngshim.h index d2c9e2b9b..903bd2bc3 100644 --- a/src/font/freetype-2.10.2/src/sfnt/pngshim.h +++ b/3rdparty/freetype-2.13.2/src/sfnt/pngshim.h @@ -4,7 +4,7 @@ * * PNG Bitmap glyph support. * - * Copyright (C) 2013-2020 by + * Copyright (C) 2013-2023 by * Google, Inc. * Written by Stuart Gill and Behdad Esfahbod. * @@ -21,7 +21,6 @@ #define PNGSHIM_H_ -#include #include "ttload.h" diff --git a/src/font/freetype-2.10.2/src/sfnt/rules.mk b/3rdparty/freetype-2.13.2/src/sfnt/rules.mk similarity index 96% rename from src/font/freetype-2.10.2/src/sfnt/rules.mk rename to 3rdparty/freetype-2.13.2/src/sfnt/rules.mk index f56ef060e..4d2d7e8d8 100644 --- a/src/font/freetype-2.10.2/src/sfnt/rules.mk +++ b/3rdparty/freetype-2.13.2/src/sfnt/rules.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 1996-2020 by +# Copyright (C) 1996-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, @@ -36,6 +36,7 @@ SFNT_DRV_SRC := $(SFNT_DIR)/pngshim.c \ $(SFNT_DIR)/ttbdf.c \ $(SFNT_DIR)/ttcmap.c \ $(SFNT_DIR)/ttcolr.c \ + $(SFNT_DIR)/ttsvg.c \ $(SFNT_DIR)/ttcpal.c \ $(SFNT_DIR)/ttkern.c \ $(SFNT_DIR)/ttload.c \ diff --git a/src/font/freetype-2.10.2/src/sfnt/sfdriver.c b/3rdparty/freetype-2.13.2/src/sfnt/sfdriver.c similarity index 82% rename from src/font/freetype-2.10.2/src/sfnt/sfdriver.c rename to 3rdparty/freetype-2.13.2/src/sfnt/sfdriver.c index 6ca4f3c26..0925940b0 100644 --- a/src/font/freetype-2.10.2/src/sfnt/sfdriver.c +++ b/3rdparty/freetype-2.13.2/src/sfnt/sfdriver.c @@ -4,7 +4,7 @@ * * High-level SFNT driver interface (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,11 +16,10 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_SFNT_H -#include FT_INTERNAL_OBJECTS_H -#include FT_TRUETYPE_IDS_H +#include +#include +#include +#include #include "sfdriver.h" #include "ttload.h" @@ -37,27 +36,31 @@ #include "ttcpal.h" #endif +#ifdef FT_CONFIG_OPTION_SVG +#include "ttsvg.h" +#endif + #ifdef TT_CONFIG_OPTION_POSTSCRIPT_NAMES #include "ttpost.h" #endif #ifdef TT_CONFIG_OPTION_BDF #include "ttbdf.h" -#include FT_SERVICE_BDF_H +#include #endif #include "ttcmap.h" #include "ttkern.h" #include "ttmtx.h" -#include FT_SERVICE_GLYPH_DICT_H -#include FT_SERVICE_POSTSCRIPT_NAME_H -#include FT_SERVICE_SFNT_H -#include FT_SERVICE_TT_CMAP_H +#include +#include +#include +#include #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT -#include FT_MULTIPLE_MASTERS_H -#include FT_SERVICE_MULTIPLE_MASTERS_H +#include +#include #endif @@ -76,41 +79,57 @@ * */ - static void* - get_sfnt_table( TT_Face face, + FT_CALLBACK_DEF( FT_Error ) + sfnt_load_table( FT_Face face, /* TT_Face */ + FT_ULong tag, + FT_Long offset, + FT_Byte* buffer, + FT_ULong* length ) + { + TT_Face ttface = (TT_Face)face; + + + return tt_face_load_any( ttface, tag, offset, buffer, length ); + } + + + FT_CALLBACK_DEF( void* ) + get_sfnt_table( FT_Face face, /* TT_Face */ FT_Sfnt_Tag tag ) { + TT_Face ttface = (TT_Face)face; + void* table; switch ( tag ) { case FT_SFNT_HEAD: - table = &face->header; + table = &ttface->header; break; case FT_SFNT_HHEA: - table = &face->horizontal; + table = &ttface->horizontal; break; case FT_SFNT_VHEA: - table = face->vertical_info ? &face->vertical : NULL; + table = ttface->vertical_info ? &ttface->vertical : NULL; break; case FT_SFNT_OS2: - table = ( face->os2.version == 0xFFFFU ) ? NULL : &face->os2; + table = ( ttface->os2.version == 0xFFFFU ) ? NULL : &ttface->os2; break; case FT_SFNT_POST: - table = &face->postscript; + table = &ttface->postscript; break; case FT_SFNT_MAXP: - table = &face->max_profile; + table = &ttface->max_profile; break; case FT_SFNT_PCLT: - table = face->pclt.Version ? &face->pclt : NULL; + table = ttface->pclt.Version ? &ttface->pclt : NULL; break; default: @@ -121,26 +140,29 @@ } - static FT_Error - sfnt_table_info( TT_Face face, + FT_CALLBACK_DEF( FT_Error ) + sfnt_table_info( FT_Face face, /* TT_Face */ FT_UInt idx, FT_ULong *tag, FT_ULong *offset, FT_ULong *length ) { + TT_Face ttface = (TT_Face)face; + + if ( !offset || !length ) return FT_THROW( Invalid_Argument ); if ( !tag ) - *length = face->num_tables; + *length = ttface->num_tables; else { - if ( idx >= face->num_tables ) + if ( idx >= ttface->num_tables ) return FT_THROW( Table_Missing ); - *tag = face->dir_tables[idx].Tag; - *offset = face->dir_tables[idx].Offset; - *length = face->dir_tables[idx].Length; + *tag = ttface->dir_tables[idx].Tag; + *offset = ttface->dir_tables[idx].Offset; + *length = ttface->dir_tables[idx].Length; } return FT_Err_Ok; @@ -150,9 +172,9 @@ FT_DEFINE_SERVICE_SFNT_TABLEREC( sfnt_service_sfnt_table, - (FT_SFNT_TableLoadFunc)tt_face_load_any, /* load_table */ - (FT_SFNT_TableGetFunc) get_sfnt_table, /* get_table */ - (FT_SFNT_TableInfoFunc)sfnt_table_info /* table_info */ + sfnt_load_table, /* FT_SFNT_TableLoadFunc load_table */ + get_sfnt_table, /* FT_SFNT_TableGetFunc get_table */ + sfnt_table_info /* FT_SFNT_TableInfoFunc table_info */ ) @@ -163,7 +185,7 @@ * */ - static FT_Error + FT_CALLBACK_DEF( FT_Error ) sfnt_get_glyph_name( FT_Face face, FT_UInt glyph_index, FT_Pointer buffer, @@ -181,7 +203,7 @@ } - static FT_UInt + FT_CALLBACK_DEF( FT_UInt ) sfnt_get_name_index( FT_Face face, const FT_String* glyph_name ) { @@ -195,7 +217,7 @@ else if ( (FT_ULong)face->num_glyphs < FT_UINT_MAX ) max_gid = (FT_UInt)face->num_glyphs; else - FT_TRACE0(( "Ignore glyph names for invalid GID 0x%08x - 0x%08x\n", + FT_TRACE0(( "Ignore glyph names for invalid GID 0x%08x - 0x%08lx\n", FT_UINT_MAX, face->num_glyphs )); for ( i = 0; i < max_gid; i++ ) @@ -218,8 +240,8 @@ FT_DEFINE_SERVICE_GLYPHDICTREC( sfnt_service_glyph_dict, - (FT_GlyphDict_GetNameFunc) sfnt_get_glyph_name, /* get_name */ - (FT_GlyphDict_NameIndexFunc)sfnt_get_name_index /* name_index */ + sfnt_get_glyph_name, /* FT_GlyphDict_GetNameFunc get_name */ + sfnt_get_name_index /* FT_GlyphDict_NameIndexFunc name_index */ ) #endif /* TT_CONFIG_OPTION_POSTSCRIPT_NAMES */ @@ -375,61 +397,61 @@ { case 15: k4 ^= (FT_UInt32)tail[14] << 16; - /* fall through */ + FALL_THROUGH; case 14: k4 ^= (FT_UInt32)tail[13] << 8; - /* fall through */ + FALL_THROUGH; case 13: k4 ^= (FT_UInt32)tail[12]; k4 *= c4; k4 = ROTL32( k4, 18 ); k4 *= c1; h4 ^= k4; - /* fall through */ + FALL_THROUGH; case 12: k3 ^= (FT_UInt32)tail[11] << 24; - /* fall through */ + FALL_THROUGH; case 11: k3 ^= (FT_UInt32)tail[10] << 16; - /* fall through */ + FALL_THROUGH; case 10: k3 ^= (FT_UInt32)tail[9] << 8; - /* fall through */ + FALL_THROUGH; case 9: k3 ^= (FT_UInt32)tail[8]; k3 *= c3; k3 = ROTL32( k3, 17 ); k3 *= c4; h3 ^= k3; - /* fall through */ + FALL_THROUGH; case 8: k2 ^= (FT_UInt32)tail[7] << 24; - /* fall through */ + FALL_THROUGH; case 7: k2 ^= (FT_UInt32)tail[6] << 16; - /* fall through */ + FALL_THROUGH; case 6: k2 ^= (FT_UInt32)tail[5] << 8; - /* fall through */ + FALL_THROUGH; case 5: k2 ^= (FT_UInt32)tail[4]; k2 *= c2; k2 = ROTL32( k2, 16 ); k2 *= c3; h2 ^= k2; - /* fall through */ + FALL_THROUGH; case 4: k1 ^= (FT_UInt32)tail[3] << 24; - /* fall through */ + FALL_THROUGH; case 3: k1 ^= (FT_UInt32)tail[2] << 16; - /* fall through */ + FALL_THROUGH; case 2: k1 ^= (FT_UInt32)tail[1] << 8; - /* fall through */ + FALL_THROUGH; case 1: k1 ^= (FT_UInt32)tail[0]; k1 *= c1; @@ -492,17 +514,15 @@ char_type_func char_type, FT_Bool report_invalid_characters ) { - FT_Error error = FT_Err_Ok; + FT_Error error; char* result = NULL; FT_String* r; FT_Char* p; FT_UInt len; - FT_UNUSED( error ); - - if ( FT_ALLOC( result, entry->stringLength / 2 + 1 ) ) + if ( FT_QALLOC( result, entry->stringLength / 2 + 1 ) ) return NULL; if ( FT_STREAM_SEEK( entry->stringOffset ) || @@ -522,15 +542,14 @@ FT_TRACE0(( "get_win_string:" " Character 0x%X invalid in PS name string\n", ((unsigned)p[0])*256 + (unsigned)p[1] )); - break; + continue; } } - if ( !len ) - *r = '\0'; + *r = '\0'; FT_FRAME_EXIT(); - if ( !len ) + if ( r != result ) return result; get_win_string_error: @@ -551,17 +570,15 @@ char_type_func char_type, FT_Bool report_invalid_characters ) { - FT_Error error = FT_Err_Ok; + FT_Error error; char* result = NULL; FT_String* r; FT_Char* p; FT_UInt len; - FT_UNUSED( error ); - - if ( FT_ALLOC( result, entry->stringLength + 1 ) ) + if ( FT_QALLOC( result, entry->stringLength + 1 ) ) return NULL; if ( FT_STREAM_SEEK( entry->stringOffset ) || @@ -581,15 +598,14 @@ FT_TRACE0(( "get_apple_string:" " Character `%c' (0x%X) invalid in PS name string\n", *p, *p )); - break; + continue; } } - if ( !len ) - *r = '\0'; + *r = '\0'; FT_FRAME_EXIT(); - if ( !len ) + if ( r != result ) return result; get_apple_string_error: @@ -603,7 +619,7 @@ } - static FT_Bool + FT_CALLBACK_DEF( FT_Bool ) sfnt_get_name_id( TT_Face face, FT_UShort id, FT_Int *win, @@ -658,7 +674,7 @@ /* - * Find the shortest decimal representation of a 16.16 fixed point + * Find the shortest decimal representation of a 16.16 fixed-point * number. The function fills `buf' with the result, returning a pointer * to the position after the representation's last byte. */ @@ -734,7 +750,7 @@ an equivalent representation of `fixed'. The above FOR loop always finds the larger of the two values; I - verified this by iterating over all possible fixed point numbers. + verified this by iterating over all possible fixed-point numbers. If the remainder is 17232*10, both values are equally good, and we take the next even number (following IEEE 754's `round to nearest, @@ -742,7 +758,7 @@ If the remainder is smaller than 17232*10, the lower of the two numbers is nearer to the exact result (values 17232 and 34480 were - also found by testing all possible fixed point values). + also found by testing all possible fixed-point values). We use this to find a shorter decimal representation. If not ending with digit zero, we take the representation with less error. @@ -820,9 +836,9 @@ if ( !found ) { - /* as a last resort we try the family name; note that this is */ - /* not in the Adobe TechNote, but GX fonts (which predate the */ - /* TechNote) benefit from this behaviour */ + /* according to the 'name' documentation in the OpenType */ + /* specification the font family name is to be used if the */ + /* typographic family name is missing, so let's do that */ found = sfnt_get_name_id( face, TT_NAME_ID_FONT_FAMILY, &win, @@ -854,6 +870,10 @@ { FT_TRACE0(( "sfnt_get_var_ps_name:" " No valid PS name prefix for font instances found\n" )); + /* XXX It probably makes sense to never let this fail */ + /* since an arbitrary prefix should work, too. */ + /* On the other hand, it is very unlikely that */ + /* we ever reach this code at all. */ return NULL; } @@ -869,8 +889,8 @@ result[len] = '\0'; FT_TRACE0(( "sfnt_get_var_ps_name:" - " Shortening variation PS name prefix\n" - " " + " Shortening variation PS name prefix\n" )); + FT_TRACE0(( " " " to %d characters\n", len )); } @@ -921,16 +941,16 @@ if ( !subfamily_name ) { FT_TRACE1(( "sfnt_get_var_ps_name:" - " can't construct named instance PS name;\n" - " " + " can't construct named instance PS name;\n" )); + FT_TRACE1(( " " " trying to construct normal instance PS name\n" )); goto construct_instance_name; } /* after the prefix we have character `-' followed by the */ /* subfamily name (using only characters a-z, A-Z, and 0-9) */ - if ( FT_ALLOC( result, face->var_postscript_prefix_len + - 1 + ft_strlen( subfamily_name ) + 1 ) ) + if ( FT_QALLOC( result, face->var_postscript_prefix_len + + 1 + ft_strlen( subfamily_name ) + 1 ) ) return NULL; ft_strcpy( result, face->var_postscript_prefix ); @@ -958,9 +978,9 @@ construct_instance_name: axis = mm_var->axis; - if ( FT_ALLOC( result, - face->var_postscript_prefix_len + - num_coords * MAX_VALUE_DESCRIPTOR_LEN + 1 ) ) + if ( FT_QALLOC( result, + face->var_postscript_prefix_len + + num_coords * MAX_VALUE_DESCRIPTOR_LEN + 1 ) ) return NULL; p = result; @@ -994,6 +1014,7 @@ if ( t != ' ' && ft_isalnum( t ) ) *p++ = t; } + *p++ = '\0'; } check_length: @@ -1041,47 +1062,49 @@ #endif /* TT_CONFIG_OPTION_GX_VAR_SUPPORT */ - static const char* - sfnt_get_ps_name( TT_Face face ) + FT_CALLBACK_DEF( const char* ) + sfnt_get_ps_name( FT_Face face ) /* TT_Face */ { + TT_Face ttface = (TT_Face)face; + FT_Int found, win, apple; const char* result = NULL; - if ( face->postscript_name ) - return face->postscript_name; + if ( ttface->postscript_name ) + return ttface->postscript_name; #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT - if ( face->blend && - ( FT_IS_NAMED_INSTANCE( FT_FACE( face ) ) || - FT_IS_VARIATION( FT_FACE( face ) ) ) ) + if ( ttface->blend && + ( FT_IS_NAMED_INSTANCE( face ) || + FT_IS_VARIATION( face ) ) ) { - face->postscript_name = sfnt_get_var_ps_name( face ); - return face->postscript_name; + ttface->postscript_name = sfnt_get_var_ps_name( ttface ); + return ttface->postscript_name; } #endif /* scan the name table to see whether we have a Postscript name here, */ /* either in Macintosh or Windows platform encodings */ - found = sfnt_get_name_id( face, TT_NAME_ID_PS_NAME, &win, &apple ); + found = sfnt_get_name_id( ttface, TT_NAME_ID_PS_NAME, &win, &apple ); if ( !found ) return NULL; /* prefer Windows entries over Apple */ if ( win != -1 ) - result = get_win_string( face->root.memory, - face->name_table.stream, - face->name_table.names + win, + result = get_win_string( FT_FACE_MEMORY( face ), + ttface->name_table.stream, + ttface->name_table.names + win, sfnt_is_postscript, 1 ); if ( !result && apple != -1 ) - result = get_apple_string( face->root.memory, - face->name_table.stream, - face->name_table.names + apple, + result = get_apple_string( FT_FACE_MEMORY( face ), + ttface->name_table.stream, + ttface->name_table.names + apple, sfnt_is_postscript, 1 ); - face->postscript_name = result; + ttface->postscript_name = result; return result; } @@ -1090,7 +1113,7 @@ FT_DEFINE_SERVICE_PSFONTNAMEREC( sfnt_service_ps_name, - (FT_PsName_GetFunc)sfnt_get_ps_name /* get_ps_font_name */ + sfnt_get_ps_name /* FT_PsName_GetFunc get_ps_font_name */ ) @@ -1100,14 +1123,14 @@ FT_DEFINE_SERVICE_TTCMAPSREC( tt_service_get_cmap_info, - (TT_CMap_Info_GetFunc)tt_get_cmap_info /* get_cmap_info */ + tt_get_cmap_info /* TT_CMap_Info_GetFunc get_cmap_info */ ) #ifdef TT_CONFIG_OPTION_BDF static FT_Error - sfnt_get_charset_id( TT_Face face, + sfnt_get_charset_id( FT_Face face, const char* *acharset_encoding, const char* *acharset_registry ) { @@ -1145,8 +1168,8 @@ FT_DEFINE_SERVICE_BDFRec( sfnt_service_bdf, - (FT_BDF_GetCharsetIdFunc)sfnt_get_charset_id, /* get_charset_id */ - (FT_BDF_GetPropertyFunc) tt_face_find_bdf_prop /* get_property */ + sfnt_get_charset_id, /* FT_BDF_GetCharsetIdFunc get_charset_id */ + tt_face_find_bdf_prop /* FT_BDF_GetPropertyFunc get_property */ ) @@ -1214,6 +1237,14 @@ #define PUT_COLOR_LAYERS( a ) NULL #endif +#ifdef FT_CONFIG_OPTION_SVG +#define PUT_SVG_SUPPORT( a ) a +#else +#define PUT_SVG_SUPPORT( a ) NULL +#endif + +#define PUT_COLOR_LAYERS_V1( a ) PUT_COLOR_LAYERS( a ) + #ifdef TT_CONFIG_OPTION_POSTSCRIPT_NAMES #define PUT_PS_NAMES( a ) a #else @@ -1272,9 +1303,9 @@ /* TT_Free_Table_Func free_eblc */ PUT_EMBEDDED_BITMAPS( tt_face_set_sbit_strike ), - /* TT_Set_SBit_Strike_Func set_sbit_strike */ + /* TT_Set_SBit_Strike_Func set_sbit_strike */ PUT_EMBEDDED_BITMAPS( tt_face_load_strike_metrics ), - /* TT_Load_Strike_Metrics_Func load_strike_metrics */ + /* TT_Load_Strike_Metrics_Func load_strike_metrics */ PUT_COLOR_LAYERS( tt_face_load_cpal ), /* TT_Load_Table_Func load_cpal */ @@ -1288,13 +1319,32 @@ /* TT_Set_Palette_Func set_palette */ PUT_COLOR_LAYERS( tt_face_get_colr_layer ), /* TT_Get_Colr_Layer_Func get_colr_layer */ + + PUT_COLOR_LAYERS_V1( tt_face_get_colr_glyph_paint ), + /* TT_Get_Color_Glyph_Paint_Func get_colr_glyph_paint */ + PUT_COLOR_LAYERS_V1( tt_face_get_color_glyph_clipbox ), + /* TT_Get_Color_Glyph_ClipBox_Func get_clipbox */ + PUT_COLOR_LAYERS_V1( tt_face_get_paint_layers ), + /* TT_Get_Paint_Layers_Func get_paint_layers */ + PUT_COLOR_LAYERS_V1( tt_face_get_colorline_stops ), + /* TT_Get_Paint get_paint */ + PUT_COLOR_LAYERS_V1( tt_face_get_paint ), + /* TT_Get_Colorline_Stops_Func get_colorline_stops */ + PUT_COLOR_LAYERS( tt_face_colr_blend_layer ), /* TT_Blend_Colr_Func colr_blend */ tt_face_get_metrics, /* TT_Get_Metrics_Func get_metrics */ tt_face_get_name, /* TT_Get_Name_Func get_name */ - sfnt_get_name_id /* TT_Get_Name_ID_Func get_name_id */ + sfnt_get_name_id, /* TT_Get_Name_ID_Func get_name_id */ + + PUT_SVG_SUPPORT( tt_face_load_svg ), + /* TT_Load_Table_Func load_svg */ + PUT_SVG_SUPPORT( tt_face_free_svg ), + /* TT_Free_Table_Func free_svg */ + PUT_SVG_SUPPORT( tt_face_load_svg_doc ) + /* TT_Load_Svg_Doc_Func load_svg_doc */ ) @@ -1310,9 +1360,9 @@ (const void*)&sfnt_interface, /* module specific interface */ - (FT_Module_Constructor)NULL, /* module_init */ - (FT_Module_Destructor) NULL, /* module_done */ - (FT_Module_Requester) sfnt_get_interface /* get_interface */ + NULL, /* FT_Module_Constructor module_init */ + NULL, /* FT_Module_Destructor module_done */ + sfnt_get_interface /* FT_Module_Requester get_interface */ ) diff --git a/src/font/freetype-2.10.2/src/sfnt/sfdriver.h b/3rdparty/freetype-2.13.2/src/sfnt/sfdriver.h similarity index 90% rename from src/font/freetype-2.10.2/src/sfnt/sfdriver.h rename to 3rdparty/freetype-2.13.2/src/sfnt/sfdriver.h index d108ee200..2445958b6 100644 --- a/src/font/freetype-2.10.2/src/sfnt/sfdriver.h +++ b/3rdparty/freetype-2.13.2/src/sfnt/sfdriver.h @@ -4,7 +4,7 @@ * * High-level SFNT driver interface (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,8 +20,7 @@ #define SFDRIVER_H_ -#include -#include FT_MODULE_H +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/src/sfnt/sferrors.h b/3rdparty/freetype-2.13.2/src/sfnt/sferrors.h similarity index 90% rename from src/font/freetype-2.10.2/src/sfnt/sferrors.h rename to 3rdparty/freetype-2.13.2/src/sfnt/sferrors.h index fbfca0e52..e7a8eb04b 100644 --- a/src/font/freetype-2.10.2/src/sfnt/sferrors.h +++ b/3rdparty/freetype-2.13.2/src/sfnt/sferrors.h @@ -4,7 +4,7 @@ * * SFNT error codes (specification only). * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -25,7 +25,7 @@ #ifndef SFERRORS_H_ #define SFERRORS_H_ -#include FT_MODULE_ERRORS_H +#include #undef FTERRORS_H_ @@ -33,7 +33,7 @@ #define FT_ERR_PREFIX SFNT_Err_ #define FT_ERR_BASE FT_Mod_Err_SFNT -#include FT_ERRORS_H +#include #endif /* SFERRORS_H_ */ diff --git a/src/font/freetype-2.10.2/src/sfnt/sfnt.c b/3rdparty/freetype-2.13.2/src/sfnt/sfnt.c similarity index 94% rename from src/font/freetype-2.10.2/src/sfnt/sfnt.c rename to 3rdparty/freetype-2.13.2/src/sfnt/sfnt.c index 9db7935ae..8e4f08a90 100644 --- a/src/font/freetype-2.10.2/src/sfnt/sfnt.c +++ b/3rdparty/freetype-2.13.2/src/sfnt/sfnt.c @@ -4,7 +4,7 @@ * * Single object library component. * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -17,7 +17,6 @@ #define FT_MAKE_OPTION_SINGLE_OBJECT -#include #include "pngshim.c" #include "sfdriver.c" @@ -28,6 +27,7 @@ #include "ttcmap.c" #include "ttcolr.c" #include "ttcpal.c" +#include "ttsvg.c" #include "ttkern.c" #include "ttload.c" diff --git a/src/font/freetype-2.10.2/src/sfnt/sfobjs.c b/3rdparty/freetype-2.13.2/src/sfnt/sfobjs.c similarity index 91% rename from src/font/freetype-2.10.2/src/sfnt/sfobjs.c rename to 3rdparty/freetype-2.13.2/src/sfnt/sfobjs.c index 2c66a9b64..f5d66ef84 100644 --- a/src/font/freetype-2.10.2/src/sfnt/sfobjs.c +++ b/3rdparty/freetype-2.13.2/src/sfnt/sfobjs.c @@ -4,7 +4,7 @@ * * SFNT object management (base). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,23 +16,22 @@ */ -#include #include "sfobjs.h" #include "ttload.h" #include "ttcmap.h" #include "ttkern.h" #include "sfwoff.h" #include "sfwoff2.h" -#include FT_INTERNAL_SFNT_H -#include FT_INTERNAL_DEBUG_H -#include FT_TRUETYPE_IDS_H -#include FT_TRUETYPE_TAGS_H -#include FT_SERVICE_POSTSCRIPT_CMAPS_H -#include FT_SFNT_NAMES_H +#include +#include +#include +#include +#include +#include #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT -#include FT_SERVICE_MULTIPLE_MASTERS_H -#include FT_SERVICE_METRICS_VARIATIONS_H +#include +#include #endif #include "sferrors.h" @@ -66,7 +65,7 @@ len = (FT_UInt)entry->stringLength / 2; - if ( FT_NEW_ARRAY( string, len + 1 ) ) + if ( FT_QNEW_ARRAY( string, len + 1 ) ) return NULL; for ( n = 0; n < len; n++ ) @@ -101,7 +100,7 @@ len = (FT_UInt)entry->stringLength; - if ( FT_NEW_ARRAY( string, len + 1 ) ) + if ( FT_QNEW_ARRAY( string, len + 1 ) ) return NULL; for ( n = 0; n < len; n++ ) @@ -361,17 +360,27 @@ FT_FRAME_END }; +#ifndef FT_CONFIG_OPTION_USE_BROTLI + FT_UNUSED( face_instance_index ); + FT_UNUSED( woff2_num_faces ); +#endif + face->ttc_header.tag = 0; face->ttc_header.version = 0; face->ttc_header.count = 0; +#if defined( FT_CONFIG_OPTION_USE_ZLIB ) || \ + defined( FT_CONFIG_OPTION_USE_BROTLI ) retry: +#endif + offset = FT_STREAM_POS(); if ( FT_READ_ULONG( tag ) ) return error; +#ifdef FT_CONFIG_OPTION_USE_ZLIB if ( tag == TTAG_wOFF ) { FT_TRACE2(( "sfnt_open_font: file is a WOFF; synthesizing SFNT\n" )); @@ -387,7 +396,9 @@ stream = face->root.stream; goto retry; } +#endif +#ifdef FT_CONFIG_OPTION_USE_BROTLI if ( tag == TTAG_wOF2 ) { FT_TRACE2(( "sfnt_open_font: file is a WOFF2; synthesizing SFNT\n" )); @@ -406,6 +417,7 @@ stream = face->root.stream; goto retry; } +#endif if ( tag != 0x00010000UL && tag != TTAG_ttcf && @@ -447,7 +459,7 @@ return FT_THROW( Array_Too_Large ); /* now read the offsets of each font in the file */ - if ( FT_NEW_ARRAY( face->ttc_header.offsets, face->ttc_header.count ) ) + if ( FT_QNEW_ARRAY( face->ttc_header.offsets, face->ttc_header.count ) ) return error; if ( FT_FRAME_ENTER( face->ttc_header.count * 4L ) ) @@ -465,7 +477,7 @@ face->ttc_header.version = 1 << 16; face->ttc_header.count = 1; - if ( FT_NEW( face->ttc_header.offsets ) ) + if ( FT_QNEW( face->ttc_header.offsets ) ) return error; face->ttc_header.offsets[0] = offset; @@ -522,17 +534,23 @@ 0 ); } - if ( !face->var ) + if ( !face->tt_var ) { /* we want the metrics variations interface */ /* from the `truetype' module only */ FT_Module tt_module = FT_Get_Module( library, "truetype" ); - face->var = ft_module_get_service( tt_module, - FT_SERVICE_ID_METRICS_VARIATIONS, - 0 ); + face->tt_var = ft_module_get_service( tt_module, + FT_SERVICE_ID_METRICS_VARIATIONS, + 0 ); } + + if ( !face->face_var ) + face->face_var = ft_module_get_service( + &face->root.driver->root, + FT_SERVICE_ID_METRICS_VARIATIONS, + 0 ); #endif FT_TRACE2(( "SFNT driver\n" )); @@ -547,14 +565,14 @@ /* Stream may have changed in sfnt_open_font. */ stream = face->root.stream; - FT_TRACE2(( "sfnt_init_face: %08p (index %d)\n", - face, + FT_TRACE2(( "sfnt_init_face: %p (index %d)\n", + (void *)face, face_instance_index )); face_index = FT_ABS( face_instance_index ) & 0xFFFF; /* value -(N+1) requests information on index N */ - if ( face_instance_index < 0 ) + if ( face_instance_index < 0 && face_index > 0 ) face_index--; if ( face_index >= face->ttc_header.count ) @@ -644,8 +662,8 @@ */ if ( ( face->variation_support & TT_FACE_FLAG_VAR_FVAR ) && - !( FT_ALLOC( default_values, num_axes * 4 ) || - FT_ALLOC( instance_values, num_axes * 4 ) ) ) + !( FT_QALLOC( default_values, num_axes * 4 ) || + FT_QALLOC( instance_values, num_axes * 4 ) ) ) { /* the current stream position is 16 bytes after the table start */ FT_ULong array_start = FT_STREAM_POS() - 16 + offset; @@ -680,6 +698,9 @@ instance_offset += instance_size; } + /* named instance indices start with value 1 */ + face->var_default_named_instance = i + 1; + if ( i == num_instances ) { /* no default instance in named instance table; */ @@ -772,17 +793,23 @@ FT_Int num_params, FT_Parameter* params ) { - FT_Error error; + FT_Error error; #ifdef TT_CONFIG_OPTION_POSTSCRIPT_NAMES - FT_Error psnames_error; + FT_Error psnames_error; #endif - FT_Bool has_outline; - FT_Bool is_apple_sbit; - FT_Bool is_apple_sbix; - FT_Bool has_CBLC; - FT_Bool has_CBDT; - FT_Bool ignore_typographic_family = FALSE; - FT_Bool ignore_typographic_subfamily = FALSE; + + FT_Bool has_outline; + FT_Bool is_apple_sbit; + + FT_Bool has_CBLC; + FT_Bool has_CBDT; + FT_Bool has_EBLC; + FT_Bool has_bloc; + FT_Bool has_sbix; + + FT_Bool ignore_typographic_family = FALSE; + FT_Bool ignore_typographic_subfamily = FALSE; + FT_Bool ignore_sbix = FALSE; SFNT_Service sfnt = (SFNT_Service)face->sfnt; @@ -801,6 +828,8 @@ ignore_typographic_family = TRUE; else if ( params[i].tag == FT_PARAM_TAG_IGNORE_TYPOGRAPHIC_SUBFAMILY ) ignore_typographic_subfamily = TRUE; + else if ( params[i].tag == FT_PARAM_TAG_IGNORE_SBIX ) + ignore_sbix = TRUE; } } @@ -821,7 +850,8 @@ /* it doesn't contain outlines. */ /* */ - FT_TRACE2(( "sfnt_load_face: %08p\n\n", face )); + FT_TRACE2(( "sfnt_load_face: %p\n", (void *)face )); + FT_TRACE2(( "\n" )); /* do we have outlines in there? */ #ifdef FT_CONFIG_OPTION_INCREMENTAL @@ -835,14 +865,17 @@ tt_face_lookup_table( face, TTAG_CFF2 ) ); #endif - is_apple_sbit = 0; - is_apple_sbix = !face->goto_table( face, TTAG_sbix, stream, 0 ); + /* check which sbit formats are present */ + has_CBLC = !face->goto_table( face, TTAG_CBLC, stream, 0 ); + has_CBDT = !face->goto_table( face, TTAG_CBDT, stream, 0 ); + has_EBLC = !face->goto_table( face, TTAG_EBLC, stream, 0 ); + has_bloc = !face->goto_table( face, TTAG_bloc, stream, 0 ); + has_sbix = !face->goto_table( face, TTAG_sbix, stream, 0 ); - /* Apple 'sbix' color bitmaps are rendered scaled and then the 'glyf' - * outline rendered on top. We don't support that yet, so just ignore - * the 'glyf' outline and advertise it as a bitmap-only font. */ - if ( is_apple_sbix ) - has_outline = FALSE; + is_apple_sbit = FALSE; + + if ( ignore_sbix ) + has_sbix = FALSE; /* if this font doesn't contain outlines, we try to load */ /* a `bhed' table */ @@ -854,16 +887,13 @@ /* load the font header (`head' table) if this isn't an Apple */ /* sbit font file */ - if ( !is_apple_sbit || is_apple_sbix ) + if ( !is_apple_sbit || has_sbix ) { LOAD_( head ); if ( error ) goto Exit; } - has_CBLC = !face->goto_table( face, TTAG_CBLC, stream, 0 ); - has_CBDT = !face->goto_table( face, TTAG_CBDT, stream, 0 ); - /* Ignore outlines for CBLC/CBDT fonts. */ if ( has_CBLC || has_CBDT ) has_outline = FALSE; @@ -973,7 +1003,11 @@ /* the optional tables */ /* embedded bitmap support */ - if ( sfnt->load_eblc ) + /* TODO: Replace this clumsy check for all possible sbit tables */ + /* with something better (for example, by passing a parameter */ + /* to suppress 'sbix' loading). */ + if ( sfnt->load_eblc && + ( has_CBLC || has_EBLC || has_bloc || has_sbix ) ) LOAD_( eblc ); /* colored glyph support */ @@ -983,6 +1017,10 @@ LOAD_( colr ); } + /* OpenType-SVG glyph support */ + if ( sfnt->load_svg ) + LOAD_( svg ); + /* consider the pclt, kerning, and gasp tables as optional */ LOAD_( pclt ); LOAD_( gasp ); @@ -1025,6 +1063,16 @@ GET_NAME( FONT_SUBFAMILY, &face->root.style_name ); } +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + { + FT_Memory memory = face->root.memory; + + + if ( FT_STRDUP( face->non_var_style_name, face->root.style_name ) ) + goto Exit; + } +#endif + /* now set up root fields */ { FT_Face root = &face->root; @@ -1037,11 +1085,19 @@ */ if ( face->sbit_table_type == TT_SBIT_TABLE_TYPE_CBLC || face->sbit_table_type == TT_SBIT_TABLE_TYPE_SBIX || - face->colr ) + face->colr || + face->svg ) flags |= FT_FACE_FLAG_COLOR; /* color glyphs */ if ( has_outline == TRUE ) - flags |= FT_FACE_FLAG_SCALABLE; /* scalable outlines */ + { + /* by default (and for backward compatibility) we handle */ + /* fonts with an 'sbix' table as bitmap-only */ + if ( has_sbix ) + flags |= FT_FACE_FLAG_SBIX; /* with 'sbix' bitmaps */ + else + flags |= FT_FACE_FLAG_SCALABLE; /* scalable outlines */ + } /* The sfnt driver only supports bitmap fonts natively, thus we */ /* don't set FT_FACE_FLAG_HINTER. */ @@ -1070,13 +1126,7 @@ /* Don't bother to load the tables unless somebody asks for them. */ /* No need to do work which will (probably) not be used. */ if ( face->variation_support & TT_FACE_FLAG_VAR_FVAR ) - { - if ( tt_face_lookup_table( face, TTAG_glyf ) != 0 && - tt_face_lookup_table( face, TTAG_gvar ) != 0 ) - flags |= FT_FACE_FLAG_MULTIPLE_MASTERS; - if ( tt_face_lookup_table( face, TTAG_CFF2 ) != 0 ) - flags |= FT_FACE_FLAG_MULTIPLE_MASTERS; - } + flags |= FT_FACE_FLAG_MULTIPLE_MASTERS; #endif root->face_flags = flags; @@ -1150,9 +1200,10 @@ } /* synthesize Unicode charmap if one is missing */ - if ( !has_unicode ) + if ( !has_unicode && + root->face_flags & FT_FACE_FLAG_GLYPH_NAMES ) { - FT_CharMapRec cmaprec; + FT_CharMapRec cmaprec; cmaprec.face = root; @@ -1189,7 +1240,7 @@ if ( count > 0 ) { - FT_Memory memory = face->root.stream->memory; + FT_Memory memory = face->root.memory; FT_UShort em_size = face->header.Units_Per_EM; FT_Short avgwidth = face->os2.xAvgCharWidth; FT_Size_Metrics metrics; @@ -1208,7 +1259,7 @@ /* of `FT_Face', we map `available_sizes' indices to strike */ /* indices */ if ( FT_NEW_ARRAY( root->available_sizes, count ) || - FT_NEW_ARRAY( sbit_strike_map, count ) ) + FT_QNEW_ARRAY( sbit_strike_map, count ) ) goto Exit; bsize_idx = 0; @@ -1237,7 +1288,7 @@ } /* reduce array size to the actually used elements */ - (void)FT_RENEW_ARRAY( sbit_strike_map, count, bsize_idx ); + FT_MEM_QRENEW_ARRAY( sbit_strike_map, count, bsize_idx ); /* from now on, all strike indices are mapped */ /* using `sbit_strike_map' */ @@ -1263,7 +1314,8 @@ * * Set up metrics. */ - if ( FT_IS_SCALABLE( root ) ) + if ( FT_IS_SCALABLE( root ) || + FT_HAS_SBIX( root ) ) { /* XXX What about if outline header is missing */ /* (e.g. sfnt wrapped bitmap)? */ @@ -1402,6 +1454,12 @@ sfnt->free_cpal( face ); sfnt->free_colr( face ); } + +#ifdef FT_CONFIG_OPTION_SVG + /* free SVG data */ + if ( sfnt->free_svg ) + sfnt->free_svg( face ); +#endif } #ifdef TT_CONFIG_OPTION_BDF @@ -1461,6 +1519,7 @@ #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT FT_FREE( face->var_postscript_prefix ); + FT_FREE( face->non_var_style_name ); #endif /* freeing glyph color palette data */ diff --git a/src/font/freetype-2.10.2/src/sfnt/sfobjs.h b/3rdparty/freetype-2.13.2/src/sfnt/sfobjs.h similarity index 92% rename from src/font/freetype-2.10.2/src/sfnt/sfobjs.h rename to 3rdparty/freetype-2.13.2/src/sfnt/sfobjs.h index d8438a483..906aebbf9 100644 --- a/src/font/freetype-2.10.2/src/sfnt/sfobjs.h +++ b/3rdparty/freetype-2.13.2/src/sfnt/sfobjs.h @@ -4,7 +4,7 @@ * * SFNT object management (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,9 +20,8 @@ #define SFOBJS_H_ -#include -#include FT_INTERNAL_SFNT_H -#include FT_INTERNAL_OBJECTS_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/src/sfnt/sfwoff.c b/3rdparty/freetype-2.13.2/src/sfnt/sfwoff.c similarity index 93% rename from src/font/freetype-2.10.2/src/sfnt/sfwoff.c rename to 3rdparty/freetype-2.13.2/src/sfnt/sfwoff.c index d1e330f67..7c0ce2205 100644 --- a/src/font/freetype-2.10.2/src/sfnt/sfwoff.c +++ b/3rdparty/freetype-2.13.2/src/sfnt/sfwoff.c @@ -4,7 +4,7 @@ * * WOFF format management (base). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,12 +16,14 @@ */ -#include #include "sfwoff.h" -#include FT_TRUETYPE_TAGS_H -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_STREAM_H -#include FT_GZIP_H +#include +#include +#include +#include + + +#ifdef FT_CONFIG_OPTION_USE_ZLIB /************************************************************************** @@ -62,12 +64,11 @@ FT_FREE( stream->base ); stream->size = 0; - stream->base = NULL; stream->close = NULL; } - FT_CALLBACK_DEF( int ) + FT_COMPARE_DEF( int ) compare_offsets( const void* a, const void* b ) { @@ -110,7 +111,7 @@ FT_ULong sfnt_offset; FT_Int nn; - FT_ULong old_tag = 0; + FT_Tag old_tag = 0; static const FT_Frame_Field woff_header_fields[] = { @@ -161,8 +162,7 @@ } /* Don't trust `totalSfntSize' before thorough checks. */ - if ( FT_ALLOC( sfnt, 12 + woff.num_tables * 16UL ) || - FT_NEW( sfnt_stream ) ) + if ( FT_QALLOC( sfnt, 12 ) || FT_NEW( sfnt_stream ) ) goto Exit; sfnt_header = sfnt; @@ -195,13 +195,13 @@ /* tag value, the tables themselves are not. We thus have to */ /* sort them by offset and check that they don't overlap. */ - if ( FT_NEW_ARRAY( tables, woff.num_tables ) || - FT_NEW_ARRAY( indices, woff.num_tables ) ) + if ( FT_QNEW_ARRAY( tables, woff.num_tables ) || + FT_QNEW_ARRAY( indices, woff.num_tables ) ) goto Exit; - FT_TRACE2(( "\n" - " tag offset compLen origLen checksum\n" - " -------------------------------------------\n" )); + FT_TRACE2(( "\n" )); + FT_TRACE2(( " tag offset compLen origLen checksum\n" )); + FT_TRACE2(( " -------------------------------------------\n" )); if ( FT_FRAME_ENTER( 20L * woff.num_tables ) ) goto Exit; @@ -327,9 +327,7 @@ } /* Now use `totalSfntSize'. */ - if ( FT_REALLOC( sfnt, - 12 + woff.num_tables * 16UL, - woff.totalSfntSize ) ) + if ( FT_QREALLOC( sfnt, 12, woff.totalSfntSize ) ) goto Exit; sfnt_header = sfnt + 12; @@ -361,8 +359,6 @@ } else { -#ifdef FT_CONFIG_OPTION_USE_ZLIB - /* Uncompress with zlib. */ FT_ULong output_len = table->OrigLength; @@ -378,13 +374,6 @@ error = FT_THROW( Invalid_Table ); goto Exit1; } - -#else /* !FT_CONFIG_OPTION_USE_ZLIB */ - - error = FT_THROW( Unimplemented_Feature ); - goto Exit1; - -#endif /* !FT_CONFIG_OPTION_USE_ZLIB */ } FT_FRAME_EXIT(); @@ -434,5 +423,12 @@ #undef WRITE_USHORT #undef WRITE_ULONG +#else /* !FT_CONFIG_OPTION_USE_ZLIB */ + + /* ANSI C doesn't like empty source files */ + typedef int sfwoff_dummy_; + +#endif /* !FT_CONFIG_OPTION_USE_ZLIB */ + /* END */ diff --git a/src/font/freetype-2.10.2/src/sfnt/sfwoff.h b/3rdparty/freetype-2.13.2/src/sfnt/sfwoff.h similarity index 83% rename from src/font/freetype-2.10.2/src/sfnt/sfwoff.h rename to 3rdparty/freetype-2.13.2/src/sfnt/sfwoff.h index c1789d33d..d43842273 100644 --- a/src/font/freetype-2.10.2/src/sfnt/sfwoff.h +++ b/3rdparty/freetype-2.13.2/src/sfnt/sfwoff.h @@ -4,7 +4,7 @@ * * WOFFF format management (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,19 +20,21 @@ #define SFWOFF_H_ -#include -#include FT_INTERNAL_SFNT_H -#include FT_INTERNAL_OBJECTS_H +#include +#include FT_BEGIN_HEADER +#ifdef FT_CONFIG_OPTION_USE_ZLIB FT_LOCAL( FT_Error ) woff_open_font( FT_Stream stream, TT_Face face ); +#endif + FT_END_HEADER #endif /* SFWOFF_H_ */ diff --git a/src/font/freetype-2.10.2/src/sfnt/sfwoff2.c b/3rdparty/freetype-2.13.2/src/sfnt/sfwoff2.c similarity index 87% rename from src/font/freetype-2.10.2/src/sfnt/sfwoff2.c rename to 3rdparty/freetype-2.13.2/src/sfnt/sfwoff2.c index 1b99e7d28..2be44a347 100644 --- a/src/font/freetype-2.10.2/src/sfnt/sfwoff2.c +++ b/3rdparty/freetype-2.13.2/src/sfnt/sfwoff2.c @@ -4,7 +4,7 @@ * * WOFF2 format management (base). * - * Copyright (C) 2019-2020 by + * Copyright (C) 2019-2023 by * Nikhil Ramakrishnan, David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -15,20 +15,17 @@ * */ -#include #include "sfwoff2.h" #include "woff2tags.h" -#include FT_TRUETYPE_TAGS_H -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_STREAM_H +#include +#include +#include #ifdef FT_CONFIG_OPTION_USE_BROTLI #include -#endif - /************************************************************************** * @@ -39,12 +36,15 @@ #undef FT_COMPONENT #define FT_COMPONENT sfwoff2 + /* An arbitrary, heuristic size limit (67MByte) for expanded WOFF2 data. */ +#define MAX_SFNT_SIZE ( 1 << 26 ) #define READ_255USHORT( var ) FT_SET_ERROR( Read255UShort( stream, &var ) ) #define READ_BASE128( var ) FT_SET_ERROR( ReadBase128( stream, &var ) ) -#define ROUND4( var ) ( ( var + 3 ) & ~3 ) + /* `var' should be FT_ULong */ +#define ROUND4( var ) ( ( var + 3 ) & ~3UL ) #define WRITE_USHORT( p, v ) \ do \ @@ -64,12 +64,12 @@ \ } while ( 0 ) -#define WRITE_SHORT( p, v ) \ - do \ - { \ - *(p)++ = ( (v) >> 8 ); \ - *(p)++ = ( (v) >> 0 ); \ - \ +#define WRITE_SHORT( p, v ) \ + do \ + { \ + *(p)++ = (FT_Byte)( (v) >> 8 ); \ + *(p)++ = (FT_Byte)( (v) >> 0 ); \ + \ } while ( 0 ) #define WRITE_SFNT_BUF( buf, s ) \ @@ -86,6 +86,8 @@ #define BBOX_STREAM 5 #define INSTRUCTION_STREAM 6 +#define HAVE_OVERLAP_SIMPLE_BITMAP 0x1 + static void stream_close( FT_Stream stream ) @@ -96,20 +98,19 @@ FT_FREE( stream->base ); stream->size = 0; - stream->base = NULL; stream->close = NULL; } - FT_CALLBACK_DEF( int ) + FT_COMPARE_DEF( int ) compare_tags( const void* a, const void* b ) { WOFF2_Table table1 = *(WOFF2_Table*)a; WOFF2_Table table2 = *(WOFF2_Table*)b; - FT_ULong tag1 = table1->Tag; - FT_ULong tag2 = table2->Tag; + FT_Tag tag1 = table1->Tag; + FT_Tag tag2 = table2->Tag; if ( tag1 > tag2 ) @@ -125,10 +126,10 @@ Read255UShort( FT_Stream stream, FT_UShort* value ) { - static const FT_Int oneMoreByteCode1 = 255; - static const FT_Int oneMoreByteCode2 = 254; - static const FT_Int wordCode = 253; - static const FT_Int lowestUCode = 253; + const FT_Byte oneMoreByteCode1 = 255; + const FT_Byte oneMoreByteCode2 = 254; + const FT_Byte wordCode = 253; + const FT_UShort lowestUCode = 253; FT_Error error = FT_Err_Ok; FT_Byte code; @@ -230,9 +231,9 @@ { FT_TRACE6(( "Reallocating %lu to %lu.\n", *dst_size, (*offset + size) )); - if ( FT_REALLOC( dst, - (FT_ULong)( *dst_size ), - (FT_ULong)( *offset + size ) ) ) + if ( FT_QREALLOC( dst, + (FT_ULong)( *dst_size ), + (FT_ULong)( *offset + size ) ) ) goto Exit; *dst_size = *offset + size; @@ -281,12 +282,12 @@ /* Calculate table checksum of `buf'. */ - static FT_Long + static FT_ULong compute_ULong_sum( FT_Byte* buf, FT_ULong size ) { FT_ULong checksum = 0; - FT_ULong aligned_size = size & ~3; + FT_ULong aligned_size = size & ~3UL; FT_ULong i; FT_ULong v; @@ -316,9 +317,9 @@ const FT_Byte* src, FT_ULong src_size ) { -#ifdef FT_CONFIG_OPTION_USE_BROTLI - - FT_ULong uncompressed_size = dst_size; + /* this cast is only of importance on 32bit systems; */ + /* we don't validate it */ + FT_Offset uncompressed_size = (FT_Offset)dst_size; BrotliDecoderResult result; @@ -336,20 +337,13 @@ FT_TRACE2(( "woff2_decompress: Brotli stream decompressed.\n" )); return FT_Err_Ok; - -#else /* !FT_CONFIG_OPTION_USE_BROTLI */ - - FT_ERROR(( "woff2_decompress: Brotli support not available.\n" )); - return FT_THROW( Unimplemented_Feature ); - -#endif /* !FT_CONFIG_OPTION_USE_BROTLI */ } static WOFF2_Table find_table( WOFF2_Table* tables, FT_UShort num_tables, - FT_ULong tag ) + FT_Tag tag ) { FT_Int i; @@ -532,17 +526,18 @@ const WOFF2_Point points, FT_UShort n_contours, FT_UShort instruction_len, + FT_Bool have_overlap, FT_Byte* dst, FT_ULong dst_size, FT_ULong* glyph_size ) { FT_UInt flag_offset = 10 + ( 2 * n_contours ) + 2 + instruction_len; - FT_Int last_flag = -1; - FT_Int repeat_count = 0; - FT_Int last_x = 0; - FT_Int last_y = 0; - FT_UInt x_bytes = 0; - FT_UInt y_bytes = 0; + FT_Byte last_flag = 0xFFU; + FT_Byte repeat_count = 0; + FT_Int last_x = 0; + FT_Int last_y = 0; + FT_UInt x_bytes = 0; + FT_UInt y_bytes = 0; FT_UInt xy_bytes; FT_UInt i; FT_UInt x_offset; @@ -554,10 +549,13 @@ { const WOFF2_PointRec point = points[i]; - FT_Int flag = point.on_curve ? GLYF_ON_CURVE : 0; - FT_Int dx = point.x - last_x; - FT_Int dy = point.y - last_y; + FT_Byte flag = point.on_curve ? GLYF_ON_CURVE : 0; + FT_Int dx = point.x - last_x; + FT_Int dy = point.y - last_y; + + if ( i == 0 && have_overlap ) + flag |= GLYF_OVERLAP_SIMPLE; if ( dx == 0 ) flag |= GLYF_THIS_X_IS_SAME; @@ -633,7 +631,7 @@ if ( dx == 0 ) ; else if ( dx > -256 && dx < 256 ) - dst[x_offset++] = FT_ABS( dx ); + dst[x_offset++] = (FT_Byte)FT_ABS( dx ); else { pointer = dst + x_offset; @@ -646,7 +644,7 @@ if ( dy == 0 ) ; else if ( dy > -256 && dy < 256 ) - dst[y_offset++] = FT_ABS( dy ); + dst[y_offset++] = (FT_Byte)FT_ABS( dy ); else { pointer = dst + y_offset; @@ -788,7 +786,7 @@ goto Fail; loca_buf_size = loca_values_size * offset_size; - if ( FT_NEW_ARRAY( loca_buf, loca_buf_size ) ) + if ( FT_QALLOC( loca_buf, loca_buf_size ) ) goto Fail; dst = loca_buf; @@ -843,15 +841,18 @@ FT_UInt num_substreams = 7; + FT_UShort option_flags; FT_UShort num_glyphs; FT_UShort index_format; FT_ULong expected_loca_length; FT_UInt offset; FT_UInt i; FT_ULong points_size; - FT_ULong bitmap_length; FT_ULong glyph_buf_size; FT_ULong bbox_bitmap_offset; + FT_ULong bbox_bitmap_length; + FT_ULong overlap_bitmap_offset = 0; + FT_ULong overlap_bitmap_length = 0; const FT_ULong glyf_start = *out_offset; FT_ULong dest_offset = *out_offset; @@ -864,18 +865,20 @@ WOFF2_Point points = NULL; - if ( FT_NEW_ARRAY( substreams, num_substreams ) ) + if ( FT_QNEW_ARRAY( substreams, num_substreams ) ) goto Fail; - if ( FT_STREAM_SKIP( 4 ) ) + if ( FT_STREAM_SKIP( 2 ) ) + goto Fail; + if ( FT_READ_USHORT( option_flags ) ) goto Fail; if ( FT_READ_USHORT( num_glyphs ) ) goto Fail; if ( FT_READ_USHORT( index_format ) ) goto Fail; - FT_TRACE4(( "num_glyphs = %u; index_format = %u\n", - num_glyphs, index_format )); + FT_TRACE4(( "option_flags = %u; num_glyphs = %u; index_format = %u\n", + option_flags, num_glyphs, index_format )); info->num_glyphs = num_glyphs; @@ -888,7 +891,7 @@ if ( info->loca_table->dst_length != expected_loca_length ) goto Fail; - offset = ( 2 + num_substreams ) * 4; + offset = 2 + 2 + 2 + 2 + ( num_substreams * 4 ); if ( offset > info->glyf_table->TransformLength ) goto Fail; @@ -911,21 +914,36 @@ offset += substream_size; } - if ( FT_NEW_ARRAY( loca_values, num_glyphs + 1 ) ) + if ( option_flags & HAVE_OVERLAP_SIMPLE_BITMAP ) + { + /* Size of overlapBitmap = floor((numGlyphs + 7) / 8) */ + overlap_bitmap_length = ( num_glyphs + 7U ) >> 3; + if ( overlap_bitmap_length > info->glyf_table->TransformLength - offset ) + goto Fail; + + overlap_bitmap_offset = pos + offset; + + FT_TRACE5(( " Overlap bitmap: offset = %lu; size = %lu;\n", + overlap_bitmap_offset, overlap_bitmap_length )); + offset += overlap_bitmap_length; + } + + if ( FT_QNEW_ARRAY( loca_values, num_glyphs + 1 ) ) goto Fail; points_size = 0; bbox_bitmap_offset = substreams[BBOX_STREAM].offset; /* Size of bboxBitmap = 4 * floor((numGlyphs + 31) / 32) */ - bitmap_length = ( ( num_glyphs + 31 ) >> 5 ) << 2; - substreams[BBOX_STREAM].offset += bitmap_length; + bbox_bitmap_length = ( ( num_glyphs + 31U ) >> 5 ) << 2; + /* bboxStreamSize is the combined size of bboxBitmap and bboxStream. */ + substreams[BBOX_STREAM].offset += bbox_bitmap_length; glyph_buf_size = WOFF2_DEFAULT_GLYPH_BUF; - if ( FT_NEW_ARRAY( glyph_buf, glyph_buf_size ) ) + if ( FT_QALLOC( glyph_buf, glyph_buf_size ) ) goto Fail; - if ( FT_NEW_ARRAY( info->x_mins, num_glyphs ) ) + if ( FT_QNEW_ARRAY( info->x_mins, num_glyphs ) ) goto Fail; for ( i = 0; i < num_glyphs; ++i ) @@ -957,7 +975,7 @@ /* composite glyph */ FT_Bool have_instructions = FALSE; FT_UShort instruction_size = 0; - FT_ULong composite_size; + FT_ULong composite_size = 0; FT_ULong size_needed; FT_Byte* pointer = NULL; @@ -983,7 +1001,7 @@ size_needed = 12 + composite_size + instruction_size; if ( glyph_buf_size < size_needed ) { - if ( FT_RENEW_ARRAY( glyph_buf, glyph_buf_size, size_needed ) ) + if ( FT_QREALLOC( glyph_buf, glyph_buf_size, size_needed ) ) goto Fail; glyph_buf_size = size_needed; } @@ -1035,8 +1053,11 @@ FT_ULong flag_size; FT_ULong triplet_size; FT_ULong triplet_bytes_used; - FT_Byte* flags_buf = NULL; - FT_Byte* triplet_buf = NULL; + FT_Bool have_overlap = FALSE; + FT_Byte overlap_bitmap; + FT_ULong overlap_offset; + FT_Byte* flags_buf = NULL; + FT_Byte* triplet_buf = NULL; FT_UShort instruction_size; FT_ULong size_needed; FT_Int end_point; @@ -1045,7 +1066,18 @@ FT_Byte* pointer = NULL; - if ( FT_NEW_ARRAY( n_points_arr, n_contours ) ) + /* Set `have_overlap`. */ + if ( overlap_bitmap_offset ) + { + overlap_offset = overlap_bitmap_offset + ( i >> 3 ); + if ( FT_STREAM_SEEK( overlap_offset ) || + FT_READ_BYTE( overlap_bitmap ) ) + goto Fail; + if ( overlap_bitmap & ( 0x80 >> ( i & 7 ) ) ) + have_overlap = TRUE; + } + + if ( FT_QNEW_ARRAY( n_points_arr, n_contours ) ) goto Fail; if ( FT_STREAM_SEEK( substreams[N_POINTS_STREAM].offset ) ) @@ -1082,7 +1114,7 @@ /* Create array to store point information. */ points_size = total_n_points; - if ( FT_NEW_ARRAY( points, points_size ) ) + if ( FT_QNEW_ARRAY( points, points_size ) ) goto Fail; if ( triplet_decode( flags_buf, @@ -1111,7 +1143,7 @@ instruction_size; if ( glyph_buf_size < size_needed ) { - if ( FT_RENEW_ARRAY( glyph_buf, glyph_buf_size, size_needed ) ) + if ( FT_QREALLOC( glyph_buf, glyph_buf_size, size_needed ) ) goto Fail; glyph_buf_size = size_needed; } @@ -1165,6 +1197,7 @@ points, n_contours, instruction_size, + have_overlap, glyph_buf, glyph_buf_size, &glyph_size ) ) @@ -1195,8 +1228,7 @@ *glyf_checksum += compute_ULong_sum( glyph_buf, glyph_size ); /* Store x_mins, may be required to reconstruct `hmtx'. */ - if ( n_contours > 0 ) - info->x_mins[i] = x_min; + info->x_mins[i] = (FT_Short)x_min; } info->glyf_table->dst_length = dest_offset - info->glyf_table->dst_offset; @@ -1220,7 +1252,7 @@ FT_TRACE4(( " loca table info:\n" )); FT_TRACE4(( " dst_offset = %lu\n", info->loca_table->dst_offset )); FT_TRACE4(( " dst_length = %lu\n", info->loca_table->dst_length )); - FT_TRACE4(( " checksum = %09x\n", *loca_checksum )); + FT_TRACE4(( " checksum = %09lx\n", *loca_checksum )); /* Set pointer `sfnt_bytes' to its correct value. */ *sfnt_bytes = sfnt; @@ -1287,6 +1319,12 @@ return FT_THROW( Invalid_Table ); } + if ( !info->loca_table ) + { + FT_ERROR(( "`loca' table is missing.\n" )); + return FT_THROW( Invalid_Table ); + } + /* Read `numGlyphs' field from `maxp' table. */ if ( FT_STREAM_SEEK( maxp_table->src_offset ) || FT_STREAM_SKIP( 8 ) ) return error; @@ -1307,7 +1345,7 @@ offset_size = index_format ? 4 : 2; /* Create `x_mins' array. */ - if ( FT_NEW_ARRAY( info->x_mins, num_glyphs ) ) + if ( FT_QNEW_ARRAY( info->x_mins, num_glyphs ) ) return error; loca_offset = info->loca_table->src_offset; @@ -1338,7 +1376,7 @@ if ( FT_STREAM_SEEK( glyf_offset ) || FT_STREAM_SKIP( 2 ) ) return error; - if ( FT_READ_USHORT( info->x_mins[i] ) ) + if ( FT_READ_SHORT( info->x_mins[i] ) ) return error; } @@ -1395,8 +1433,8 @@ if ( num_hmetrics < 1 ) goto Fail; - if ( FT_NEW_ARRAY( advance_widths, num_hmetrics ) || - FT_NEW_ARRAY( lsbs, num_glyphs ) ) + if ( FT_QNEW_ARRAY( advance_widths, num_hmetrics ) || + FT_QNEW_ARRAY( lsbs, num_glyphs ) ) goto Fail; /* Read `advanceWidth' stream. Always present. */ @@ -1447,7 +1485,7 @@ /* Build the hmtx table. */ hmtx_table_size = 2 * num_hmetrics + 2 * num_glyphs; - if ( FT_NEW_ARRAY( hmtx_table, hmtx_table_size ) ) + if ( FT_QALLOC( hmtx_table, hmtx_table_size ) ) goto Fail; dst = hmtx_table; @@ -1504,10 +1542,10 @@ { /* Memory management of `transformed_buf' is handled by the caller. */ - FT_Error error = FT_Err_Ok; - FT_Stream stream = NULL; - FT_Byte* buf_cursor = NULL; - FT_Byte* table_entry = NULL; + FT_Error error = FT_Err_Ok; + FT_Stream stream = NULL; + FT_Byte* buf_cursor = NULL; + FT_Byte table_entry[16]; /* We are reallocating memory for `sfnt', so its pointer may change. */ FT_Byte* sfnt = *sfnt_bytes; @@ -1548,10 +1586,6 @@ } } - /* Create buffer for table entries. */ - if ( FT_NEW_ARRAY( table_entry, 16 ) ) - goto Fail; - /* Create a stream for the uncompressed buffer. */ if ( FT_NEW( stream ) ) goto Fail; @@ -1565,7 +1599,7 @@ WOFF2_TableRec table = *( indices[nn] ); - FT_TRACE3(( "Seeking to %d with table size %d.\n", + FT_TRACE3(( "Seeking to %ld with table size %ld.\n", table.src_offset, table.src_length )); FT_TRACE3(( "Table tag: %c%c%c%c.\n", (FT_Char)( table.Tag >> 24 ), @@ -1606,7 +1640,7 @@ checksum = compute_ULong_sum( transformed_buf + table.src_offset, table.src_length ); - FT_TRACE4(( "Checksum = %09x.\n", checksum )); + FT_TRACE4(( "Checksum = %09lx.\n", checksum )); if ( WRITE_SFNT_BUF( transformed_buf + table.src_offset, table.src_length ) ) @@ -1631,7 +1665,7 @@ memory ) ) goto Fail; - FT_TRACE4(( "Checksum = %09x.\n", checksum )); + FT_TRACE4(( "Checksum = %09lx.\n", checksum )); } else if ( table.Tag == TTAG_loca ) @@ -1707,14 +1741,13 @@ WRITE_ULONG( buf_cursor, font_checksum ); - FT_TRACE2(( "Final checksum = %09x.\n", font_checksum )); + FT_TRACE2(( "Final checksum = %09lx.\n", font_checksum )); woff2->actual_sfnt_size = dest_offset; /* Set pointer of sfnt stream to its correct value. */ *sfnt_bytes = sfnt; - FT_FREE( table_entry ); FT_Stream_Close( stream ); FT_FREE( stream ); @@ -1727,7 +1760,6 @@ /* Set pointer of sfnt stream to its correct value. */ *sfnt_bytes = sfnt; - FT_FREE( table_entry ); FT_Stream_Close( stream ); FT_FREE( stream ); @@ -1804,15 +1836,15 @@ if ( FT_STREAM_READ_FIELDS( woff2_header_fields, &woff2 ) ) return error; - FT_TRACE4(( "signature -> 0x%X\n", woff2.signature )); + FT_TRACE4(( "signature -> 0x%lX\n", woff2.signature )); FT_TRACE2(( "flavor -> 0x%08lx\n", woff2.flavor )); FT_TRACE4(( "length -> %lu\n", woff2.length )); FT_TRACE2(( "num_tables -> %hu\n", woff2.num_tables )); FT_TRACE4(( "totalSfntSize -> %lu\n", woff2.totalSfntSize )); - FT_TRACE4(( "metaOffset -> %hu\n", woff2.metaOffset )); - FT_TRACE4(( "metaLength -> %hu\n", woff2.metaLength )); - FT_TRACE4(( "privOffset -> %hu\n", woff2.privOffset )); - FT_TRACE4(( "privLength -> %hu\n", woff2.privLength )); + FT_TRACE4(( "metaOffset -> %lu\n", woff2.metaOffset )); + FT_TRACE4(( "metaLength -> %lu\n", woff2.metaLength )); + FT_TRACE4(( "privOffset -> %lu\n", woff2.privOffset )); + FT_TRACE4(( "privLength -> %lu\n", woff2.privLength )); /* Make sure we don't recurse back here. */ if ( woff2.flavor == TTAG_wOF2 ) @@ -1840,13 +1872,14 @@ woff2.ttc_fonts = NULL; /* Read table directory. */ - if ( FT_NEW_ARRAY( tables, woff2.num_tables ) || - FT_NEW_ARRAY( indices, woff2.num_tables ) ) + if ( FT_QNEW_ARRAY( tables, woff2.num_tables ) || + FT_QNEW_ARRAY( indices, woff2.num_tables ) ) goto Exit; - FT_TRACE2(( "\n" - " tag flags transform origLen transformLen\n" - " --------------------------------------------------\n" )); + FT_TRACE2(( "\n" )); + FT_TRACE2(( " tag flags transform origLen transformLen offset\n" )); + FT_TRACE2(( " -----------------------------------------------------------\n" )); + /* " XXXX XXXXXXXX XXXXXXXX XXXXXXXX XXXXXXXX XXXXXXXX" */ for ( nn = 0; nn < woff2.num_tables; nn++ ) { @@ -1911,12 +1944,13 @@ goto Exit; } + table->flags = flags; table->src_offset = src_offset; table->src_length = table->TransformLength; src_offset += table->TransformLength; - table->flags = flags; + table->dst_offset = 0; - FT_TRACE2(( " %c%c%c%c %08d %08d %08ld %08ld\n", + FT_TRACE2(( " %c%c%c%c %08d %08d %08ld %08ld %08ld\n", (FT_Char)( table->Tag >> 24 ), (FT_Char)( table->Tag >> 16 ), (FT_Char)( table->Tag >> 8 ), @@ -1925,7 +1959,6 @@ ( table->FlagByte >> 6 ) & 0x03, table->dst_length, table->TransformLength, - table->src_length, table->src_offset )); indices[nn] = table; @@ -1971,8 +2004,9 @@ goto Exit; } - FT_TRACE4(( "Number of fonts in TTC: %ld\n", woff2.num_fonts )); + FT_TRACE4(( "Number of fonts in TTC: %d\n", woff2.num_fonts )); + /* pre-zero pointers within in case of failure */ if ( FT_NEW_ARRAY( woff2.ttc_fonts, woff2.num_fonts ) ) goto Exit; @@ -1986,10 +2020,10 @@ if ( FT_READ_ULONG( ttc_font->flavor ) ) goto Exit; - if ( FT_NEW_ARRAY( ttc_font->table_indices, ttc_font->num_tables ) ) + if ( FT_QNEW_ARRAY( ttc_font->table_indices, ttc_font->num_tables ) ) goto Exit; - FT_TRACE5(( "Number of tables in font %d: %ld\n", + FT_TRACE5(( "Number of tables in font %d: %d\n", nn, ttc_font->num_tables )); #ifdef FT_DEBUG_LEVEL_TRACE @@ -2067,7 +2101,7 @@ error = FT_THROW( Invalid_Table ); goto Exit; } - file_offset = ROUND4(woff2.metaOffset + woff2.metaLength); + file_offset = ROUND4( woff2.metaOffset + woff2.metaLength ); } if ( woff2.privOffset ) @@ -2077,7 +2111,7 @@ error = FT_THROW( Invalid_Table ); goto Exit; } - file_offset = ROUND4(woff2.privOffset + woff2.privLength); + file_offset = ROUND4( woff2.privOffset + woff2.privLength ); } if ( file_offset != ( ROUND4( woff2.length ) ) ) @@ -2089,7 +2123,7 @@ /* Validate requested face index. */ *num_faces = woff2.num_fonts; /* value -(N+1) requests information on index N */ - if ( *face_instance_index < 0 ) + if ( *face_instance_index < 0 && face_index > 0 ) face_index--; if ( face_index >= woff2.num_fonts ) @@ -2110,8 +2144,8 @@ /* Create a temporary array. */ - if ( FT_NEW_ARRAY( temp_indices, - ttc_font->num_tables ) ) + if ( FT_QNEW_ARRAY( temp_indices, + ttc_font->num_tables ) ) goto Exit; FT_TRACE4(( "Storing tables for TTC face index %d.\n", face_index )); @@ -2119,9 +2153,9 @@ temp_indices[nn] = indices[ttc_font->table_indices[nn]]; /* Resize array to required size. */ - if ( FT_RENEW_ARRAY( indices, - woff2.num_tables, - ttc_font->num_tables ) ) + if ( FT_QRENEW_ARRAY( indices, + woff2.num_tables, + ttc_font->num_tables ) ) goto Exit; for ( nn = 0; nn < ttc_font->num_tables; nn++ ) @@ -2148,9 +2182,8 @@ else sfnt_size = woff2.totalSfntSize; - /* Value 1<<26 = 67108864 is heuristic. */ - if (sfnt_size >= (1 << 26)) - sfnt_size = 1 << 26; + if ( sfnt_size >= MAX_SFNT_SIZE ) + sfnt_size = MAX_SFNT_SIZE; #ifdef FT_DEBUG_LEVEL_TRACE if ( sfnt_size != woff2.totalSfntSize ) @@ -2161,8 +2194,8 @@ } /* Write sfnt header. */ - if ( FT_ALLOC( sfnt, sfnt_size ) || - FT_NEW( sfnt_stream ) ) + if ( FT_QALLOC( sfnt, sfnt_size ) || + FT_NEW( sfnt_stream ) ) goto Exit; sfnt_header = sfnt; @@ -2200,22 +2233,46 @@ sizeof ( WOFF2_Table ), compare_tags ); + /* reject fonts that have multiple tables with the same tag */ + for ( nn = 1; nn < woff2.num_tables; nn++ ) + { + FT_Tag tag = indices[nn]->Tag; + + + if ( tag == indices[nn - 1]->Tag ) + { + FT_ERROR(( "woff2_open_font:" + " multiple tables with tag `%c%c%c%c'.\n", + (FT_Char)( tag >> 24 ), + (FT_Char)( tag >> 16 ), + (FT_Char)( tag >> 8 ), + (FT_Char)( tag ) )); + error = FT_THROW( Invalid_Table ); + goto Exit; + } + } + if ( woff2.uncompressed_size < 1 ) { error = FT_THROW( Invalid_Table ); goto Exit; } - if ( woff2.uncompressed_size > sfnt_size ) + /* We must not blindly trust `uncompressed_size` since its */ + /* value might be corrupted. If it is too large, reject the */ + /* font. In other words, we don't accept a WOFF2 font that */ + /* expands to something larger than MAX_SFNT_SIZE. If ever */ + /* necessary, this limit can be easily adjusted. */ + if ( woff2.uncompressed_size > MAX_SFNT_SIZE ) { - FT_ERROR(( "woff2_open_font: SFNT table lengths are too large.\n" )); - error = FT_THROW( Invalid_Table ); + FT_ERROR(( "Uncompressed font too large.\n" )); + error = FT_THROW( Array_Too_Large ); goto Exit; } /* Allocate memory for uncompressed table data. */ - if ( FT_ALLOC( uncompressed_buf, woff2.uncompressed_size ) || - FT_FRAME_ENTER( woff2.totalCompressedSize ) ) + if ( FT_QALLOC( uncompressed_buf, woff2.uncompressed_size ) || + FT_FRAME_ENTER( woff2.totalCompressedSize ) ) goto Exit; /* Uncompress the stream. */ @@ -2246,9 +2303,9 @@ { FT_TRACE5(( "Trimming sfnt stream from %lu to %lu.\n", sfnt_size, woff2.actual_sfnt_size )); - if ( FT_REALLOC( sfnt, - (FT_ULong)( sfnt_size ), - (FT_ULong)( woff2.actual_sfnt_size ) ) ) + if ( FT_QREALLOC( sfnt, + (FT_ULong)( sfnt_size ), + (FT_ULong)( woff2.actual_sfnt_size ) ) ) goto Exit; } @@ -2324,5 +2381,12 @@ #undef BBOX_STREAM #undef INSTRUCTION_STREAM +#else /* !FT_CONFIG_OPTION_USE_BROTLI */ + + /* ANSI C doesn't like empty source files */ + typedef int sfwoff2_dummy_; + +#endif /* !FT_CONFIG_OPTION_USE_BROTLI */ + /* END */ diff --git a/src/font/freetype-2.10.2/src/sfnt/sfwoff2.h b/3rdparty/freetype-2.13.2/src/sfnt/sfwoff2.h similarity index 89% rename from src/font/freetype-2.10.2/src/sfnt/sfwoff2.h rename to 3rdparty/freetype-2.13.2/src/sfnt/sfwoff2.h index 7ae6e2c06..4901286ee 100644 --- a/src/font/freetype-2.10.2/src/sfnt/sfwoff2.h +++ b/3rdparty/freetype-2.13.2/src/sfnt/sfwoff2.h @@ -4,7 +4,7 @@ * * WOFFF2 format management (specification). * - * Copyright (C) 2019-2020 by + * Copyright (C) 2019-2023 by * Nikhil Ramakrishnan, David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,13 +20,13 @@ #define SFWOFF2_H_ -#include -#include FT_INTERNAL_SFNT_H -#include FT_INTERNAL_OBJECTS_H +#include +#include FT_BEGIN_HEADER +#ifdef FT_CONFIG_OPTION_USE_BROTLI /* Leave the first byte open to store `flag_byte'. */ #define WOFF2_FLAGS_TRANSFORM 1 << 8 @@ -56,6 +56,7 @@ FT_BEGIN_HEADER #define GLYF_REPEAT 1 << 3 #define GLYF_THIS_X_IS_SAME 1 << 4 #define GLYF_THIS_Y_IS_SAME 1 << 5 +#define GLYF_OVERLAP_SIMPLE 1 << 6 /* Other constants */ #define CONTOUR_OFFSET_END_POINT 10 @@ -67,6 +68,7 @@ FT_BEGIN_HEADER FT_Int* face_index, FT_Long* num_faces ); +#endif /* FT_CONFIG_OPTION_USE_BROTLI */ FT_END_HEADER diff --git a/src/font/freetype-2.10.2/src/sfnt/ttbdf.c b/3rdparty/freetype-2.13.2/src/sfnt/ttbdf.c similarity index 92% rename from src/font/freetype-2.10.2/src/sfnt/ttbdf.c rename to 3rdparty/freetype-2.13.2/src/sfnt/ttbdf.c index bc35284cc..536fa7467 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttbdf.c +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttbdf.c @@ -4,7 +4,7 @@ * * TrueType and OpenType embedded BDF properties (body). * - * Copyright (C) 2005-2020 by + * Copyright (C) 2005-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,10 +16,9 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_STREAM_H -#include FT_TRUETYPE_TAGS_H +#include +#include +#include #include "ttbdf.h" #include "sferrors.h" @@ -137,13 +136,14 @@ FT_LOCAL_DEF( FT_Error ) - tt_face_find_bdf_prop( TT_Face face, + tt_face_find_bdf_prop( FT_Face face, /* TT_Face */ const char* property_name, BDF_PropertyRec *aprop ) { - TT_BDF bdf = &face->bdf; - FT_Size size = FT_FACE( face )->size; - FT_Error error = FT_Err_Ok; + TT_Face ttface = (TT_Face)face; + TT_BDF bdf = &ttface->bdf; + FT_Size size = FT_FACE_SIZE( face ); + FT_Error error = FT_Err_Ok; FT_Byte* p; FT_UInt count; FT_Byte* strike; @@ -154,7 +154,7 @@ if ( bdf->loaded == 0 ) { - error = tt_face_load_bdf_props( face, FT_FACE( face )->stream ); + error = tt_face_load_bdf_props( ttface, FT_FACE_STREAM( face ) ); if ( error ) goto Exit; } @@ -249,7 +249,7 @@ #else /* !TT_CONFIG_OPTION_BDF */ /* ANSI C doesn't like empty source files */ - typedef int _tt_bdf_dummy; + typedef int tt_bdf_dummy_; #endif /* !TT_CONFIG_OPTION_BDF */ diff --git a/src/font/freetype-2.10.2/src/sfnt/ttbdf.h b/3rdparty/freetype-2.13.2/src/sfnt/ttbdf.h similarity index 88% rename from src/font/freetype-2.10.2/src/sfnt/ttbdf.h rename to 3rdparty/freetype-2.13.2/src/sfnt/ttbdf.h index c340f6631..0d7a0acec 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttbdf.h +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttbdf.h @@ -4,7 +4,7 @@ * * TrueType and OpenType embedded BDF properties (specification). * - * Copyright (C) 2005-2020 by + * Copyright (C) 2005-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,9 +20,8 @@ #define TTBDF_H_ -#include #include "ttload.h" -#include FT_BDF_H +#include FT_BEGIN_HEADER @@ -35,7 +34,7 @@ FT_BEGIN_HEADER FT_LOCAL( FT_Error ) - tt_face_find_bdf_prop( TT_Face face, + tt_face_find_bdf_prop( FT_Face face, const char* property_name, BDF_PropertyRec *aprop ); diff --git a/src/font/freetype-2.10.2/src/sfnt/ttcmap.c b/3rdparty/freetype-2.13.2/src/sfnt/ttcmap.c similarity index 88% rename from src/font/freetype-2.10.2/src/sfnt/ttcmap.c rename to 3rdparty/freetype-2.13.2/src/sfnt/ttcmap.c index 2c34efb5c..9ba25dcbc 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttcmap.c +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttcmap.c @@ -4,7 +4,7 @@ * * TrueType character mapping table (cmap) support (body). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,14 +16,13 @@ */ -#include -#include FT_INTERNAL_DEBUG_H +#include -#include "sferrors.h" /* must come before FT_INTERNAL_VALIDATE_H */ +#include "sferrors.h" /* must come before `ftvalid.h' */ -#include FT_INTERNAL_VALIDATE_H -#include FT_INTERNAL_STREAM_H -#include FT_SERVICE_POSTSCRIPT_CMAPS_H +#include +#include +#include #include "ttload.h" #include "ttcmap.h" #include "ttpost.h" @@ -60,10 +59,14 @@ FT_CALLBACK_DEF( FT_Error ) - tt_cmap_init( TT_CMap cmap, - FT_Byte* table ) + tt_cmap_init( FT_CMap cmap, /* TT_CMap */ + void* table_ ) { - cmap->data = table; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* table = (FT_Byte*)table_; + + + ttcmap->data = table; return FT_Err_Ok; } @@ -129,21 +132,23 @@ FT_CALLBACK_DEF( FT_UInt ) - tt_cmap0_char_index( TT_CMap cmap, + tt_cmap0_char_index( FT_CMap cmap, /* TT_CMap */ FT_UInt32 char_code ) { - FT_Byte* table = cmap->data; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* table = ttcmap->data; return char_code < 256 ? table[6 + char_code] : 0; } - FT_CALLBACK_DEF( FT_UInt32 ) - tt_cmap0_char_next( TT_CMap cmap, + FT_CALLBACK_DEF( FT_UInt ) + tt_cmap0_char_next( FT_CMap cmap, /* TT_CMap */ FT_UInt32 *pchar_code ) { - FT_Byte* table = cmap->data; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* table = ttcmap->data; FT_UInt32 charcode = *pchar_code; FT_UInt32 result = 0; FT_UInt gindex = 0; @@ -166,10 +171,11 @@ FT_CALLBACK_DEF( FT_Error ) - tt_cmap0_get_info( TT_CMap cmap, + tt_cmap0_get_info( FT_CharMap cmap, /* TT_CMap */ TT_CMapInfo *cmap_info ) { - FT_Byte* p = cmap->data + 4; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* p = ttcmap->data + 4; cmap_info->format = 0; @@ -454,10 +460,11 @@ FT_CALLBACK_DEF( FT_UInt ) - tt_cmap2_char_index( TT_CMap cmap, + tt_cmap2_char_index( FT_CMap cmap, /* TT_CMap */ FT_UInt32 char_code ) { - FT_Byte* table = cmap->data; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* table = ttcmap->data; FT_UInt result = 0; FT_Byte* subheader; @@ -466,7 +473,7 @@ if ( subheader ) { FT_Byte* p = subheader; - FT_UInt idx = (FT_UInt)(char_code & 0xFF); + FT_UInt idx = (FT_UInt)( char_code & 0xFF ); FT_UInt start, count; FT_Int delta; FT_UInt offset; @@ -492,11 +499,12 @@ } - FT_CALLBACK_DEF( FT_UInt32 ) - tt_cmap2_char_next( TT_CMap cmap, + FT_CALLBACK_DEF( FT_UInt ) + tt_cmap2_char_next( FT_CMap cmap, /* TT_CMap */ FT_UInt32 *pcharcode ) { - FT_Byte* table = cmap->data; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* table = ttcmap->data; FT_UInt gindex = 0; FT_UInt32 result = 0; FT_UInt32 charcode = *pcharcode + 1; @@ -580,10 +588,11 @@ FT_CALLBACK_DEF( FT_Error ) - tt_cmap2_get_info( TT_CMap cmap, + tt_cmap2_get_info( FT_CharMap cmap, /* TT_CMap */ TT_CMapInfo *cmap_info ) { - FT_Byte* p = cmap->data + 4; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* p = ttcmap->data + 4; cmap_info->format = 2; @@ -707,18 +716,20 @@ FT_CALLBACK_DEF( FT_Error ) - tt_cmap4_init( TT_CMap4 cmap, - FT_Byte* table ) + tt_cmap4_init( FT_CMap cmap, /* TT_CMap4 */ + void* table_ ) { + TT_CMap4 ttcmap = (TT_CMap4)cmap; + FT_Byte* table = (FT_Byte*)table_; FT_Byte* p; - cmap->cmap.data = table; + ttcmap->cmap.data = table; - p = table + 6; - cmap->num_ranges = FT_PEEK_USHORT( p ) >> 1; - cmap->cur_charcode = (FT_UInt32)0xFFFFFFFFUL; - cmap->cur_gindex = 0; + p = table + 6; + ttcmap->num_ranges = FT_PEEK_USHORT( p ) >> 1; + ttcmap->cur_charcode = (FT_UInt32)0xFFFFFFFFUL; + ttcmap->cur_gindex = 0; return FT_Err_Ok; } @@ -756,7 +767,7 @@ cmap->cur_start == 0xFFFFU && cmap->cur_end == 0xFFFFU ) { - TT_Face face = (TT_Face)cmap->cmap.cmap.charmap.face; + TT_Face face = (TT_Face)FT_CMAP_FACE( cmap ); FT_Byte* limit = face->cmap_table + face->cmap_size; @@ -789,15 +800,12 @@ static void tt_cmap4_next( TT_CMap4 cmap ) { - TT_Face face = (TT_Face)cmap->cmap.cmap.charmap.face; + TT_Face face = (TT_Face)FT_CMAP_FACE( cmap ); FT_Byte* limit = face->cmap_table + face->cmap_size; FT_UInt charcode; - if ( cmap->cur_charcode >= 0xFFFFUL ) - goto Fail; - charcode = (FT_UInt)cmap->cur_charcode + 1; if ( charcode < cmap->cur_start ) @@ -883,7 +891,6 @@ charcode = cmap->cur_start; } - Fail: cmap->cur_charcode = (FT_UInt32)0xFFFFFFFFUL; cmap->cur_gindex = 0; } @@ -917,6 +924,16 @@ length = (FT_UInt)( valid->limit - table ); } + /* it also happens that the `length' field is too small; */ + /* this is easy to correct */ + if ( length < (FT_UInt)( valid->limit - table ) ) + { + if ( valid->level >= FT_VALIDATE_PARANOID ) + FT_INVALID_DATA; + + length = (FT_UInt)( valid->limit - table ); + } + if ( length < 16 ) FT_INVALID_TOO_SHORT; @@ -1088,32 +1105,26 @@ FT_UInt32* pcharcode, FT_Bool next ) { - TT_Face face = (TT_Face)cmap->cmap.charmap.face; + TT_Face face = (TT_Face)FT_CMAP_FACE( cmap ); FT_Byte* limit = face->cmap_table + face->cmap_size; FT_UInt num_segs2, start, end, offset; FT_Int delta; FT_UInt i, num_segs; - FT_UInt32 charcode = *pcharcode; + FT_UInt32 charcode = *pcharcode + next; FT_UInt gindex = 0; FT_Byte* p; FT_Byte* q; p = cmap->data + 6; - num_segs2 = FT_PAD_FLOOR( TT_PEEK_USHORT( p ), 2 ); - - num_segs = num_segs2 >> 1; + num_segs = TT_PEEK_USHORT( p ) >> 1; if ( !num_segs ) return 0; - if ( next ) - charcode++; - - if ( charcode > 0xFFFFU ) - return 0; + num_segs2 = num_segs << 1; /* linear search */ p = cmap->data + 14; /* ends table */ @@ -1223,37 +1234,30 @@ FT_UInt32* pcharcode, FT_Bool next ) { - TT_Face face = (TT_Face)cmap->cmap.charmap.face; + TT_Face face = (TT_Face)FT_CMAP_FACE( cmap ); FT_Byte* limit = face->cmap_table + face->cmap_size; FT_UInt num_segs2, start, end, offset; FT_Int delta; FT_UInt max, min, mid, num_segs; - FT_UInt charcode = (FT_UInt)*pcharcode; + FT_UInt charcode = (FT_UInt)*pcharcode + next; FT_UInt gindex = 0; FT_Byte* p; p = cmap->data + 6; - num_segs2 = FT_PAD_FLOOR( TT_PEEK_USHORT( p ), 2 ); + num_segs = TT_PEEK_USHORT( p ) >> 1; - if ( !num_segs2 ) + if ( !num_segs ) return 0; - num_segs = num_segs2 >> 1; - - /* make compiler happy */ - mid = num_segs; - end = 0xFFFFU; - - if ( next ) - charcode++; + num_segs2 = num_segs << 1; min = 0; max = num_segs; /* binary search */ - while ( min < max ) + do { mid = ( min + max ) >> 1; p = cmap->data + 14 + mid * 2; @@ -1436,6 +1440,7 @@ break; } } + while ( min < max ); if ( next ) { @@ -1445,12 +1450,8 @@ /* if `charcode' is not in any segment, then `mid' is */ /* the segment nearest to `charcode' */ - if ( charcode > end ) - { - mid++; - if ( mid == num_segs ) - return 0; - } + if ( charcode > end && ++mid == num_segs ) + return 0; if ( tt_cmap4_set_range( cmap4, mid ) ) { @@ -1465,7 +1466,6 @@ cmap4->cur_gindex = gindex; else { - cmap4->cur_charcode = charcode; tt_cmap4_next( cmap4 ); gindex = cmap4->cur_gindex; } @@ -1480,31 +1480,35 @@ FT_CALLBACK_DEF( FT_UInt ) - tt_cmap4_char_index( TT_CMap cmap, + tt_cmap4_char_index( FT_CMap cmap, /* TT_CMap */ FT_UInt32 char_code ) { + TT_CMap ttcmap = (TT_CMap)cmap; + + if ( char_code >= 0x10000UL ) return 0; - if ( cmap->flags & TT_CMAP_FLAG_UNSORTED ) - return tt_cmap4_char_map_linear( cmap, &char_code, 0 ); + if ( ttcmap->flags & TT_CMAP_FLAG_UNSORTED ) + return tt_cmap4_char_map_linear( ttcmap, &char_code, 0 ); else - return tt_cmap4_char_map_binary( cmap, &char_code, 0 ); + return tt_cmap4_char_map_binary( ttcmap, &char_code, 0 ); } - FT_CALLBACK_DEF( FT_UInt32 ) - tt_cmap4_char_next( TT_CMap cmap, + FT_CALLBACK_DEF( FT_UInt ) + tt_cmap4_char_next( FT_CMap cmap, /* TT_CMap */ FT_UInt32 *pchar_code ) { + TT_CMap ttcmap = (TT_CMap)cmap; FT_UInt gindex; if ( *pchar_code >= 0xFFFFU ) return 0; - if ( cmap->flags & TT_CMAP_FLAG_UNSORTED ) - gindex = tt_cmap4_char_map_linear( cmap, pchar_code, 1 ); + if ( ttcmap->flags & TT_CMAP_FLAG_UNSORTED ) + gindex = tt_cmap4_char_map_linear( ttcmap, pchar_code, 1 ); else { TT_CMap4 cmap4 = (TT_CMap4)cmap; @@ -1519,7 +1523,7 @@ *pchar_code = cmap4->cur_charcode; } else - gindex = tt_cmap4_char_map_binary( cmap, pchar_code, 1 ); + gindex = tt_cmap4_char_map_binary( ttcmap, pchar_code, 1 ); } return gindex; @@ -1527,10 +1531,11 @@ FT_CALLBACK_DEF( FT_Error ) - tt_cmap4_get_info( TT_CMap cmap, + tt_cmap4_get_info( FT_CharMap cmap, /* TT_CMap */ TT_CMapInfo *cmap_info ) { - FT_Byte* p = cmap->data + 4; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* p = ttcmap->data + 4; cmap_info->format = 4; @@ -1631,10 +1636,11 @@ FT_CALLBACK_DEF( FT_UInt ) - tt_cmap6_char_index( TT_CMap cmap, + tt_cmap6_char_index( FT_CMap cmap, /* TT_CMap */ FT_UInt32 char_code ) { - FT_Byte* table = cmap->data; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* table = ttcmap->data; FT_UInt result = 0; FT_Byte* p = table + 6; FT_UInt start = TT_NEXT_USHORT( p ); @@ -1652,11 +1658,12 @@ } - FT_CALLBACK_DEF( FT_UInt32 ) - tt_cmap6_char_next( TT_CMap cmap, + FT_CALLBACK_DEF( FT_UInt ) + tt_cmap6_char_next( FT_CMap cmap, /* TT_CMap */ FT_UInt32 *pchar_code ) { - FT_Byte* table = cmap->data; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* table = ttcmap->data; FT_UInt32 result = 0; FT_UInt32 char_code = *pchar_code + 1; FT_UInt gindex = 0; @@ -1697,10 +1704,11 @@ FT_CALLBACK_DEF( FT_Error ) - tt_cmap6_get_info( TT_CMap cmap, + tt_cmap6_get_info( FT_CharMap cmap, /* TT_CMap */ TT_CMapInfo *cmap_info ) { - FT_Byte* p = cmap->data + 4; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* p = ttcmap->data + 4; cmap_info->format = 6; @@ -1891,10 +1899,11 @@ FT_CALLBACK_DEF( FT_UInt ) - tt_cmap8_char_index( TT_CMap cmap, + tt_cmap8_char_index( FT_CMap cmap, /* TT_CMap */ FT_UInt32 char_code ) { - FT_Byte* table = cmap->data; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* table = ttcmap->data; FT_UInt result = 0; FT_Byte* p = table + 8204; FT_UInt32 num_groups = TT_NEXT_ULONG( p ); @@ -1923,15 +1932,16 @@ } - FT_CALLBACK_DEF( FT_UInt32 ) - tt_cmap8_char_next( TT_CMap cmap, + FT_CALLBACK_DEF( FT_UInt ) + tt_cmap8_char_next( FT_CMap cmap, /* TT_CMap */ FT_UInt32 *pchar_code ) { - FT_Face face = cmap->cmap.charmap.face; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Face face = FT_CMAP_FACE( cmap ); FT_UInt32 result = 0; FT_UInt32 char_code; FT_UInt gindex = 0; - FT_Byte* table = cmap->data; + FT_Byte* table = ttcmap->data; FT_Byte* p = table + 8204; FT_UInt32 num_groups = TT_NEXT_ULONG( p ); FT_UInt32 start, end, start_id; @@ -1991,10 +2001,11 @@ FT_CALLBACK_DEF( FT_Error ) - tt_cmap8_get_info( TT_CMap cmap, + tt_cmap8_get_info( FT_CharMap cmap, /* TT_CMap */ TT_CMapInfo *cmap_info ) { - FT_Byte* p = cmap->data + 8; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* p = ttcmap->data + 8; cmap_info->format = 8; @@ -2095,10 +2106,11 @@ FT_CALLBACK_DEF( FT_UInt ) - tt_cmap10_char_index( TT_CMap cmap, + tt_cmap10_char_index( FT_CMap cmap, /* TT_CMap */ FT_UInt32 char_code ) { - FT_Byte* table = cmap->data; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* table = ttcmap->data; FT_UInt result = 0; FT_Byte* p = table + 12; FT_UInt32 start = TT_NEXT_ULONG( p ); @@ -2121,11 +2133,12 @@ } - FT_CALLBACK_DEF( FT_UInt32 ) - tt_cmap10_char_next( TT_CMap cmap, + FT_CALLBACK_DEF( FT_UInt ) + tt_cmap10_char_next( FT_CMap cmap, /* TT_CMap */ FT_UInt32 *pchar_code ) { - FT_Byte* table = cmap->data; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* table = ttcmap->data; FT_UInt32 char_code; FT_UInt gindex = 0; FT_Byte* p = table + 12; @@ -2163,10 +2176,11 @@ FT_CALLBACK_DEF( FT_Error ) - tt_cmap10_get_info( TT_CMap cmap, + tt_cmap10_get_info( FT_CharMap cmap, /* TT_CMap */ TT_CMapInfo *cmap_info ) { - FT_Byte* p = cmap->data + 8; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* p = ttcmap->data + 8; cmap_info->format = 10; @@ -2244,15 +2258,19 @@ FT_CALLBACK_DEF( FT_Error ) - tt_cmap12_init( TT_CMap12 cmap, - FT_Byte* table ) + tt_cmap12_init( FT_CMap cmap, /* TT_CMap12 */ + void* table_ ) { - cmap->cmap.data = table; + TT_CMap12 ttcmap = (TT_CMap12)cmap; + FT_Byte* table = (FT_Byte*)table_; + + + ttcmap->cmap.data = table; - table += 12; - cmap->num_groups = FT_PEEK_ULONG( table ); + table += 12; + ttcmap->num_groups = FT_PEEK_ULONG( table ); - cmap->valid = 0; + ttcmap->valid = 0; return FT_Err_Ok; } @@ -2322,23 +2340,21 @@ /* cmap->cur_group should be set up properly by caller */ /* */ static void - tt_cmap12_next( TT_CMap12 cmap ) + tt_cmap12_next( FT_CMap cmap ) /* TT_CMap12 */ { - FT_Face face = cmap->cmap.cmap.charmap.face; - FT_Byte* p; - FT_ULong start, end, start_id, char_code; - FT_ULong n; - FT_UInt gindex; - + TT_CMap12 ttcmap = (TT_CMap12)cmap; + FT_Face face = FT_CMAP_FACE( cmap ); + FT_Byte* p; + FT_ULong start, end, start_id, char_code; + FT_ULong n; + FT_UInt gindex; - if ( cmap->cur_charcode >= 0xFFFFFFFFUL ) - goto Fail; - char_code = cmap->cur_charcode + 1; + char_code = ttcmap->cur_charcode + 1; - for ( n = cmap->cur_group; n < cmap->num_groups; n++ ) + for ( n = ttcmap->cur_group; n < ttcmap->num_groups; n++ ) { - p = cmap->cmap.data + 16 + 12 * n; + p = ttcmap->cmap.data + 16 + 12 * n; start = TT_NEXT_ULONG( p ); end = TT_NEXT_ULONG( p ); start_id = TT_PEEK_ULONG( p ); @@ -2370,16 +2386,16 @@ if ( gindex >= (FT_UInt)face->num_glyphs ) continue; - cmap->cur_charcode = char_code; - cmap->cur_gindex = gindex; - cmap->cur_group = n; + ttcmap->cur_charcode = char_code; + ttcmap->cur_gindex = gindex; + ttcmap->cur_group = n; return; } } Fail: - cmap->valid = 0; + ttcmap->valid = 0; } @@ -2391,7 +2407,7 @@ FT_UInt gindex = 0; FT_Byte* p = cmap->data + 12; FT_UInt32 num_groups = TT_PEEK_ULONG( p ); - FT_UInt32 char_code = *pchar_code; + FT_UInt32 char_code = *pchar_code + next; FT_UInt32 start, end, start_id; FT_UInt32 max, min, mid; @@ -2399,23 +2415,11 @@ if ( !num_groups ) return 0; - /* make compiler happy */ - mid = num_groups; - end = 0xFFFFFFFFUL; - - if ( next ) - { - if ( char_code >= 0xFFFFFFFFUL ) - return 0; - - char_code++; - } - min = 0; max = num_groups; /* binary search */ - while ( min < max ) + do { mid = ( min + max ) >> 1; p = cmap->data + 16 + 12 * mid; @@ -2439,22 +2443,19 @@ break; } } + while ( min < max ); if ( next ) { - FT_Face face = cmap->cmap.charmap.face; + FT_Face face = FT_CMAP_FACE( cmap ); TT_CMap12 cmap12 = (TT_CMap12)cmap; /* if `char_code' is not in any group, then `mid' is */ /* the group nearest to `char_code' */ - if ( char_code > end ) - { - mid++; - if ( mid == num_groups ) - return 0; - } + if ( char_code > end && ++mid == num_groups ) + return 0; cmap12->valid = 1; cmap12->cur_charcode = char_code; @@ -2465,7 +2466,7 @@ if ( !gindex ) { - tt_cmap12_next( cmap12 ); + tt_cmap12_next( FT_CMAP( cmap12 ) ); if ( cmap12->valid ) gindex = cmap12->cur_gindex; @@ -2481,25 +2482,28 @@ FT_CALLBACK_DEF( FT_UInt ) - tt_cmap12_char_index( TT_CMap cmap, + tt_cmap12_char_index( FT_CMap cmap, /* TT_CMap */ FT_UInt32 char_code ) { - return tt_cmap12_char_map_binary( cmap, &char_code, 0 ); + return tt_cmap12_char_map_binary( (TT_CMap)cmap, &char_code, 0 ); } - FT_CALLBACK_DEF( FT_UInt32 ) - tt_cmap12_char_next( TT_CMap cmap, + FT_CALLBACK_DEF( FT_UInt ) + tt_cmap12_char_next( FT_CMap cmap, /* TT_CMap12 */ FT_UInt32 *pchar_code ) { TT_CMap12 cmap12 = (TT_CMap12)cmap; FT_UInt gindex; + if ( *pchar_code >= 0xFFFFFFFFUL ) + return 0; + /* no need to search */ if ( cmap12->valid && cmap12->cur_charcode == *pchar_code ) { - tt_cmap12_next( cmap12 ); + tt_cmap12_next( FT_CMAP( cmap12 ) ); if ( cmap12->valid ) { gindex = cmap12->cur_gindex; @@ -2509,17 +2513,18 @@ gindex = 0; } else - gindex = tt_cmap12_char_map_binary( cmap, pchar_code, 1 ); + gindex = tt_cmap12_char_map_binary( (TT_CMap)cmap, pchar_code, 1 ); return gindex; } FT_CALLBACK_DEF( FT_Error ) - tt_cmap12_get_info( TT_CMap cmap, + tt_cmap12_get_info( FT_CharMap cmap, /* TT_CMap */ TT_CMapInfo *cmap_info ) { - FT_Byte* p = cmap->data + 8; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* p = ttcmap->data + 8; cmap_info->format = 12; @@ -2597,15 +2602,19 @@ FT_CALLBACK_DEF( FT_Error ) - tt_cmap13_init( TT_CMap13 cmap, - FT_Byte* table ) + tt_cmap13_init( FT_CMap cmap, /* TT_CMap13 */ + void* table_ ) { - cmap->cmap.data = table; + TT_CMap13 ttcmap = (TT_CMap13)cmap; + FT_Byte* table = (FT_Byte*)table_; - table += 12; - cmap->num_groups = FT_PEEK_ULONG( table ); - cmap->valid = 0; + ttcmap->cmap.data = table; + + table += 12; + ttcmap->num_groups = FT_PEEK_ULONG( table ); + + ttcmap->valid = 0; return FT_Err_Ok; } @@ -2670,23 +2679,21 @@ /* cmap->cur_group should be set up properly by caller */ /* */ static void - tt_cmap13_next( TT_CMap13 cmap ) + tt_cmap13_next( FT_CMap cmap ) /* TT_CMap13 */ { - FT_Face face = cmap->cmap.cmap.charmap.face; - FT_Byte* p; - FT_ULong start, end, glyph_id, char_code; - FT_ULong n; - FT_UInt gindex; - + TT_CMap13 ttcmap = (TT_CMap13)cmap; + FT_Face face = FT_CMAP_FACE( cmap ); + FT_Byte* p; + FT_ULong start, end, glyph_id, char_code; + FT_ULong n; + FT_UInt gindex; - if ( cmap->cur_charcode >= 0xFFFFFFFFUL ) - goto Fail; - char_code = cmap->cur_charcode + 1; + char_code = ttcmap->cur_charcode + 1; - for ( n = cmap->cur_group; n < cmap->num_groups; n++ ) + for ( n = ttcmap->cur_group; n < ttcmap->num_groups; n++ ) { - p = cmap->cmap.data + 16 + 12 * n; + p = ttcmap->cmap.data + 16 + 12 * n; start = TT_NEXT_ULONG( p ); end = TT_NEXT_ULONG( p ); glyph_id = TT_PEEK_ULONG( p ); @@ -2700,17 +2707,16 @@ if ( gindex && gindex < (FT_UInt)face->num_glyphs ) { - cmap->cur_charcode = char_code; - cmap->cur_gindex = gindex; - cmap->cur_group = n; + ttcmap->cur_charcode = char_code; + ttcmap->cur_gindex = gindex; + ttcmap->cur_group = n; return; } } } - Fail: - cmap->valid = 0; + ttcmap->valid = 0; } @@ -2722,7 +2728,7 @@ FT_UInt gindex = 0; FT_Byte* p = cmap->data + 12; FT_UInt32 num_groups = TT_PEEK_ULONG( p ); - FT_UInt32 char_code = *pchar_code; + FT_UInt32 char_code = *pchar_code + next; FT_UInt32 start, end; FT_UInt32 max, min, mid; @@ -2730,23 +2736,11 @@ if ( !num_groups ) return 0; - /* make compiler happy */ - mid = num_groups; - end = 0xFFFFFFFFUL; - - if ( next ) - { - if ( char_code >= 0xFFFFFFFFUL ) - return 0; - - char_code++; - } - min = 0; max = num_groups; /* binary search */ - while ( min < max ) + do { mid = ( min + max ) >> 1; p = cmap->data + 16 + 12 * mid; @@ -2765,6 +2759,7 @@ break; } } + while ( min < max ); if ( next ) { @@ -2775,12 +2770,8 @@ /* if `char_code' is not in any group, then `mid' is */ /* the group nearest to `char_code' */ - if ( char_code > end ) - { - mid++; - if ( mid == num_groups ) - return 0; - } + if ( char_code > end && ++mid == num_groups ) + return 0; cmap13->valid = 1; cmap13->cur_charcode = char_code; @@ -2791,7 +2782,7 @@ if ( !gindex ) { - tt_cmap13_next( cmap13 ); + tt_cmap13_next( FT_CMAP( cmap13 ) ); if ( cmap13->valid ) gindex = cmap13->cur_gindex; @@ -2807,25 +2798,28 @@ FT_CALLBACK_DEF( FT_UInt ) - tt_cmap13_char_index( TT_CMap cmap, + tt_cmap13_char_index( FT_CMap cmap, /* TT_CMap */ FT_UInt32 char_code ) { - return tt_cmap13_char_map_binary( cmap, &char_code, 0 ); + return tt_cmap13_char_map_binary( (TT_CMap)cmap, &char_code, 0 ); } - FT_CALLBACK_DEF( FT_UInt32 ) - tt_cmap13_char_next( TT_CMap cmap, + FT_CALLBACK_DEF( FT_UInt ) + tt_cmap13_char_next( FT_CMap cmap, /* TT_CMap13 */ FT_UInt32 *pchar_code ) { TT_CMap13 cmap13 = (TT_CMap13)cmap; FT_UInt gindex; + if ( *pchar_code >= 0xFFFFFFFFUL ) + return 0; + /* no need to search */ if ( cmap13->valid && cmap13->cur_charcode == *pchar_code ) { - tt_cmap13_next( cmap13 ); + tt_cmap13_next( FT_CMAP( cmap13 ) ); if ( cmap13->valid ) { gindex = cmap13->cur_gindex; @@ -2835,17 +2829,18 @@ gindex = 0; } else - gindex = tt_cmap13_char_map_binary( cmap, pchar_code, 1 ); + gindex = tt_cmap13_char_map_binary( (TT_CMap)cmap, pchar_code, 1 ); return gindex; } FT_CALLBACK_DEF( FT_Error ) - tt_cmap13_get_info( TT_CMap cmap, + tt_cmap13_get_info( FT_CharMap cmap, /* TT_CMap */ TT_CMapInfo *cmap_info ) { - FT_Byte* p = cmap->data + 8; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* p = ttcmap->data + 8; cmap_info->format = 13; @@ -2960,14 +2955,15 @@ FT_CALLBACK_DEF( void ) - tt_cmap14_done( TT_CMap14 cmap ) + tt_cmap14_done( FT_CMap cmap ) /* TT_CMap14 */ { - FT_Memory memory = cmap->memory; + TT_CMap14 ttcmap = (TT_CMap14)cmap; + FT_Memory memory = ttcmap->memory; - cmap->max_results = 0; - if ( memory && cmap->results ) - FT_FREE( cmap->results ); + ttcmap->max_results = 0; + if ( memory && ttcmap->results ) + FT_FREE( ttcmap->results ); } @@ -2995,15 +2991,19 @@ FT_CALLBACK_DEF( FT_Error ) - tt_cmap14_init( TT_CMap14 cmap, - FT_Byte* table ) + tt_cmap14_init( FT_CMap cmap, /* TT_CMap14 */ + void* table_ ) { - cmap->cmap.data = table; + TT_CMap14 ttcmap = (TT_CMap14)cmap; + FT_Byte* table = (FT_Byte*)table_; + + + ttcmap->cmap.data = table; - table += 6; - cmap->num_selectors = FT_PEEK_ULONG( table ); - cmap->max_results = 0; - cmap->results = NULL; + table += 6; + ttcmap->num_selectors = FT_PEEK_ULONG( table ); + ttcmap->max_results = 0; + ttcmap->results = NULL; return FT_Err_Ok; } @@ -3133,7 +3133,7 @@ FT_CALLBACK_DEF( FT_UInt ) - tt_cmap14_char_index( TT_CMap cmap, + tt_cmap14_char_index( FT_CMap cmap, FT_UInt32 char_code ) { FT_UNUSED( cmap ); @@ -3144,8 +3144,8 @@ } - FT_CALLBACK_DEF( FT_UInt32 ) - tt_cmap14_char_next( TT_CMap cmap, + FT_CALLBACK_DEF( FT_UInt ) + tt_cmap14_char_next( FT_CMap cmap, FT_UInt32 *pchar_code ) { FT_UNUSED( cmap ); @@ -3157,7 +3157,7 @@ FT_CALLBACK_DEF( FT_Error ) - tt_cmap14_get_info( TT_CMap cmap, + tt_cmap14_get_info( FT_CharMap cmap, TT_CMapInfo *cmap_info ) { FT_UNUSED( cmap ); @@ -3271,12 +3271,16 @@ FT_CALLBACK_DEF( FT_UInt ) - tt_cmap14_char_var_index( TT_CMap cmap, - TT_CMap ucmap, + tt_cmap14_char_var_index( FT_CMap cmap, /* TT_CMap */ + FT_CMap ucmap, /* TT_CMap */ FT_UInt32 charcode, FT_UInt32 variantSelector ) { - FT_Byte* p = tt_cmap14_find_variant( cmap->data + 6, variantSelector ); + TT_CMap ttcmap = (TT_CMap)cmap; + TT_CMap ttucmap = (TT_CMap)ucmap; + + FT_Byte* p = tt_cmap14_find_variant( ttcmap->data + 6, + variantSelector ); FT_ULong defOff; FT_ULong nondefOff; @@ -3287,16 +3291,16 @@ defOff = TT_NEXT_ULONG( p ); nondefOff = TT_PEEK_ULONG( p ); - if ( defOff != 0 && - tt_cmap14_char_map_def_binary( cmap->data + defOff, charcode ) ) + if ( defOff != 0 && + tt_cmap14_char_map_def_binary( ttcmap->data + defOff, charcode ) ) { /* This is the default variant of this charcode. GID not stored */ /* here; stored in the normal Unicode charmap instead. */ - return ucmap->cmap.clazz->char_index( &ucmap->cmap, charcode ); + return ttucmap->cmap.clazz->char_index( &ttucmap->cmap, charcode ); } if ( nondefOff != 0 ) - return tt_cmap14_char_map_nondef_binary( cmap->data + nondefOff, + return tt_cmap14_char_map_nondef_binary( ttcmap->data + nondefOff, charcode ); return 0; @@ -3304,11 +3308,13 @@ FT_CALLBACK_DEF( FT_Int ) - tt_cmap14_char_var_isdefault( TT_CMap cmap, + tt_cmap14_char_var_isdefault( FT_CMap cmap, /* TT_CMap */ FT_UInt32 charcode, FT_UInt32 variantSelector ) { - FT_Byte* p = tt_cmap14_find_variant( cmap->data + 6, variantSelector ); + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte* p = tt_cmap14_find_variant( ttcmap->data + 6, + variantSelector ); FT_ULong defOff; FT_ULong nondefOff; @@ -3319,13 +3325,13 @@ defOff = TT_NEXT_ULONG( p ); nondefOff = TT_NEXT_ULONG( p ); - if ( defOff != 0 && - tt_cmap14_char_map_def_binary( cmap->data + defOff, charcode ) ) + if ( defOff != 0 && + tt_cmap14_char_map_def_binary( ttcmap->data + defOff, charcode ) ) return 1; - if ( nondefOff != 0 && - tt_cmap14_char_map_nondef_binary( cmap->data + nondefOff, - charcode ) != 0 ) + if ( nondefOff != 0 && + tt_cmap14_char_map_nondef_binary( ttcmap->data + nondefOff, + charcode ) != 0 ) return 0; return -1; @@ -3333,12 +3339,13 @@ FT_CALLBACK_DEF( FT_UInt32* ) - tt_cmap14_variants( TT_CMap cmap, + tt_cmap14_variants( FT_CMap cmap, /* TT_CMap14 */ FT_Memory memory ) { + TT_CMap ttcmap = (TT_CMap)cmap; TT_CMap14 cmap14 = (TT_CMap14)cmap; FT_UInt32 count = cmap14->num_selectors; - FT_Byte* p = cmap->data + 10; + FT_Byte* p = ttcmap->data + 10; FT_UInt32* result; FT_UInt32 i; @@ -3359,13 +3366,14 @@ FT_CALLBACK_DEF( FT_UInt32 * ) - tt_cmap14_char_variants( TT_CMap cmap, + tt_cmap14_char_variants( FT_CMap cmap, /* TT_CMap14 */ FT_Memory memory, FT_UInt32 charCode ) { - TT_CMap14 cmap14 = (TT_CMap14) cmap; + TT_CMap ttcmap = (TT_CMap)cmap; + TT_CMap14 cmap14 = (TT_CMap14)cmap; FT_UInt32 count = cmap14->num_selectors; - FT_Byte* p = cmap->data + 10; + FT_Byte* p = ttcmap->data + 10; FT_UInt32* q; @@ -3379,12 +3387,12 @@ FT_ULong nondefOff = TT_NEXT_ULONG( p ); - if ( ( defOff != 0 && - tt_cmap14_char_map_def_binary( cmap->data + defOff, - charCode ) ) || - ( nondefOff != 0 && - tt_cmap14_char_map_nondef_binary( cmap->data + nondefOff, - charCode ) != 0 ) ) + if ( ( defOff != 0 && + tt_cmap14_char_map_def_binary( ttcmap->data + defOff, + charCode ) ) || + ( nondefOff != 0 && + tt_cmap14_char_map_nondef_binary( ttcmap->data + nondefOff, + charCode ) != 0 ) ) { q[0] = varSel; q++; @@ -3480,15 +3488,16 @@ FT_CALLBACK_DEF( FT_UInt32 * ) - tt_cmap14_variant_chars( TT_CMap cmap, + tt_cmap14_variant_chars( FT_CMap cmap, /* TT_CMap */ FT_Memory memory, FT_UInt32 variantSelector ) { - FT_Byte *p = tt_cmap14_find_variant( cmap->data + 6, - variantSelector ); - FT_Int i; - FT_ULong defOff; - FT_ULong nondefOff; + TT_CMap ttcmap = (TT_CMap)cmap; + FT_Byte *p = tt_cmap14_find_variant( ttcmap->data + 6, + variantSelector ); + FT_Int i; + FT_ULong defOff; + FT_ULong nondefOff; if ( !p ) @@ -3501,16 +3510,16 @@ return NULL; if ( defOff == 0 ) - return tt_cmap14_get_nondef_chars( cmap, cmap->data + nondefOff, + return tt_cmap14_get_nondef_chars( ttcmap, ttcmap->data + nondefOff, memory ); else if ( nondefOff == 0 ) - return tt_cmap14_get_def_chars( cmap, cmap->data + defOff, + return tt_cmap14_get_def_chars( ttcmap, ttcmap->data + defOff, memory ); else { /* Both a default and a non-default glyph set? That's probably not */ /* good font design, but the spec allows for it... */ - TT_CMap14 cmap14 = (TT_CMap14) cmap; + TT_CMap14 cmap14 = (TT_CMap14)cmap; FT_UInt32 numRanges; FT_UInt32 numMappings; FT_UInt32 duni; @@ -3522,18 +3531,18 @@ FT_UInt32 *ret; - p = cmap->data + nondefOff; - dp = cmap->data + defOff; + p = ttcmap->data + nondefOff; + dp = ttcmap->data + defOff; numMappings = (FT_UInt32)TT_NEXT_ULONG( p ); dcnt = tt_cmap14_def_char_count( dp ); numRanges = (FT_UInt32)TT_NEXT_ULONG( dp ); if ( numMappings == 0 ) - return tt_cmap14_get_def_chars( cmap, cmap->data + defOff, + return tt_cmap14_get_def_chars( ttcmap, ttcmap->data + defOff, memory ); if ( dcnt == 0 ) - return tt_cmap14_get_nondef_chars( cmap, cmap->data + nondefOff, + return tt_cmap14_get_nondef_chars( ttcmap, ttcmap->data + nondefOff, memory ); if ( tt_cmap14_ensure( cmap14, ( dcnt + numMappings + 1 ), memory ) ) @@ -3655,9 +3664,10 @@ #ifdef FT_CONFIG_OPTION_POSTSCRIPT_NAMES FT_CALLBACK_DEF( const char * ) - tt_get_glyph_name( TT_Face face, + tt_get_glyph_name( void* face_, /* TT_Face */ FT_UInt idx ) { + TT_Face face = (TT_Face)face_; FT_String* PSname = NULL; @@ -3668,12 +3678,13 @@ FT_CALLBACK_DEF( FT_Error ) - tt_cmap_unicode_init( PS_Unicodes unicodes, - FT_Pointer pointer ) + tt_cmap_unicode_init( FT_CMap cmap, /* PS_Unicodes */ + FT_Pointer pointer ) { - TT_Face face = (TT_Face)FT_CMAP_FACE( unicodes ); - FT_Memory memory = FT_FACE_MEMORY( face ); - FT_Service_PsCMaps psnames = (FT_Service_PsCMaps)face->psnames; + PS_Unicodes unicodes = (PS_Unicodes)cmap; + TT_Face face = (TT_Face)FT_CMAP_FACE( cmap ); + FT_Memory memory = FT_FACE_MEMORY( face ); + FT_Service_PsCMaps psnames = (FT_Service_PsCMaps)face->psnames; FT_UNUSED( pointer ); @@ -3684,17 +3695,18 @@ return psnames->unicodes_init( memory, unicodes, face->root.num_glyphs, - (PS_GetGlyphNameFunc)&tt_get_glyph_name, + &tt_get_glyph_name, (PS_FreeGlyphNameFunc)NULL, (FT_Pointer)face ); } FT_CALLBACK_DEF( void ) - tt_cmap_unicode_done( PS_Unicodes unicodes ) + tt_cmap_unicode_done( FT_CMap cmap ) /* PS_Unicodes */ { - FT_Face face = FT_CMAP_FACE( unicodes ); - FT_Memory memory = FT_FACE_MEMORY( face ); + PS_Unicodes unicodes = (PS_Unicodes)cmap; + FT_Face face = FT_CMAP_FACE( cmap ); + FT_Memory memory = FT_FACE_MEMORY( face ); FT_FREE( unicodes->maps ); @@ -3703,23 +3715,25 @@ FT_CALLBACK_DEF( FT_UInt ) - tt_cmap_unicode_char_index( PS_Unicodes unicodes, - FT_UInt32 char_code ) + tt_cmap_unicode_char_index( FT_CMap cmap, /* PS_Unicodes */ + FT_UInt32 char_code ) { - TT_Face face = (TT_Face)FT_CMAP_FACE( unicodes ); - FT_Service_PsCMaps psnames = (FT_Service_PsCMaps)face->psnames; + PS_Unicodes unicodes = (PS_Unicodes)cmap; + TT_Face face = (TT_Face)FT_CMAP_FACE( cmap ); + FT_Service_PsCMaps psnames = (FT_Service_PsCMaps)face->psnames; return psnames->unicodes_char_index( unicodes, char_code ); } - FT_CALLBACK_DEF( FT_UInt32 ) - tt_cmap_unicode_char_next( PS_Unicodes unicodes, - FT_UInt32 *pchar_code ) + FT_CALLBACK_DEF( FT_UInt ) + tt_cmap_unicode_char_next( FT_CMap cmap, /* PS_Unicodes */ + FT_UInt32 *pchar_code ) { - TT_Face face = (TT_Face)FT_CMAP_FACE( unicodes ); - FT_Service_PsCMaps psnames = (FT_Service_PsCMaps)face->psnames; + PS_Unicodes unicodes = (PS_Unicodes)cmap; + TT_Face face = (TT_Face)FT_CMAP_FACE( cmap ); + FT_Service_PsCMaps psnames = (FT_Service_PsCMaps)face->psnames; return psnames->unicodes_char_next( unicodes, pchar_code ); @@ -3752,6 +3766,7 @@ static const TT_CMap_Class tt_cmap_classes[] = { +#undef TTCMAPCITEM #define TTCMAPCITEM( a ) &a, #include "ttcmapc.h" NULL, @@ -3788,8 +3803,9 @@ p += 2; num_cmaps = TT_NEXT_USHORT( p ); - limit = table + face->cmap_size; + FT_TRACE4(( "tt_face_build_cmaps: %d cmaps\n", num_cmaps )); + limit = table + face->cmap_size; for ( ; num_cmaps > 0 && p + 8 <= limit; num_cmaps-- ) { FT_CharMapRec charmap; @@ -3868,13 +3884,14 @@ } - FT_LOCAL( FT_Error ) + FT_LOCAL_DEF( FT_Error ) tt_get_cmap_info( FT_CharMap charmap, TT_CMapInfo *cmap_info ) { - FT_CMap cmap = (FT_CMap)charmap; + FT_CMap cmap = FT_CMAP( charmap ); TT_CMap_Class clazz = (TT_CMap_Class)cmap->clazz; + if ( clazz->get_cmap_info ) return clazz->get_cmap_info( charmap, cmap_info ); else diff --git a/src/font/freetype-2.10.2/src/sfnt/ttcmap.h b/3rdparty/freetype-2.13.2/src/sfnt/ttcmap.h similarity index 92% rename from src/font/freetype-2.10.2/src/sfnt/ttcmap.h rename to 3rdparty/freetype-2.13.2/src/sfnt/ttcmap.h index 4bf49e2d4..ff52917ed 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttcmap.h +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttcmap.h @@ -4,7 +4,7 @@ * * TrueType character mapping table (cmap) support (specification). * - * Copyright (C) 2002-2020 by + * Copyright (C) 2002-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,10 +20,9 @@ #define TTCMAP_H_ -#include -#include FT_INTERNAL_TRUETYPE_TYPES_H -#include FT_INTERNAL_VALIDATE_H -#include FT_SERVICE_TT_CMAP_H +#include +#include +#include FT_BEGIN_HEADER @@ -91,6 +90,11 @@ FT_BEGIN_HEADER }; +#undef TTCMAPCITEM +#define TTCMAPCITEM( a ) FT_CALLBACK_TABLE const TT_CMap_ClassRec a; +#include "ttcmapc.h" + + typedef struct TT_ValidatorRec_ { FT_ValidatorRec validator; diff --git a/src/font/freetype-2.10.2/src/sfnt/ttcmapc.h b/3rdparty/freetype-2.13.2/src/sfnt/ttcmapc.h similarity index 97% rename from src/font/freetype-2.10.2/src/sfnt/ttcmapc.h rename to 3rdparty/freetype-2.13.2/src/sfnt/ttcmapc.h index 2e4ce5075..0af48c247 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttcmapc.h +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttcmapc.h @@ -4,7 +4,7 @@ * * TT CMAP classes definitions (specification only). * - * Copyright (C) 2009-2020 by + * Copyright (C) 2009-2023 by * Oran Agra and Mickey Gabel. * * This file is part of the FreeType project, and may only be used, diff --git a/3rdparty/freetype-2.13.2/src/sfnt/ttcolr.c b/3rdparty/freetype-2.13.2/src/sfnt/ttcolr.c new file mode 100644 index 000000000..281e7135e --- /dev/null +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttcolr.c @@ -0,0 +1,1921 @@ +/**************************************************************************** + * + * ttcolr.c + * + * TrueType and OpenType colored glyph layer support (body). + * + * Copyright (C) 2018-2023 by + * David Turner, Robert Wilhelm, Dominik Röttsches, and Werner Lemberg. + * + * Originally written by Shao Yu Zhang . + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + + /************************************************************************** + * + * `COLR' table specification: + * + * https://www.microsoft.com/typography/otspec/colr.htm + * + */ + + +#include +#include +#include +#include +#include +#include + +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT +#include +#endif + +#ifdef TT_CONFIG_OPTION_COLOR_LAYERS + +#include "ttcolr.h" + + + /* NOTE: These are the table sizes calculated through the specs. */ +#define BASE_GLYPH_SIZE 6U +#define BASE_GLYPH_PAINT_RECORD_SIZE 6U +#define LAYER_V1_LIST_PAINT_OFFSET_SIZE 4U +#define LAYER_V1_LIST_NUM_LAYERS_SIZE 4U +#define COLOR_STOP_SIZE 6U +#define VAR_IDX_BASE_SIZE 4U +#define LAYER_SIZE 4U +/* https://docs.microsoft.com/en-us/typography/opentype/spec/colr#colr-header */ +/* 3 * uint16 + 2 * Offset32 */ +#define COLRV0_HEADER_SIZE 14U +/* COLRV0_HEADER_SIZE + 5 * Offset32 */ +#define COLRV1_HEADER_SIZE 34U + + +#define ENSURE_READ_BYTES( byte_size ) \ + if ( p < colr->paints_start_v1 || \ + p > (FT_Byte*)colr->table + colr->table_size - byte_size ) \ + return 0 + + + typedef enum FT_PaintFormat_Internal_ + { + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SOLID = 3, + FT_COLR_PAINTFORMAT_INTERNAL_VAR_LINEAR_GRADIENT = 5, + FT_COLR_PAINTFORMAT_INTERNAL_VAR_RADIAL_GRADIENT = 7, + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SWEEP_GRADIENT = 9, + FT_COLR_PAINTFORMAT_INTERNAL_VAR_TRANSFORM = 13, + FT_COLR_PAINTFORMAT_INTERNAL_VAR_TRANSLATE = 15, + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SCALE = 17, + FT_COLR_PAINTFORMAT_INTERNAL_SCALE_CENTER = 18, + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SCALE_CENTER = 19, + FT_COLR_PAINTFORMAT_INTERNAL_SCALE_UNIFORM = 20, + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SCALE_UNIFORM = 21, + FT_COLR_PAINTFORMAT_INTERNAL_SCALE_UNIFORM_CENTER = 22, + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SCALE_UNIFORM_CENTER = 23, + FT_COLR_PAINTFORMAT_INTERNAL_VAR_ROTATE = 25, + FT_COLR_PAINTFORMAT_INTERNAL_ROTATE_CENTER = 26, + FT_COLR_PAINTFORMAT_INTERNAL_VAR_ROTATE_CENTER = 27, + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SKEW = 29, + FT_COLR_PAINTFORMAT_INTERNAL_SKEW_CENTER = 30, + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SKEW_CENTER = 31, + + } FT_PaintFormat_Internal; + + + typedef struct BaseGlyphRecord_ + { + FT_UShort gid; + FT_UShort first_layer_index; + FT_UShort num_layers; + + } BaseGlyphRecord; + + + typedef struct BaseGlyphV1Record_ + { + FT_UShort gid; + /* Offset from start of BaseGlyphV1List, i.e., from base_glyphs_v1. */ + FT_ULong paint_offset; + + } BaseGlyphV1Record; + + + typedef struct Colr_ + { + FT_UShort version; + FT_UShort num_base_glyphs; + FT_UShort num_layers; + + FT_Byte* base_glyphs; + FT_Byte* layers; + + FT_ULong num_base_glyphs_v1; + /* Points at beginning of BaseGlyphV1List. */ + FT_Byte* base_glyphs_v1; + + FT_ULong num_layers_v1; + FT_Byte* layers_v1; + + FT_Byte* clip_list; + + /* + * Paint tables start at the minimum of the end of the LayerList and the + * end of the BaseGlyphList. Record this location in a field here for + * safety checks when accessing paint tables. + */ + FT_Byte* paints_start_v1; + +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + /* Item Variation Store for variable 'COLR' v1. */ + GX_ItemVarStoreRec var_store; + GX_DeltaSetIdxMapRec delta_set_idx_map; +#endif + + /* The memory that backs up the `COLR' table. */ + void* table; + FT_ULong table_size; + + } Colr; + + + /************************************************************************** + * + * The macro FT_COMPONENT is used in trace mode. It is an implicit + * parameter of the FT_TRACE() and FT_ERROR() macros, used to print/log + * messages during execution. + */ +#undef FT_COMPONENT +#define FT_COMPONENT ttcolr + + + FT_LOCAL_DEF( FT_Error ) + tt_face_load_colr( TT_Face face, + FT_Stream stream ) + { + FT_Error error; + FT_Memory memory = face->root.memory; + + FT_Byte* table = NULL; + FT_Byte* p = NULL; + /* Needed for reading array lengths in referenced tables. */ + FT_Byte* p1 = NULL; + + Colr* colr = NULL; + + FT_ULong base_glyph_offset, layer_offset; + FT_ULong base_glyphs_offset_v1, num_base_glyphs_v1; + FT_ULong layer_offset_v1, num_layers_v1, clip_list_offset; + FT_ULong table_size; +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + FT_ULong colr_offset_in_stream; +#endif + + + /* `COLR' always needs `CPAL' */ + if ( !face->cpal ) + return FT_THROW( Invalid_File_Format ); + + error = face->goto_table( face, TTAG_COLR, stream, &table_size ); + if ( error ) + goto NoColr; + +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + colr_offset_in_stream = FT_STREAM_POS(); +#endif + + if ( table_size < COLRV0_HEADER_SIZE ) + goto NoColr; + + if ( FT_FRAME_EXTRACT( table_size, table ) ) + goto NoColr; + + p = table; + + if ( FT_NEW( colr ) ) + goto NoColr; + + colr->version = FT_NEXT_USHORT( p ); + if ( colr->version != 0 && colr->version != 1 ) + goto InvalidTable; + + colr->num_base_glyphs = FT_NEXT_USHORT( p ); + base_glyph_offset = FT_NEXT_ULONG( p ); + + if ( base_glyph_offset >= table_size ) + goto InvalidTable; + if ( colr->num_base_glyphs * BASE_GLYPH_SIZE > + table_size - base_glyph_offset ) + goto InvalidTable; + + layer_offset = FT_NEXT_ULONG( p ); + colr->num_layers = FT_NEXT_USHORT( p ); + + if ( layer_offset >= table_size ) + goto InvalidTable; + if ( colr->num_layers * LAYER_SIZE > table_size - layer_offset ) + goto InvalidTable; + + if ( colr->version == 1 ) + { + if ( table_size < COLRV1_HEADER_SIZE ) + goto InvalidTable; + + base_glyphs_offset_v1 = FT_NEXT_ULONG( p ); + + if ( base_glyphs_offset_v1 >= table_size - 4 ) + goto InvalidTable; + + p1 = (FT_Byte*)( table + base_glyphs_offset_v1 ); + num_base_glyphs_v1 = FT_PEEK_ULONG( p1 ); + + if ( num_base_glyphs_v1 * BASE_GLYPH_PAINT_RECORD_SIZE > + table_size - base_glyphs_offset_v1 ) + goto InvalidTable; + + colr->num_base_glyphs_v1 = num_base_glyphs_v1; + colr->base_glyphs_v1 = p1; + + layer_offset_v1 = FT_NEXT_ULONG( p ); + + if ( layer_offset_v1 >= table_size ) + goto InvalidTable; + + if ( layer_offset_v1 ) + { + if ( layer_offset_v1 >= table_size - 4 ) + goto InvalidTable; + + p1 = (FT_Byte*)( table + layer_offset_v1 ); + num_layers_v1 = FT_PEEK_ULONG( p1 ); + + if ( num_layers_v1 * LAYER_V1_LIST_PAINT_OFFSET_SIZE > + table_size - layer_offset_v1 ) + goto InvalidTable; + + colr->num_layers_v1 = num_layers_v1; + colr->layers_v1 = p1; + + colr->paints_start_v1 = + FT_MIN( colr->base_glyphs_v1 + + colr->num_base_glyphs_v1 * BASE_GLYPH_PAINT_RECORD_SIZE, + colr->layers_v1 + + colr->num_layers_v1 * LAYER_V1_LIST_PAINT_OFFSET_SIZE ); + } + else + { + colr->num_layers_v1 = 0; + colr->layers_v1 = 0; + colr->paints_start_v1 = + colr->base_glyphs_v1 + + colr->num_base_glyphs_v1 * BASE_GLYPH_PAINT_RECORD_SIZE; + } + + clip_list_offset = FT_NEXT_ULONG( p ); + + if ( clip_list_offset >= table_size ) + goto InvalidTable; + + if ( clip_list_offset ) + colr->clip_list = (FT_Byte*)( table + clip_list_offset ); + else + colr->clip_list = 0; + +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + colr->var_store.dataCount = 0; + colr->var_store.varData = NULL; + colr->var_store.axisCount = 0; + colr->var_store.regionCount = 0; + colr->var_store.varRegionList = 0; + + colr->delta_set_idx_map.mapCount = 0; + colr->delta_set_idx_map.outerIndex = NULL; + colr->delta_set_idx_map.innerIndex = NULL; + + if ( face->variation_support & TT_FACE_FLAG_VAR_FVAR ) + { + FT_ULong var_idx_map_offset, var_store_offset; + + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm; + + + var_idx_map_offset = FT_NEXT_ULONG( p ); + + if ( var_idx_map_offset >= table_size ) + goto InvalidTable; + + var_store_offset = FT_NEXT_ULONG( p ); + if ( var_store_offset >= table_size ) + goto InvalidTable; + + if ( var_store_offset ) + { + /* If variation info has not been initialized yet, try doing so, */ + /* otherwise loading the variation store will fail as it */ + /* requires access to `blend` for checking the number of axes. */ + if ( !face->blend ) + if ( mm->get_mm_var( FT_FACE( face ), NULL ) ) + goto InvalidTable; + + /* Try loading `VarIdxMap` and `VarStore`. */ + error = mm->load_item_var_store( + FT_FACE( face ), + colr_offset_in_stream + var_store_offset, + &colr->var_store ); + if ( error != FT_Err_Ok ) + goto InvalidTable; + } + + if ( colr->var_store.axisCount && var_idx_map_offset ) + { + error = mm->load_delta_set_idx_map( + FT_FACE( face ), + colr_offset_in_stream + var_idx_map_offset, + &colr->delta_set_idx_map, + &colr->var_store, + table_size ); + if ( error != FT_Err_Ok ) + goto InvalidTable; + } + } +#endif /* TT_CONFIG_OPTION_GX_VAR_SUPPORT */ + } + + colr->base_glyphs = (FT_Byte*)( table + base_glyph_offset ); + colr->layers = (FT_Byte*)( table + layer_offset ); + colr->table = table; + colr->table_size = table_size; + + face->colr = colr; + + return FT_Err_Ok; + + InvalidTable: +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + { + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm; + + + mm->done_delta_set_idx_map( FT_FACE( face ), + &colr->delta_set_idx_map ); + mm->done_item_var_store( FT_FACE( face ), + &colr->var_store ); + } +#endif + + error = FT_THROW( Invalid_Table ); + + NoColr: + FT_FRAME_RELEASE( table ); + FT_FREE( colr ); + + return error; + } + + + FT_LOCAL_DEF( void ) + tt_face_free_colr( TT_Face face ) + { + FT_Stream stream = face->root.stream; + FT_Memory memory = face->root.memory; + + Colr* colr = (Colr*)face->colr; + + + if ( colr ) + { +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + { + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm; + + + mm->done_delta_set_idx_map( FT_FACE( face ), + &colr->delta_set_idx_map ); + mm->done_item_var_store( FT_FACE( face ), + &colr->var_store ); + } +#endif + FT_FRAME_RELEASE( colr->table ); + FT_FREE( colr ); + } + } + + + static FT_Bool + find_base_glyph_record( FT_Byte* base_glyph_begin, + FT_UInt num_base_glyph, + FT_UInt glyph_id, + BaseGlyphRecord* record ) + { + FT_UInt min = 0; + FT_UInt max = num_base_glyph; + + + while ( min < max ) + { + FT_UInt mid = min + ( max - min ) / 2; + FT_Byte* p = base_glyph_begin + mid * BASE_GLYPH_SIZE; + + FT_UShort gid = FT_NEXT_USHORT( p ); + + + if ( gid < glyph_id ) + min = mid + 1; + else if (gid > glyph_id ) + max = mid; + else + { + record->gid = gid; + record->first_layer_index = FT_NEXT_USHORT( p ); + record->num_layers = FT_NEXT_USHORT( p ); + + return 1; + } + } + + return 0; + } + + + FT_LOCAL_DEF( FT_Bool ) + tt_face_get_colr_layer( TT_Face face, + FT_UInt base_glyph, + FT_UInt *aglyph_index, + FT_UInt *acolor_index, + FT_LayerIterator* iterator ) + { + Colr* colr = (Colr*)face->colr; + BaseGlyphRecord glyph_record; + + + if ( !colr ) + return 0; + + if ( !iterator->p ) + { + FT_ULong offset; + + + /* first call to function */ + iterator->layer = 0; + + if ( !find_base_glyph_record( colr->base_glyphs, + colr->num_base_glyphs, + base_glyph, + &glyph_record ) ) + return 0; + + if ( glyph_record.num_layers ) + iterator->num_layers = glyph_record.num_layers; + else + return 0; + + offset = LAYER_SIZE * glyph_record.first_layer_index; + if ( offset + LAYER_SIZE * glyph_record.num_layers > colr->table_size ) + return 0; + + iterator->p = colr->layers + offset; + } + + if ( iterator->layer >= iterator->num_layers || + iterator->p < colr->layers || + iterator->p >= ( (FT_Byte*)colr->table + colr->table_size ) ) + return 0; + + *aglyph_index = FT_NEXT_USHORT( iterator->p ); + *acolor_index = FT_NEXT_USHORT( iterator->p ); + + if ( *aglyph_index >= (FT_UInt)( FT_FACE( face )->num_glyphs ) || + ( *acolor_index != 0xFFFF && + *acolor_index >= face->palette_data.num_palette_entries ) ) + return 0; + + iterator->layer++; + + return 1; + } + + + static FT_Bool + read_color_line( Colr* colr, + FT_Byte* color_line_p, + FT_ColorLine* colorline, + FT_Bool read_variable ) + { + FT_Byte* p = color_line_p; + FT_PaintExtend paint_extend; + + + ENSURE_READ_BYTES( 3 ); + + paint_extend = (FT_PaintExtend)FT_NEXT_BYTE( p ); + if ( paint_extend > FT_COLR_PAINT_EXTEND_REFLECT ) + return 0; + + colorline->extend = paint_extend; + + colorline->color_stop_iterator.num_color_stops = FT_NEXT_USHORT( p ); + colorline->color_stop_iterator.p = p; + colorline->color_stop_iterator.current_color_stop = 0; + colorline->color_stop_iterator.read_variable = read_variable; + + return 1; + } + + + /* + * Read a paint offset for `FT_Paint*` objects that have them and check + * whether it is within reasonable limits within the font and the COLR + * table. + * + * Return 1 on success, 0 on failure. + */ + static FT_Bool + get_child_table_pointer ( Colr* colr, + FT_Byte* paint_base, + FT_Byte** p, + FT_Byte** child_table_pointer ) + { + FT_UInt32 paint_offset; + FT_Byte* child_table_p; + + + if ( !child_table_pointer ) + return 0; + + if ( *p < colr->paints_start_v1 || + *p > (FT_Byte*)colr->table + colr->table_size - 1 - 3 ) + return 0; + + paint_offset = FT_NEXT_UOFF3( *p ); + if ( !paint_offset ) + return 0; + + child_table_p = (FT_Byte*)( paint_base + paint_offset ); + + if ( child_table_p < colr->paints_start_v1 || + child_table_p >= ( (FT_Byte*)colr->table + colr->table_size ) ) + return 0; + + *child_table_pointer = child_table_p; + return 1; + } + + +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + + static FT_Bool + get_deltas_for_var_index_base ( TT_Face face, + Colr* colr, + FT_ULong var_index_base, + FT_UInt num_deltas, + FT_ItemVarDelta* deltas ) + { + FT_UInt outer_index = 0; + FT_UInt inner_index = 0; + FT_ULong loop_var_index = var_index_base; + + FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm; + + FT_UInt i = 0; + + + if ( var_index_base == 0xFFFFFFFF ) + { + for ( i = 0; i < num_deltas; ++i ) + deltas[i] = 0; + return 1; + } + + for ( i = 0; i < num_deltas; ++i ) + { + loop_var_index = var_index_base + i; + + if ( colr->delta_set_idx_map.innerIndex ) + { + if ( loop_var_index >= colr->delta_set_idx_map.mapCount ) + loop_var_index = colr->delta_set_idx_map.mapCount - 1; + + outer_index = colr->delta_set_idx_map.outerIndex[loop_var_index]; + inner_index = colr->delta_set_idx_map.innerIndex[loop_var_index]; + } + else + { + outer_index = 0; + inner_index = loop_var_index; + } + + deltas[i] = mm->get_item_delta( FT_FACE( face ), &colr->var_store, + outer_index, inner_index ); + } + + return 1; + } + +#endif /* TT_CONFIG_OPTION_GX_VAR_SUPPORT */ + + + static FT_Bool + read_paint( TT_Face face, + Colr* colr, + FT_Byte* p, + FT_COLR_Paint* apaint ) + { + FT_Byte* paint_base = p; + FT_Byte* child_table_p = NULL; + FT_Bool do_read_var = FALSE; + +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + FT_ULong var_index_base = 0; + /* Longest varIndexBase offset is 5 in the spec. */ + FT_ItemVarDelta item_deltas[6] = { 0, 0, 0, 0, 0, 0 }; +#else + FT_UNUSED( face ); +#endif + + + if ( !p || !colr || !colr->table ) + return 0; + + /* The last byte of the 'COLR' table is at 'size-1'; subtract 1 of */ + /* that to account for the expected format byte we are going to read. */ + if ( p < colr->paints_start_v1 || + p > (FT_Byte*)colr->table + colr->table_size - 2 ) + return 0; + + apaint->format = (FT_PaintFormat)FT_NEXT_BYTE( p ); + + if ( apaint->format >= FT_COLR_PAINT_FORMAT_MAX ) + return 0; + + if ( apaint->format == FT_COLR_PAINTFORMAT_COLR_LAYERS ) + { + /* Initialize layer iterator/ */ + FT_Byte num_layers; + FT_UInt32 first_layer_index; + + + num_layers = FT_NEXT_BYTE( p ); + if ( num_layers > colr->num_layers_v1 ) + return 0; + + first_layer_index = FT_NEXT_ULONG( p ); + if ( first_layer_index + num_layers > colr->num_layers_v1 ) + return 0; + + apaint->u.colr_layers.layer_iterator.num_layers = num_layers; + apaint->u.colr_layers.layer_iterator.layer = 0; + /* TODO: Check whether pointer is outside colr? */ + apaint->u.colr_layers.layer_iterator.p = + colr->layers_v1 + + LAYER_V1_LIST_NUM_LAYERS_SIZE + + LAYER_V1_LIST_PAINT_OFFSET_SIZE * first_layer_index; + + return 1; + } + + else if ( apaint->format == FT_COLR_PAINTFORMAT_SOLID || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SOLID ) + { + ENSURE_READ_BYTES( 4 ); + apaint->u.solid.color.palette_index = FT_NEXT_USHORT( p ); + apaint->u.solid.color.alpha = FT_NEXT_SHORT( p ); + +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + if ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SOLID ) + { + ENSURE_READ_BYTES( 4 ); + var_index_base = FT_NEXT_ULONG( p ); + + if ( !get_deltas_for_var_index_base( face, colr, var_index_base, 1, + item_deltas ) ) + return 0; + + apaint->u.solid.color.alpha += (FT_F2Dot14)item_deltas[0]; + } +#endif + + apaint->format = FT_COLR_PAINTFORMAT_SOLID; + + return 1; + } + + else if ( apaint->format == FT_COLR_PAINTFORMAT_COLR_GLYPH ) + { + ENSURE_READ_BYTES(2); + apaint->u.colr_glyph.glyphID = FT_NEXT_USHORT( p ); + + return 1; + } + + /* + * Grouped below here are all paint formats that have an offset to a + * child paint table as the first entry (for example, a color line or a + * child paint table). Retrieve that and determine whether that paint + * offset is valid first. + */ + + if ( !get_child_table_pointer( colr, paint_base, &p, &child_table_p ) ) + return 0; + + if ( apaint->format == FT_COLR_PAINTFORMAT_LINEAR_GRADIENT || + ( do_read_var = + ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_LINEAR_GRADIENT ) ) ) + { + if ( !read_color_line( colr, + child_table_p, + &apaint->u.linear_gradient.colorline, + do_read_var ) ) + return 0; + + /* + * In order to support variations expose these as FT_Fixed 16.16 + * values so that we can support fractional values after + * interpolation. + */ + ENSURE_READ_BYTES( 12 ); + apaint->u.linear_gradient.p0.x = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + apaint->u.linear_gradient.p0.y = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + apaint->u.linear_gradient.p1.x = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + apaint->u.linear_gradient.p1.y = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + apaint->u.linear_gradient.p2.x = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + apaint->u.linear_gradient.p2.y = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + if ( do_read_var ) + { + ENSURE_READ_BYTES( 4 ); + var_index_base = FT_NEXT_ULONG ( p ); + + if ( !get_deltas_for_var_index_base( face, colr, var_index_base, 6, + item_deltas ) ) + return 0; + + apaint->u.linear_gradient.p0.x += INT_TO_FIXED( item_deltas[0] ); + apaint->u.linear_gradient.p0.y += INT_TO_FIXED( item_deltas[1] ); + apaint->u.linear_gradient.p1.x += INT_TO_FIXED( item_deltas[2] ); + apaint->u.linear_gradient.p1.y += INT_TO_FIXED( item_deltas[3] ); + apaint->u.linear_gradient.p2.x += INT_TO_FIXED( item_deltas[4] ); + apaint->u.linear_gradient.p2.y += INT_TO_FIXED( item_deltas[5] ); + } +#endif + + apaint->format = FT_COLR_PAINTFORMAT_LINEAR_GRADIENT; + + return 1; + } + + else if ( apaint->format == FT_COLR_PAINTFORMAT_RADIAL_GRADIENT || + ( do_read_var = + ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_RADIAL_GRADIENT ) ) ) + { + FT_Pos tmp; + + + if ( !read_color_line( colr, + child_table_p, + &apaint->u.radial_gradient.colorline, + do_read_var ) ) + return 0; + + + /* In the OpenType specification, `r0` and `r1` are defined as */ + /* `UFWORD`. Since FreeType doesn't have a corresponding 16.16 */ + /* format we convert to `FWORD` and replace negative values with */ + /* (32bit) `FT_INT_MAX`. */ + + ENSURE_READ_BYTES( 12 ); + + apaint->u.radial_gradient.c0.x = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + apaint->u.radial_gradient.c0.y = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + + tmp = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + apaint->u.radial_gradient.r0 = tmp < 0 ? FT_INT_MAX : tmp; + + apaint->u.radial_gradient.c1.x = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + apaint->u.radial_gradient.c1.y = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + + tmp = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + apaint->u.radial_gradient.r1 = tmp < 0 ? FT_INT_MAX : tmp; + +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + if ( do_read_var ) + { + ENSURE_READ_BYTES( 4 ); + var_index_base = FT_NEXT_ULONG ( p ); + + if ( !get_deltas_for_var_index_base( face, colr, var_index_base, 6, + item_deltas ) ) + return 0; + + apaint->u.radial_gradient.c0.x += INT_TO_FIXED( item_deltas[0] ); + apaint->u.radial_gradient.c0.y += INT_TO_FIXED( item_deltas[1] ); + + // TODO: Anything to be done about UFWORD deltas here? + apaint->u.radial_gradient.r0 += INT_TO_FIXED( item_deltas[2] ); + + apaint->u.radial_gradient.c1.x += INT_TO_FIXED( item_deltas[3] ); + apaint->u.radial_gradient.c1.y += INT_TO_FIXED( item_deltas[4] ); + + apaint->u.radial_gradient.r1 += INT_TO_FIXED( item_deltas[5] ); + } +#endif + + apaint->format = FT_COLR_PAINTFORMAT_RADIAL_GRADIENT; + + return 1; + } + + else if ( apaint->format == FT_COLR_PAINTFORMAT_SWEEP_GRADIENT || + ( do_read_var = + ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SWEEP_GRADIENT ) ) ) + { + if ( !read_color_line( colr, + child_table_p, + &apaint->u.sweep_gradient.colorline, + do_read_var) ) + return 0; + + ENSURE_READ_BYTES( 8 ); + + apaint->u.sweep_gradient.center.x = + INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + apaint->u.sweep_gradient.center.y = + INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + + apaint->u.sweep_gradient.start_angle = + F2DOT14_TO_FIXED( FT_NEXT_SHORT( p ) ); + apaint->u.sweep_gradient.end_angle = + F2DOT14_TO_FIXED( FT_NEXT_SHORT( p ) ); + +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + if ( do_read_var ) + { + ENSURE_READ_BYTES( 4 ); + var_index_base = FT_NEXT_ULONG ( p ); + + if ( !get_deltas_for_var_index_base( face, colr, var_index_base, 4, + item_deltas ) ) + return 0; + + // TODO: Handle overflow? + apaint->u.sweep_gradient.center.x += INT_TO_FIXED( item_deltas[0] ); + apaint->u.sweep_gradient.center.y += INT_TO_FIXED( item_deltas[1] ); + + apaint->u.sweep_gradient.start_angle += + F2DOT14_TO_FIXED( item_deltas[2] ); + apaint->u.sweep_gradient.end_angle += + F2DOT14_TO_FIXED( item_deltas[3] ); + } +#endif + apaint->format = FT_COLR_PAINTFORMAT_SWEEP_GRADIENT; + + return 1; + } + + if ( apaint->format == FT_COLR_PAINTFORMAT_GLYPH ) + { + ENSURE_READ_BYTES( 2 ); + apaint->u.glyph.paint.p = child_table_p; + apaint->u.glyph.paint.insert_root_transform = 0; + apaint->u.glyph.glyphID = FT_NEXT_USHORT( p ); + + return 1; + } + + else if ( apaint->format == FT_COLR_PAINTFORMAT_TRANSFORM || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_TRANSFORM ) + { + apaint->u.transform.paint.p = child_table_p; + apaint->u.transform.paint.insert_root_transform = 0; + + if ( !get_child_table_pointer( colr, paint_base, &p, &child_table_p ) ) + return 0; + + p = child_table_p; + + /* + * The following matrix coefficients are encoded as + * OpenType 16.16 fixed-point values. + */ + ENSURE_READ_BYTES( 24 ); + apaint->u.transform.affine.xx = FT_NEXT_LONG( p ); + apaint->u.transform.affine.yx = FT_NEXT_LONG( p ); + apaint->u.transform.affine.xy = FT_NEXT_LONG( p ); + apaint->u.transform.affine.yy = FT_NEXT_LONG( p ); + apaint->u.transform.affine.dx = FT_NEXT_LONG( p ); + apaint->u.transform.affine.dy = FT_NEXT_LONG( p ); + +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + if ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_TRANSFORM ) + { + ENSURE_READ_BYTES( 4 ); + var_index_base = FT_NEXT_ULONG( p ); + + if ( !get_deltas_for_var_index_base( face, colr, var_index_base, 6, + item_deltas ) ) + return 0; + + apaint->u.transform.affine.xx += (FT_Fixed)item_deltas[0]; + apaint->u.transform.affine.yx += (FT_Fixed)item_deltas[1]; + apaint->u.transform.affine.xy += (FT_Fixed)item_deltas[2]; + apaint->u.transform.affine.yy += (FT_Fixed)item_deltas[3]; + apaint->u.transform.affine.dx += (FT_Fixed)item_deltas[4]; + apaint->u.transform.affine.dy += (FT_Fixed)item_deltas[5]; + } +#endif + + apaint->format = FT_COLR_PAINTFORMAT_TRANSFORM; + + return 1; + } + + else if ( apaint->format == FT_COLR_PAINTFORMAT_TRANSLATE || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_TRANSLATE ) + { + apaint->u.translate.paint.p = child_table_p; + apaint->u.translate.paint.insert_root_transform = 0; + + ENSURE_READ_BYTES( 4 ); + apaint->u.translate.dx = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + apaint->u.translate.dy = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + if ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_TRANSLATE ) + { + ENSURE_READ_BYTES( 4 ); + var_index_base = FT_NEXT_ULONG( p ); + + if ( !get_deltas_for_var_index_base( face, colr, var_index_base, 2, + item_deltas ) ) + return 0; + + apaint->u.translate.dx += INT_TO_FIXED( item_deltas[0] ); + apaint->u.translate.dy += INT_TO_FIXED( item_deltas[1] ); + } +#endif + + apaint->format = FT_COLR_PAINTFORMAT_TRANSLATE; + + return 1; + } + + else if ( apaint->format >= FT_COLR_PAINTFORMAT_SCALE && + (FT_PaintFormat_Internal)apaint->format <= + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SCALE_UNIFORM_CENTER ) + { + apaint->u.scale.paint.p = child_table_p; + apaint->u.scale.paint.insert_root_transform = 0; + + /* All scale paints get at least one scale value. */ + ENSURE_READ_BYTES( 2 ); + apaint->u.scale.scale_x = F2DOT14_TO_FIXED( FT_NEXT_SHORT( p ) ); + + /* Non-uniform ones read an extra y value. */ + if ( apaint->format == FT_COLR_PAINTFORMAT_SCALE || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SCALE || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_SCALE_CENTER || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SCALE_CENTER ) + { + ENSURE_READ_BYTES( 2 ); + apaint->u.scale.scale_y = F2DOT14_TO_FIXED( FT_NEXT_SHORT( p ) ); + } + else + apaint->u.scale.scale_y = apaint->u.scale.scale_x; + + /* Scale paints that have a center read center coordinates, */ + /* otherwise the center is (0,0). */ + if ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_SCALE_CENTER || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SCALE_CENTER || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_SCALE_UNIFORM_CENTER || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SCALE_UNIFORM_CENTER ) + { + ENSURE_READ_BYTES( 4 ); + apaint->u.scale.center_x = INT_TO_FIXED( FT_NEXT_SHORT ( p ) ); + apaint->u.scale.center_y = INT_TO_FIXED( FT_NEXT_SHORT ( p ) ); + } + else + { + apaint->u.scale.center_x = 0; + apaint->u.scale.center_y = 0; + } + + /* Base values set, now handle variations. */ + +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + if ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SCALE || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SCALE_CENTER || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SCALE_UNIFORM || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SCALE_UNIFORM_CENTER ) + { + ENSURE_READ_BYTES( 4 ); + var_index_base = FT_NEXT_ULONG( p ); + + if ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SCALE ) + { + if ( !get_deltas_for_var_index_base( face, colr, var_index_base, 2, + item_deltas ) ) + return 0; + + apaint->u.scale.scale_x += F2DOT14_TO_FIXED( item_deltas[0] ); + apaint->u.scale.scale_y += F2DOT14_TO_FIXED( item_deltas[1] ); + } + + if ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SCALE_CENTER ) + { + if ( !get_deltas_for_var_index_base( face, colr, var_index_base, 4, + item_deltas ) ) + return 0; + + apaint->u.scale.scale_x += F2DOT14_TO_FIXED( item_deltas[0] ); + apaint->u.scale.scale_y += F2DOT14_TO_FIXED( item_deltas[1] ); + apaint->u.scale.center_x += INT_TO_FIXED( item_deltas[2] ); + apaint->u.scale.center_y += INT_TO_FIXED( item_deltas[3] ); + } + + if ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SCALE_UNIFORM ) + { + if ( !get_deltas_for_var_index_base( face, colr, var_index_base, 1, + item_deltas ) ) + return 0; + + apaint->u.scale.scale_x += F2DOT14_TO_FIXED( item_deltas[0] ); + apaint->u.scale.scale_y += F2DOT14_TO_FIXED( item_deltas[0] ); + } + + if ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SCALE_UNIFORM_CENTER ) + { + if ( !get_deltas_for_var_index_base( face, colr, var_index_base, 3, + item_deltas ) ) + return 0; + + apaint->u.scale.scale_x += F2DOT14_TO_FIXED( item_deltas[0] ); + apaint->u.scale.scale_y += F2DOT14_TO_FIXED( item_deltas[0] ); + apaint->u.scale.center_x += INT_TO_FIXED( item_deltas[1] ); + apaint->u.scale.center_y += INT_TO_FIXED( item_deltas[2] ); + } + } +#endif + + /* FT 'COLR' v1 API output format always returns fully defined */ + /* structs; we thus set the format to the public API value. */ + apaint->format = FT_COLR_PAINTFORMAT_SCALE; + + return 1; + } + + else if ( apaint->format == FT_COLR_PAINTFORMAT_ROTATE || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_ROTATE_CENTER || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_ROTATE || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_ROTATE_CENTER ) + { + apaint->u.rotate.paint.p = child_table_p; + apaint->u.rotate.paint.insert_root_transform = 0; + + ENSURE_READ_BYTES( 2 ); + apaint->u.rotate.angle = F2DOT14_TO_FIXED( FT_NEXT_SHORT( p ) ); + + if ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_ROTATE_CENTER || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_ROTATE_CENTER ) + { + ENSURE_READ_BYTES( 4 ); + apaint->u.rotate.center_x = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + apaint->u.rotate.center_y = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + } + else + { + apaint->u.rotate.center_x = 0; + apaint->u.rotate.center_y = 0; + } + +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + if ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_ROTATE || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_ROTATE_CENTER ) + { + FT_UInt num_deltas = 0; + + + ENSURE_READ_BYTES( 4 ); + var_index_base = FT_NEXT_ULONG( p ); + + if ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_ROTATE_CENTER ) + num_deltas = 3; + if ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_ROTATE ) + num_deltas = 1; + + if ( num_deltas > 0 ) + { + if ( !get_deltas_for_var_index_base( face, colr, var_index_base, + num_deltas, item_deltas ) ) + return 0; + + apaint->u.rotate.angle += F2DOT14_TO_FIXED( item_deltas[0] ); + + if ( num_deltas == 3 ) + { + apaint->u.rotate.center_x += INT_TO_FIXED( item_deltas[1] ); + apaint->u.rotate.center_y += INT_TO_FIXED( item_deltas[2] ); + } + } + } +#endif + + apaint->format = FT_COLR_PAINTFORMAT_ROTATE; + + + return 1; + } + + else if ( apaint->format == FT_COLR_PAINTFORMAT_SKEW || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SKEW || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_SKEW_CENTER || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SKEW_CENTER ) + { + apaint->u.skew.paint.p = child_table_p; + apaint->u.skew.paint.insert_root_transform = 0; + + ENSURE_READ_BYTES( 4 ); + apaint->u.skew.x_skew_angle = F2DOT14_TO_FIXED( FT_NEXT_SHORT( p ) ); + apaint->u.skew.y_skew_angle = F2DOT14_TO_FIXED( FT_NEXT_SHORT( p ) ); + + if ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_SKEW_CENTER || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SKEW_CENTER ) + { + ENSURE_READ_BYTES( 4 ); + apaint->u.skew.center_x = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + apaint->u.skew.center_y = INT_TO_FIXED( FT_NEXT_SHORT( p ) ); + } + else + { + apaint->u.skew.center_x = 0; + apaint->u.skew.center_y = 0; + } + + +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + if ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SKEW || + (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SKEW_CENTER ) + { + ENSURE_READ_BYTES( 4 ); + var_index_base = FT_NEXT_ULONG( p ); + + if ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SKEW ) + { + if ( !get_deltas_for_var_index_base( face, colr, var_index_base, 2, + item_deltas ) ) + return 0; + + apaint->u.skew.x_skew_angle += F2DOT14_TO_FIXED( item_deltas[0] ); + apaint->u.skew.y_skew_angle += F2DOT14_TO_FIXED( item_deltas[1] ); + } + + if ( (FT_PaintFormat_Internal)apaint->format == + FT_COLR_PAINTFORMAT_INTERNAL_VAR_SKEW_CENTER ) + { + if ( !get_deltas_for_var_index_base( face, colr, var_index_base, 4, + item_deltas ) ) + return 0; + + apaint->u.skew.x_skew_angle += F2DOT14_TO_FIXED( item_deltas[0] ); + apaint->u.skew.y_skew_angle += F2DOT14_TO_FIXED( item_deltas[1] ); + apaint->u.skew.center_x += INT_TO_FIXED( item_deltas[2] ); + apaint->u.skew.center_y += INT_TO_FIXED( item_deltas[3] ); + } + } +#endif + + apaint->format = FT_COLR_PAINTFORMAT_SKEW; + + return 1; + } + + else if ( apaint->format == FT_COLR_PAINTFORMAT_COMPOSITE ) + { + FT_UInt composite_mode; + + + apaint->u.composite.source_paint.p = child_table_p; + apaint->u.composite.source_paint.insert_root_transform = 0; + + ENSURE_READ_BYTES( 1 ); + composite_mode = FT_NEXT_BYTE( p ); + if ( composite_mode >= FT_COLR_COMPOSITE_MAX ) + return 0; + + apaint->u.composite.composite_mode = (FT_Composite_Mode)composite_mode; + + if ( !get_child_table_pointer( colr, paint_base, &p, &child_table_p ) ) + return 0; + + apaint->u.composite.backdrop_paint.p = + child_table_p; + apaint->u.composite.backdrop_paint.insert_root_transform = + 0; + + return 1; + } + + return 0; + } + + + static FT_Bool + find_base_glyph_v1_record( FT_Byte * base_glyph_begin, + FT_UInt num_base_glyph, + FT_UInt glyph_id, + BaseGlyphV1Record *record ) + { + FT_UInt min = 0; + FT_UInt max = num_base_glyph; + + + while ( min < max ) + { + FT_UInt mid = min + ( max - min ) / 2; + + /* + * `base_glyph_begin` is the beginning of `BaseGlyphV1List`; + * skip `numBaseGlyphV1Records` by adding 4 to start binary search + * in the array of `BaseGlyphV1Record`. + */ + FT_Byte *p = base_glyph_begin + 4 + mid * BASE_GLYPH_PAINT_RECORD_SIZE; + + FT_UShort gid = FT_NEXT_USHORT( p ); + + + if ( gid < glyph_id ) + min = mid + 1; + else if (gid > glyph_id ) + max = mid; + else + { + record->gid = gid; + record->paint_offset = FT_NEXT_ULONG ( p ); + return 1; + } + } + + return 0; + } + + + FT_LOCAL_DEF( FT_Bool ) + tt_face_get_colr_glyph_paint( TT_Face face, + FT_UInt base_glyph, + FT_Color_Root_Transform root_transform, + FT_OpaquePaint* opaque_paint ) + { + Colr* colr = (Colr*)face->colr; + BaseGlyphV1Record base_glyph_v1_record; + FT_Byte* p; + + if ( !colr || !colr->table ) + return 0; + + if ( colr->version < 1 || !colr->num_base_glyphs_v1 || + !colr->base_glyphs_v1 ) + return 0; + + if ( opaque_paint->p ) + return 0; + + if ( !find_base_glyph_v1_record( colr->base_glyphs_v1, + colr->num_base_glyphs_v1, + base_glyph, + &base_glyph_v1_record ) ) + return 0; + + if ( !base_glyph_v1_record.paint_offset || + base_glyph_v1_record.paint_offset > colr->table_size ) + return 0; + + p = (FT_Byte*)( colr->base_glyphs_v1 + + base_glyph_v1_record.paint_offset ); + if ( p >= ( (FT_Byte*)colr->table + colr->table_size ) ) + return 0; + + opaque_paint->p = p; + + if ( root_transform == FT_COLOR_INCLUDE_ROOT_TRANSFORM ) + opaque_paint->insert_root_transform = 1; + else + opaque_paint->insert_root_transform = 0; + + return 1; + } + + + FT_LOCAL_DEF( FT_Bool ) + tt_face_get_color_glyph_clipbox( TT_Face face, + FT_UInt base_glyph, + FT_ClipBox* clip_box ) + { + Colr* colr; + + FT_Byte *p, *p1, *clip_base, *limit; + + FT_Byte clip_list_format; + FT_ULong num_clip_boxes, i; + FT_UShort gid_start, gid_end; + FT_UInt32 clip_box_offset; + FT_Byte format; + + const FT_Byte num_corners = 4; + FT_Vector corners[4]; + FT_Byte j; + FT_BBox font_clip_box; + + + colr = (Colr*)face->colr; + if ( !colr ) + return 0; + + if ( !colr->clip_list ) + return 0; + + p = colr->clip_list; + + /* Limit points to the first byte after the end of the color table. */ + /* Thus, in subsequent limit checks below we need to check whether the */ + /* read pointer is strictly greater than a position offset by certain */ + /* field sizes to the left of that position. */ + limit = (FT_Byte*)colr->table + colr->table_size; + + /* Check whether we can extract one `uint8` and one `uint32`. */ + if ( p > limit - ( 1 + 4 ) ) + return 0; + + clip_base = p; + clip_list_format = FT_NEXT_BYTE ( p ); + + /* Format byte used here to be able to upgrade ClipList for >16bit */ + /* glyph ids; for now we can expect it to be 1. */ + if ( !( clip_list_format == 1 ) ) + return 0; + + num_clip_boxes = FT_NEXT_ULONG( p ); + + /* Check whether we can extract two `uint16` and one `Offset24`, */ + /* `num_clip_boxes` times. */ + if ( colr->table_size / ( 2 + 2 + 3 ) < num_clip_boxes || + p > limit - ( 2 + 2 + 3 ) * num_clip_boxes ) + return 0; + + for ( i = 0; i < num_clip_boxes; ++i ) + { + gid_start = FT_NEXT_USHORT( p ); + gid_end = FT_NEXT_USHORT( p ); + clip_box_offset = FT_NEXT_UOFF3( p ); + + if ( base_glyph >= gid_start && base_glyph <= gid_end ) + { + p1 = (FT_Byte*)( clip_base + clip_box_offset ); + + /* Check whether we can extract one `uint8`. */ + if ( p1 > limit - 1 ) + return 0; + + format = FT_NEXT_BYTE( p1 ); + + if ( format > 2 ) + return 0; + + /* Check whether we can extract four `FWORD`. */ + if ( p1 > limit - ( 2 + 2 + 2 + 2 ) ) + return 0; + + /* `face->root.size->metrics.x_scale` and `y_scale` are factors */ + /* that scale a font unit value in integers to a 26.6 fixed value */ + /* according to the requested size, see for example */ + /* `ft_recompute_scaled_metrics`. */ + font_clip_box.xMin = FT_MulFix( FT_NEXT_SHORT( p1 ), + face->root.size->metrics.x_scale ); + font_clip_box.yMin = FT_MulFix( FT_NEXT_SHORT( p1 ), + face->root.size->metrics.y_scale ); + font_clip_box.xMax = FT_MulFix( FT_NEXT_SHORT( p1 ), + face->root.size->metrics.x_scale ); + font_clip_box.yMax = FT_MulFix( FT_NEXT_SHORT( p1 ), + face->root.size->metrics.y_scale ); + +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + if ( format == 2 ) + { + FT_ULong var_index_base = 0; + /* varIndexBase offset for clipbox is 3 at most. */ + FT_ItemVarDelta item_deltas[4] = { 0, 0, 0, 0 }; + + + /* Check whether we can extract a 32-bit varIndexBase now. */ + if ( p1 > limit - 4 ) + return 0; + + var_index_base = FT_NEXT_ULONG( p1 ); + + if ( !get_deltas_for_var_index_base( face, colr, var_index_base, 4, + item_deltas ) ) + return 0; + + font_clip_box.xMin += + FT_MulFix( item_deltas[0], face->root.size->metrics.x_scale ); + font_clip_box.yMin += + FT_MulFix( item_deltas[1], face->root.size->metrics.y_scale ); + font_clip_box.xMax += + FT_MulFix( item_deltas[2], face->root.size->metrics.x_scale ); + font_clip_box.yMax += + FT_MulFix( item_deltas[3], face->root.size->metrics.y_scale ); + } +#endif + + /* Make 4 corner points (xMin, yMin), (xMax, yMax) and transform */ + /* them. If we we would only transform two corner points and */ + /* span a rectangle based on those, the rectangle may become too */ + /* small to cover the glyph. */ + corners[0].x = font_clip_box.xMin; + corners[1].x = font_clip_box.xMin; + corners[2].x = font_clip_box.xMax; + corners[3].x = font_clip_box.xMax; + + corners[0].y = font_clip_box.yMin; + corners[1].y = font_clip_box.yMax; + corners[2].y = font_clip_box.yMax; + corners[3].y = font_clip_box.yMin; + + for ( j = 0; j < num_corners; ++j ) + { + if ( face->root.internal->transform_flags & 1 ) + FT_Vector_Transform( &corners[j], + &face->root.internal->transform_matrix ); + + if ( face->root.internal->transform_flags & 2 ) + { + corners[j].x += face->root.internal->transform_delta.x; + corners[j].y += face->root.internal->transform_delta.y; + } + } + + clip_box->bottom_left = corners[0]; + clip_box->top_left = corners[1]; + clip_box->top_right = corners[2]; + clip_box->bottom_right = corners[3]; + + return 1; + } + } + + return 0; + } + + + FT_LOCAL_DEF( FT_Bool ) + tt_face_get_paint_layers( TT_Face face, + FT_LayerIterator* iterator, + FT_OpaquePaint* opaque_paint ) + { + FT_Byte* p = NULL; + FT_Byte* p_first_layer = NULL; + FT_Byte* p_paint = NULL; + FT_UInt32 paint_offset; + + Colr* colr; + + + if ( iterator->layer == iterator->num_layers ) + return 0; + + colr = (Colr*)face->colr; + if ( !colr ) + return 0; + + /* + * We have an iterator pointing at a paint offset as part of the + * `paintOffset` array in `LayerV1List`. + */ + p = iterator->p; + + /* + * Do a cursor sanity check of the iterator. Counting backwards from + * where it stands, we need to end up at a position after the beginning + * of the `LayerV1List` table and not after the end of the + * `LayerV1List`. + */ + p_first_layer = p - + iterator->layer * LAYER_V1_LIST_PAINT_OFFSET_SIZE - + LAYER_V1_LIST_NUM_LAYERS_SIZE; + if ( p_first_layer < (FT_Byte*)colr->layers_v1 ) + return 0; + if ( p_first_layer >= (FT_Byte*)( + colr->layers_v1 + LAYER_V1_LIST_NUM_LAYERS_SIZE + + colr->num_layers_v1 * LAYER_V1_LIST_PAINT_OFFSET_SIZE ) ) + return 0; + + /* + * Before reading, ensure that `p` is within 'COLR' v1 and we can read a + * 4-byte ULONG. + */ + if ( p < colr->layers_v1 || + p > (FT_Byte*)colr->table + colr->table_size - 4 ) + return 0; + + paint_offset = + FT_NEXT_ULONG( p ); + opaque_paint->insert_root_transform = + 0; + + p_paint = (FT_Byte*)( colr->layers_v1 + paint_offset ); + + if ( p_paint < colr->paints_start_v1 || + p_paint >= ( (FT_Byte*)colr->table + colr->table_size ) ) + return 0; + + opaque_paint->p = p_paint; + + iterator->p = p; + + iterator->layer++; + + return 1; + } + + + FT_LOCAL_DEF( FT_Bool ) + tt_face_get_colorline_stops( TT_Face face, + FT_ColorStop* color_stop, + FT_ColorStopIterator *iterator ) + { + Colr* colr = (Colr*)face->colr; + + FT_Byte* p; + FT_ULong var_index_base; + FT_Byte* last_entry_p = NULL; + FT_UInt entry_size = COLOR_STOP_SIZE; + + + if ( !colr || !colr->table || !iterator ) + return 0; + + if ( iterator->current_color_stop >= iterator->num_color_stops ) + return 0; + + if ( iterator->read_variable ) + entry_size += VAR_IDX_BASE_SIZE; + + /* Calculate the start pointer for the last to-be-read (Var)ColorStop */ + /* and check whether we can read a full (Var)ColorStop at that */ + /* position by comparing it to the position that is the size of one */ + /* (Var)ColorStop before the end of the 'COLR' table. */ + last_entry_p = + iterator->p + ( iterator->num_color_stops - 1 - + iterator->current_color_stop ) * entry_size; + if ( iterator->p < colr->paints_start_v1 || + last_entry_p > (FT_Byte*)colr->table + + colr->table_size - entry_size ) + return 0; + + /* Iterator points at first `ColorStop` of `ColorLine`. */ + p = iterator->p; + + color_stop->stop_offset = F2DOT14_TO_FIXED( FT_NEXT_SHORT( p ) ); + + color_stop->color.palette_index = FT_NEXT_USHORT( p ); + + color_stop->color.alpha = FT_NEXT_SHORT( p ); + + if ( iterator->read_variable ) + { + /* Pointer p needs to be advanced independently of whether we intend */ + /* to take variable deltas into account or not. Otherwise iteration */ + /* would fail due to wrong offsets. */ + var_index_base = FT_NEXT_ULONG( p ); + +#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT + { + FT_Int item_deltas[2]; + + + if ( !get_deltas_for_var_index_base( face, colr, + var_index_base, + 2, + item_deltas ) ) + return 0; + + color_stop->stop_offset += F2DOT14_TO_FIXED( item_deltas[0] ); + color_stop->color.alpha += (FT_F2Dot14)item_deltas[1]; + } +#else + FT_UNUSED( var_index_base ); +#endif + } + + iterator->p = p; + iterator->current_color_stop++; + + return 1; + } + + + FT_LOCAL_DEF( FT_Bool ) + tt_face_get_paint( TT_Face face, + FT_OpaquePaint opaque_paint, + FT_COLR_Paint* paint ) + { + Colr* colr = (Colr*)face->colr; + FT_OpaquePaint next_paint; + FT_Matrix ft_root_scale; + + if ( !colr || !colr->base_glyphs_v1 || !colr->table ) + return 0; + + if ( opaque_paint.insert_root_transform ) + { + /* 'COLR' v1 glyph information is returned in unscaled coordinates, + * i.e., `FT_Size` is not applied or multiplied into the values. When + * client applications draw color glyphs, they can request to include + * a top-level transform, which includes the active `x_scale` and + * `y_scale` information for scaling the glyph, as well the additional + * transform and translate configured through `FT_Set_Transform`. + * This allows client applications to apply this top-level transform + * to the graphics context first and only once, then have gradient and + * contour scaling applied correctly when performing the additional + * drawing operations for subsequenct paints. Prepare this initial + * transform here. + */ + paint->format = FT_COLR_PAINTFORMAT_TRANSFORM; + + next_paint.p = opaque_paint.p; + next_paint.insert_root_transform = 0; + paint->u.transform.paint = next_paint; + + /* `x_scale` and `y_scale` are in 26.6 format, representing the scale + * factor to get from font units to requested size. However, expected + * return values are in 16.16, so we shift accordingly with rounding. + */ + ft_root_scale.xx = ( face->root.size->metrics.x_scale + 32 ) >> 6; + ft_root_scale.xy = 0; + ft_root_scale.yx = 0; + ft_root_scale.yy = ( face->root.size->metrics.y_scale + 32 ) >> 6; + + if ( face->root.internal->transform_flags & 1 ) + FT_Matrix_Multiply( &face->root.internal->transform_matrix, + &ft_root_scale ); + + paint->u.transform.affine.xx = ft_root_scale.xx; + paint->u.transform.affine.xy = ft_root_scale.xy; + paint->u.transform.affine.yx = ft_root_scale.yx; + paint->u.transform.affine.yy = ft_root_scale.yy; + + /* The translation is specified in 26.6 format and, according to the + * documentation of `FT_Set_Translate`, is performed on the character + * size given in the last call to `FT_Set_Char_Size`. The + * 'PaintTransform' paint table's `FT_Affine23` format expects + * values in 16.16 format, thus we need to shift by 10 bits. + */ + if ( face->root.internal->transform_flags & 2 ) + { + paint->u.transform.affine.dx = + face->root.internal->transform_delta.x * ( 1 << 10 ); + paint->u.transform.affine.dy = + face->root.internal->transform_delta.y * ( 1 << 10 ); + } + else + { + paint->u.transform.affine.dx = 0; + paint->u.transform.affine.dy = 0; + } + + return 1; + } + + return read_paint( face, colr, opaque_paint.p, paint ); + } + + + FT_LOCAL_DEF( FT_Error ) + tt_face_colr_blend_layer( TT_Face face, + FT_UInt color_index, + FT_GlyphSlot dstSlot, + FT_GlyphSlot srcSlot ) + { + FT_Error error; + + FT_UInt x, y; + FT_Byte b, g, r, alpha; + + FT_ULong size; + FT_Byte* src; + FT_Byte* dst; + + + if ( !dstSlot->bitmap.buffer ) + { + /* Initialize destination of color bitmap */ + /* with the size of first component. */ + dstSlot->bitmap_left = srcSlot->bitmap_left; + dstSlot->bitmap_top = srcSlot->bitmap_top; + + dstSlot->bitmap.width = srcSlot->bitmap.width; + dstSlot->bitmap.rows = srcSlot->bitmap.rows; + dstSlot->bitmap.pixel_mode = FT_PIXEL_MODE_BGRA; + dstSlot->bitmap.pitch = (int)dstSlot->bitmap.width * 4; + dstSlot->bitmap.num_grays = 256; + + size = dstSlot->bitmap.rows * (unsigned int)dstSlot->bitmap.pitch; + + error = ft_glyphslot_alloc_bitmap( dstSlot, size ); + if ( error ) + return error; + + FT_MEM_ZERO( dstSlot->bitmap.buffer, size ); + } + else + { + /* Resize destination if needed such that new component fits. */ + FT_Int x_min, x_max, y_min, y_max; + + + x_min = FT_MIN( dstSlot->bitmap_left, srcSlot->bitmap_left ); + x_max = FT_MAX( dstSlot->bitmap_left + (FT_Int)dstSlot->bitmap.width, + srcSlot->bitmap_left + (FT_Int)srcSlot->bitmap.width ); + + y_min = FT_MIN( dstSlot->bitmap_top - (FT_Int)dstSlot->bitmap.rows, + srcSlot->bitmap_top - (FT_Int)srcSlot->bitmap.rows ); + y_max = FT_MAX( dstSlot->bitmap_top, srcSlot->bitmap_top ); + + if ( x_min != dstSlot->bitmap_left || + x_max != dstSlot->bitmap_left + (FT_Int)dstSlot->bitmap.width || + y_min != dstSlot->bitmap_top - (FT_Int)dstSlot->bitmap.rows || + y_max != dstSlot->bitmap_top ) + { + FT_Memory memory = face->root.memory; + + FT_UInt width = (FT_UInt)( x_max - x_min ); + FT_UInt rows = (FT_UInt)( y_max - y_min ); + FT_UInt pitch = width * 4; + + FT_Byte* buf = NULL; + FT_Byte* p; + FT_Byte* q; + + + size = rows * pitch; + if ( FT_ALLOC( buf, size ) ) + return error; + + p = dstSlot->bitmap.buffer; + q = buf + + (int)pitch * ( y_max - dstSlot->bitmap_top ) + + 4 * ( dstSlot->bitmap_left - x_min ); + + for ( y = 0; y < dstSlot->bitmap.rows; y++ ) + { + FT_MEM_COPY( q, p, dstSlot->bitmap.width * 4 ); + + p += dstSlot->bitmap.pitch; + q += pitch; + } + + ft_glyphslot_set_bitmap( dstSlot, buf ); + + dstSlot->bitmap_top = y_max; + dstSlot->bitmap_left = x_min; + + dstSlot->bitmap.width = width; + dstSlot->bitmap.rows = rows; + dstSlot->bitmap.pitch = (int)pitch; + + dstSlot->internal->flags |= FT_GLYPH_OWN_BITMAP; + dstSlot->format = FT_GLYPH_FORMAT_BITMAP; + } + } + + if ( color_index == 0xFFFF ) + { + if ( face->have_foreground_color ) + { + b = face->foreground_color.blue; + g = face->foreground_color.green; + r = face->foreground_color.red; + alpha = face->foreground_color.alpha; + } + else + { + if ( face->palette_data.palette_flags && + ( face->palette_data.palette_flags[face->palette_index] & + FT_PALETTE_FOR_DARK_BACKGROUND ) ) + { + /* white opaque */ + b = 0xFF; + g = 0xFF; + r = 0xFF; + alpha = 0xFF; + } + else + { + /* black opaque */ + b = 0x00; + g = 0x00; + r = 0x00; + alpha = 0xFF; + } + } + } + else + { + b = face->palette[color_index].blue; + g = face->palette[color_index].green; + r = face->palette[color_index].red; + alpha = face->palette[color_index].alpha; + } + + /* XXX Convert if srcSlot.bitmap is not grey? */ + src = srcSlot->bitmap.buffer; + dst = dstSlot->bitmap.buffer + + dstSlot->bitmap.pitch * ( dstSlot->bitmap_top - srcSlot->bitmap_top ) + + 4 * ( srcSlot->bitmap_left - dstSlot->bitmap_left ); + + for ( y = 0; y < srcSlot->bitmap.rows; y++ ) + { + for ( x = 0; x < srcSlot->bitmap.width; x++ ) + { + int aa = src[x]; + int fa = alpha * aa / 255; + + int fb = b * fa / 255; + int fg = g * fa / 255; + int fr = r * fa / 255; + + int ba2 = 255 - fa; + + int bb = dst[4 * x + 0]; + int bg = dst[4 * x + 1]; + int br = dst[4 * x + 2]; + int ba = dst[4 * x + 3]; + + + dst[4 * x + 0] = (FT_Byte)( bb * ba2 / 255 + fb ); + dst[4 * x + 1] = (FT_Byte)( bg * ba2 / 255 + fg ); + dst[4 * x + 2] = (FT_Byte)( br * ba2 / 255 + fr ); + dst[4 * x + 3] = (FT_Byte)( ba * ba2 / 255 + fa ); + } + + src += srcSlot->bitmap.pitch; + dst += dstSlot->bitmap.pitch; + } + + return FT_Err_Ok; + } + +#else /* !TT_CONFIG_OPTION_COLOR_LAYERS */ + + /* ANSI C doesn't like empty source files */ + typedef int tt_colr_dummy_; + +#endif /* !TT_CONFIG_OPTION_COLOR_LAYERS */ + +/* EOF */ diff --git a/src/font/freetype-2.10.2/src/sfnt/ttcolr.h b/3rdparty/freetype-2.13.2/src/sfnt/ttcolr.h similarity index 56% rename from src/font/freetype-2.10.2/src/sfnt/ttcolr.h rename to 3rdparty/freetype-2.13.2/src/sfnt/ttcolr.h index 8da6b3aa1..20c85f035 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttcolr.h +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttcolr.h @@ -4,7 +4,7 @@ * * TrueType and OpenType colored glyph layer support (specification). * - * Copyright (C) 2018-2020 by + * Copyright (C) 2018-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * Originally written by Shao Yu Zhang . @@ -22,7 +22,6 @@ #define __TTCOLR_H__ -#include #include "ttload.h" @@ -43,6 +42,32 @@ FT_BEGIN_HEADER FT_UInt *acolor_index, FT_LayerIterator* iterator ); + FT_LOCAL( FT_Bool ) + tt_face_get_colr_glyph_paint( TT_Face face, + FT_UInt base_glyph, + FT_Color_Root_Transform root_transform, + FT_OpaquePaint* paint ); + + FT_LOCAL( FT_Bool ) + tt_face_get_color_glyph_clipbox( TT_Face face, + FT_UInt base_glyph, + FT_ClipBox* clip_box ); + + FT_LOCAL( FT_Bool ) + tt_face_get_paint_layers( TT_Face face, + FT_LayerIterator* iterator, + FT_OpaquePaint* paint ); + + FT_LOCAL( FT_Bool ) + tt_face_get_colorline_stops( TT_Face face, + FT_ColorStop* color_stop, + FT_ColorStopIterator* iterator ); + + FT_LOCAL( FT_Bool ) + tt_face_get_paint( TT_Face face, + FT_OpaquePaint opaque_paint, + FT_COLR_Paint* paint ); + FT_LOCAL( FT_Error ) tt_face_colr_blend_layer( TT_Face face, FT_UInt color_index, diff --git a/src/font/freetype-2.10.2/src/sfnt/ttcpal.c b/3rdparty/freetype-2.13.2/src/sfnt/ttcpal.c similarity index 93% rename from src/font/freetype-2.10.2/src/sfnt/ttcpal.c rename to 3rdparty/freetype-2.13.2/src/sfnt/ttcpal.c index 165423e30..46ae08596 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttcpal.c +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttcpal.c @@ -4,7 +4,7 @@ * * TrueType and OpenType color palette support (body). * - * Copyright (C) 2018-2020 by + * Copyright (C) 2018-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * Originally written by Shao Yu Zhang . @@ -27,11 +27,10 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_STREAM_H -#include FT_TRUETYPE_TAGS_H -#include FT_COLOR_H +#include +#include +#include +#include #ifdef TT_CONFIG_OPTION_COLOR_LAYERS @@ -40,8 +39,8 @@ /* NOTE: These are the table sizes calculated through the specs. */ -#define CPAL_V0_HEADER_BASE_SIZE 12 -#define COLOR_SIZE 4 +#define CPAL_V0_HEADER_BASE_SIZE 12U +#define COLOR_SIZE 4U /* all data from `CPAL' not covered in FT_Palette_Data */ @@ -140,7 +139,7 @@ 3U * 4 > table_size ) goto InvalidTable; - p += face->palette_data.num_palettes * 2; + p += face->palette_data.num_palettes * 2U; type_offset = FT_NEXT_ULONG( p ); label_offset = FT_NEXT_ULONG( p ); @@ -150,7 +149,7 @@ { if ( type_offset >= table_size ) goto InvalidTable; - if ( face->palette_data.num_palettes * 2 > + if ( face->palette_data.num_palettes * 2U > table_size - type_offset ) goto InvalidTable; @@ -171,7 +170,7 @@ { if ( label_offset >= table_size ) goto InvalidTable; - if ( face->palette_data.num_palettes * 2 > + if ( face->palette_data.num_palettes * 2U > table_size - label_offset ) goto InvalidTable; @@ -192,7 +191,7 @@ { if ( entry_label_offset >= table_size ) goto InvalidTable; - if ( face->palette_data.num_palette_entries * 2 > + if ( face->palette_data.num_palette_entries * 2U > table_size - entry_label_offset ) goto InvalidTable; @@ -304,7 +303,7 @@ #else /* !TT_CONFIG_OPTION_COLOR_LAYERS */ /* ANSI C doesn't like empty source files */ - typedef int _tt_cpal_dummy; + typedef int tt_cpal_dummy_; #endif /* !TT_CONFIG_OPTION_COLOR_LAYERS */ diff --git a/src/font/freetype-2.10.2/src/sfnt/ttcpal.h b/3rdparty/freetype-2.13.2/src/sfnt/ttcpal.h similarity index 95% rename from src/font/freetype-2.10.2/src/sfnt/ttcpal.h rename to 3rdparty/freetype-2.13.2/src/sfnt/ttcpal.h index f2e116ba2..8e9913f0c 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttcpal.h +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttcpal.h @@ -4,7 +4,7 @@ * * TrueType and OpenType color palette support (specification). * - * Copyright (C) 2018-2020 by + * Copyright (C) 2018-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * Originally written by Shao Yu Zhang . @@ -22,7 +22,6 @@ #define __TTCPAL_H__ -#include #include "ttload.h" diff --git a/src/font/freetype-2.10.2/src/sfnt/ttkern.c b/3rdparty/freetype-2.13.2/src/sfnt/ttkern.c similarity index 94% rename from src/font/freetype-2.10.2/src/sfnt/ttkern.c rename to 3rdparty/freetype-2.13.2/src/sfnt/ttkern.c index 1d34acbd1..a47d08bd6 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttkern.c +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttkern.c @@ -5,7 +5,7 @@ * Load the basic TrueType kerning table. This doesn't handle * kerning data within the GPOS table at the moment. * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -17,10 +17,9 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_STREAM_H -#include FT_TRUETYPE_TAGS_H +#include +#include +#include #include "ttkern.h" #include "sferrors.h" @@ -95,7 +94,7 @@ p_next = p; - p += 2; /* skip version */ + p += 2; /* skip version */ length = FT_NEXT_USHORT( p ); coverage = FT_NEXT_USHORT( p ); @@ -145,7 +144,7 @@ cur_pair = FT_NEXT_ULONG( p ); - if ( cur_pair <= old_pair ) + if ( cur_pair < old_pair ) break; p += 2; @@ -188,11 +187,18 @@ FT_UInt left_glyph, FT_UInt right_glyph ) { - FT_Int result = 0; - FT_UInt count, mask; - FT_Byte* p = face->kern_table; - FT_Byte* p_limit = p + face->kern_table_size; + FT_Int result = 0; + FT_UInt count, mask; + FT_Byte* p; + FT_Byte* p_limit; + + + if ( !face->kern_table ) + return result; + + p = face->kern_table; + p_limit = p + face->kern_table_size; p += 4; mask = 0x0001; diff --git a/src/font/freetype-2.10.2/src/sfnt/ttkern.h b/3rdparty/freetype-2.13.2/src/sfnt/ttkern.h similarity index 90% rename from src/font/freetype-2.10.2/src/sfnt/ttkern.h rename to 3rdparty/freetype-2.13.2/src/sfnt/ttkern.h index 6560a283a..960c7da49 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttkern.h +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttkern.h @@ -5,7 +5,7 @@ * Load the basic TrueType kerning table. This doesn't handle * kerning data within the GPOS table at the moment. * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -21,9 +21,8 @@ #define TTKERN_H_ -#include -#include FT_INTERNAL_STREAM_H -#include FT_INTERNAL_TRUETYPE_TYPES_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/src/sfnt/ttload.c b/3rdparty/freetype-2.13.2/src/sfnt/ttload.c similarity index 91% rename from src/font/freetype-2.10.2/src/sfnt/ttload.c rename to 3rdparty/freetype-2.13.2/src/sfnt/ttload.c index d4e4ee4f1..7b44e9cd2 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttload.c +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttload.c @@ -5,7 +5,7 @@ * Load the basic TrueType tables, i.e., tables that can be either in * TTF or OTF fonts (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -17,10 +17,9 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_STREAM_H -#include FT_TRUETYPE_TAGS_H +#include +#include +#include #include "ttload.h" #include "sferrors.h" @@ -65,8 +64,8 @@ #endif - FT_TRACE4(( "tt_face_lookup_table: %08p, `%c%c%c%c' -- ", - face, + FT_TRACE4(( "tt_face_lookup_table: %p, `%c%c%c%c' -- ", + (void *)face, (FT_Char)( tag >> 24 ), (FT_Char)( tag >> 16 ), (FT_Char)( tag >> 8 ), @@ -206,9 +205,8 @@ if ( FT_STREAM_READ_FIELDS( table_dir_entry_fields, &table ) ) { - nn--; FT_TRACE2(( "check_table_dir:" - " can read only %d table%s in font (instead of %d)\n", + " can read only %hu table%s in font (instead of %hu)\n", nn, nn == 1 ? "" : "s", sfnt->num_tables )); sfnt->num_tables = nn; break; @@ -218,7 +216,7 @@ if ( table.Offset > stream->size ) { - FT_TRACE2(( "check_table_dir: table entry %d invalid\n", nn )); + FT_TRACE2(( "check_table_dir: table entry %hu invalid\n", nn )); continue; } else if ( table.Length > stream->size - table.Offset ) @@ -233,7 +231,7 @@ valid_entries++; else { - FT_TRACE2(( "check_table_dir: table entry %d invalid\n", nn )); + FT_TRACE2(( "check_table_dir: table entry %hu invalid\n", nn )); continue; } } @@ -363,7 +361,7 @@ }; - FT_TRACE2(( "tt_face_load_font_dir: %08p\n", face )); + FT_TRACE2(( "tt_face_load_font_dir: %p\n", (void *)face )); /* read the offset table */ @@ -382,7 +380,7 @@ /* load the table directory */ - FT_TRACE2(( "-- Number of tables: %10u\n", sfnt.num_tables )); + FT_TRACE2(( "-- Number of tables: %10hu\n", sfnt.num_tables )); FT_TRACE2(( "-- Format version: 0x%08lx\n", sfnt.format_tag )); if ( sfnt.format_tag != TTAG_OTTO ) @@ -417,9 +415,9 @@ FT_FRAME_ENTER( sfnt.num_tables * 16L ) ) goto Exit; - FT_TRACE2(( "\n" - " tag offset length checksum\n" - " ----------------------------------\n" )); + FT_TRACE2(( "\n" )); + FT_TRACE2(( " tag offset length checksum\n" )); + FT_TRACE2(( " ----------------------------------\n" )); valid_entries = 0; for ( nn = 0; nn < sfnt.num_tables; nn++ ) @@ -506,7 +504,15 @@ FT_FRAME_EXIT(); - FT_TRACE2(( "table directory loaded\n\n" )); + if ( !valid_entries ) + { + FT_TRACE2(( "tt_face_load_font_dir: no valid tables found\n" )); + error = FT_THROW( Unknown_File_Format ); + goto Exit; + } + + FT_TRACE2(( "table directory loaded\n" )); + FT_TRACE2(( "\n" )); Exit: return error; @@ -672,8 +678,8 @@ if ( FT_STREAM_READ_FIELDS( header_fields, header ) ) goto Exit; - FT_TRACE3(( "Units per EM: %4u\n", header->Units_Per_EM )); - FT_TRACE3(( "IndexToLoc: %4d\n", header->Index_To_Loc_Format )); + FT_TRACE3(( "Units per EM: %4hu\n", header->Units_Per_EM )); + FT_TRACE3(( "IndexToLoc: %4hd\n", header->Index_To_Loc_Format )); Exit: return error; @@ -795,15 +801,15 @@ if ( maxProfile->maxTwilightPoints > ( 0xFFFFU - 4 ) ) { FT_TRACE0(( "tt_face_load_maxp:" - " too much twilight points in `maxp' table;\n" - " " + " too much twilight points in `maxp' table;\n" )); + FT_TRACE0(( " " " some glyphs might be rendered incorrectly\n" )); maxProfile->maxTwilightPoints = 0xFFFFU - 4; } } - FT_TRACE3(( "numGlyphs: %u\n", maxProfile->numGlyphs )); + FT_TRACE3(( "numGlyphs: %hu\n", maxProfile->numGlyphs )); Exit: return error; @@ -837,6 +843,8 @@ FT_ULong table_pos, table_len; FT_ULong storage_start, storage_limit; TT_NameTable table; + TT_Name names = NULL; + TT_LangTag langTags = NULL; static const FT_Frame_Field name_table_fields[] = { @@ -917,13 +925,13 @@ storage_start += 2 + 4 * table->numLangTagRecords; /* allocate language tag records array */ - if ( FT_NEW_ARRAY( table->langTags, table->numLangTagRecords ) || - FT_FRAME_ENTER( table->numLangTagRecords * 4 ) ) + if ( FT_QNEW_ARRAY( langTags, table->numLangTagRecords ) || + FT_FRAME_ENTER( table->numLangTagRecords * 4 ) ) goto Exit; /* load language tags */ { - TT_LangTag entry = table->langTags; + TT_LangTag entry = langTags; TT_LangTag limit = FT_OFFSET( entry, table->numLangTagRecords ); @@ -939,7 +947,13 @@ /* invalid entry; ignore it */ entry->stringLength = 0; } + + /* mark the string as not yet loaded */ + entry->string = NULL; } + + table->langTags = langTags; + langTags = NULL; } FT_FRAME_EXIT(); @@ -948,14 +962,15 @@ } /* allocate name records array */ - if ( FT_NEW_ARRAY( table->names, table->numNameRecords ) || - FT_FRAME_ENTER( table->numNameRecords * 12 ) ) + if ( FT_QNEW_ARRAY( names, table->numNameRecords ) || + FT_FRAME_ENTER( table->numNameRecords * 12 ) ) goto Exit; /* load name records */ { - TT_Name entry = table->names; + TT_Name entry = names; FT_UInt count = table->numNameRecords; + FT_UInt valid = 0; for ( ; count > 0; count-- ) @@ -988,15 +1003,20 @@ } } + /* mark the string as not yet converted */ + entry->string = NULL; + + valid++; entry++; } /* reduce array size to the actually used elements */ - count = (FT_UInt)( entry - table->names ); - (void)FT_RENEW_ARRAY( table->names, - table->numNameRecords, - count ); - table->numNameRecords = count; + FT_MEM_QRENEW_ARRAY( names, + table->numNameRecords, + valid ); + table->names = names; + names = NULL; + table->numNameRecords = valid; } FT_FRAME_EXIT(); @@ -1005,6 +1025,8 @@ face->num_names = (FT_UShort)table->numNameRecords; Exit: + FT_FREE( names ); + FT_FREE( langTags ); return error; } @@ -1250,11 +1272,11 @@ } } - FT_TRACE3(( "sTypoAscender: %4d\n", os2->sTypoAscender )); - FT_TRACE3(( "sTypoDescender: %4d\n", os2->sTypoDescender )); - FT_TRACE3(( "usWinAscent: %4u\n", os2->usWinAscent )); - FT_TRACE3(( "usWinDescent: %4u\n", os2->usWinDescent )); - FT_TRACE3(( "fsSelection: 0x%2x\n", os2->fsSelection )); + FT_TRACE3(( "sTypoAscender: %4hd\n", os2->sTypoAscender )); + FT_TRACE3(( "sTypoDescender: %4hd\n", os2->sTypoDescender )); + FT_TRACE3(( "usWinAscent: %4hu\n", os2->usWinAscent )); + FT_TRACE3(( "usWinDescent: %4hu\n", os2->usWinDescent )); + FT_TRACE3(( "fsSelection: 0x%2hx\n", os2->fsSelection )); Exit: return error; @@ -1312,10 +1334,16 @@ if ( FT_STREAM_READ_FIELDS( post_fields, post ) ) return error; + if ( post->FormatType != 0x00030000L && + post->FormatType != 0x00025000L && + post->FormatType != 0x00020000L && + post->FormatType != 0x00010000L ) + return FT_THROW( Invalid_Post_Table_Format ); + /* we don't load the glyph names, we do that in another */ /* module (ttpost). */ - FT_TRACE3(( "FormatType: 0x%x\n", post->FormatType )); + FT_TRACE3(( "FormatType: 0x%lx\n", post->FormatType )); FT_TRACE3(( "isFixedPitch: %s\n", post->isFixedPitch ? " yes" : " no" )); @@ -1411,8 +1439,8 @@ FT_Error error; FT_Memory memory = stream->memory; - FT_UInt j,num_ranges; - TT_GaspRange gaspranges = NULL; + FT_UShort j, num_ranges; + TT_GaspRange gasp_ranges = NULL; /* the gasp table is optional */ @@ -1423,8 +1451,8 @@ if ( FT_FRAME_ENTER( 4L ) ) goto Exit; - face->gasp.version = FT_GET_USHORT(); - face->gasp.numRanges = FT_GET_USHORT(); + face->gasp.version = FT_GET_USHORT(); + num_ranges = FT_GET_USHORT(); FT_FRAME_EXIT(); @@ -1436,29 +1464,31 @@ goto Exit; } - num_ranges = face->gasp.numRanges; - FT_TRACE3(( "numRanges: %u\n", num_ranges )); + FT_TRACE3(( "numRanges: %hu\n", num_ranges )); - if ( FT_QNEW_ARRAY( face->gasp.gaspRanges, num_ranges ) || - FT_FRAME_ENTER( num_ranges * 4L ) ) + if ( FT_QNEW_ARRAY( gasp_ranges, num_ranges ) || + FT_FRAME_ENTER( num_ranges * 4L ) ) goto Exit; - gaspranges = face->gasp.gaspRanges; - for ( j = 0; j < num_ranges; j++ ) { - gaspranges[j].maxPPEM = FT_GET_USHORT(); - gaspranges[j].gaspFlag = FT_GET_USHORT(); + gasp_ranges[j].maxPPEM = FT_GET_USHORT(); + gasp_ranges[j].gaspFlag = FT_GET_USHORT(); - FT_TRACE3(( "gaspRange %d: rangeMaxPPEM %5d, rangeGaspBehavior 0x%x\n", + FT_TRACE3(( "gaspRange %hu: rangeMaxPPEM %5hu, rangeGaspBehavior 0x%hx\n", j, - gaspranges[j].maxPPEM, - gaspranges[j].gaspFlag )); + gasp_ranges[j].maxPPEM, + gasp_ranges[j].gaspFlag )); } + face->gasp.gaspRanges = gasp_ranges; + gasp_ranges = NULL; + face->gasp.numRanges = num_ranges; + FT_FRAME_EXIT(); Exit: + FT_FREE( gasp_ranges ); return error; } diff --git a/src/font/freetype-2.10.2/src/sfnt/ttload.h b/3rdparty/freetype-2.13.2/src/sfnt/ttload.h similarity index 95% rename from src/font/freetype-2.10.2/src/sfnt/ttload.h rename to 3rdparty/freetype-2.13.2/src/sfnt/ttload.h index 49d40655f..1499dd573 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttload.h +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttload.h @@ -5,7 +5,7 @@ * Load the basic TrueType tables, i.e., tables that can be either in * TTF or OTF fonts (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -21,9 +21,8 @@ #define TTLOAD_H_ -#include -#include FT_INTERNAL_STREAM_H -#include FT_INTERNAL_TRUETYPE_TYPES_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/src/sfnt/ttmtx.c b/3rdparty/freetype-2.13.2/src/sfnt/ttmtx.c similarity index 96% rename from src/font/freetype-2.10.2/src/sfnt/ttmtx.c rename to 3rdparty/freetype-2.13.2/src/sfnt/ttmtx.c index e18ff877e..38ee9ae72 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttmtx.c +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttmtx.c @@ -4,7 +4,7 @@ * * Load the metrics tables common to TTF and OTF fonts (body). * - * Copyright (C) 2006-2020 by + * Copyright (C) 2006-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,13 +16,12 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_STREAM_H -#include FT_TRUETYPE_TAGS_H +#include +#include +#include #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT -#include FT_SERVICE_METRICS_VARIATIONS_H +#include #endif #include "ttmtx.h" @@ -240,7 +239,7 @@ #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT FT_Service_MetricsVariations var = - (FT_Service_MetricsVariations)face->var; + (FT_Service_MetricsVariations)face->tt_var; #endif @@ -307,7 +306,7 @@ } #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT - if ( var ) + if ( var && face->blend ) { FT_Face f = FT_FACE( face ); FT_Int a = (FT_Int)*aadvance; diff --git a/src/font/freetype-2.10.2/src/sfnt/ttmtx.h b/3rdparty/freetype-2.13.2/src/sfnt/ttmtx.h similarity index 90% rename from src/font/freetype-2.10.2/src/sfnt/ttmtx.h rename to 3rdparty/freetype-2.13.2/src/sfnt/ttmtx.h index c98c79ec5..56d2b6276 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttmtx.h +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttmtx.h @@ -4,7 +4,7 @@ * * Load the metrics tables common to TTF and OTF fonts (specification). * - * Copyright (C) 2006-2020 by + * Copyright (C) 2006-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,9 +20,8 @@ #define TTMTX_H_ -#include -#include FT_INTERNAL_STREAM_H -#include FT_INTERNAL_TRUETYPE_TYPES_H +#include +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/src/sfnt/ttpost.c b/3rdparty/freetype-2.13.2/src/sfnt/ttpost.c similarity index 59% rename from src/font/freetype-2.10.2/src/sfnt/ttpost.c rename to 3rdparty/freetype-2.13.2/src/sfnt/ttpost.c index f7be71621..1dfad4298 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttpost.c +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttpost.c @@ -5,7 +5,7 @@ * PostScript name table processing for TrueType and OpenType fonts * (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -25,10 +25,9 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_STREAM_H -#include FT_TRUETYPE_TAGS_H +#include +#include +#include #ifdef TT_CONFIG_OPTION_POSTSCRIPT_NAMES @@ -54,12 +53,12 @@ #ifdef FT_CONFIG_OPTION_POSTSCRIPT_NAMES -#include FT_SERVICE_POSTSCRIPT_CMAPS_H +#include #define MAC_NAME( x ) (FT_String*)psnames->macintosh_name( (FT_UInt)(x) ) -#else /* FT_CONFIG_OPTION_POSTSCRIPT_NAMES */ +#else /* !FT_CONFIG_OPTION_POSTSCRIPT_NAMES */ /* Otherwise, we ignore the `psnames' module, and provide our own */ @@ -153,155 +152,109 @@ }; -#endif /* FT_CONFIG_OPTION_POSTSCRIPT_NAMES */ +#endif /* !FT_CONFIG_OPTION_POSTSCRIPT_NAMES */ static FT_Error - load_format_20( TT_Face face, - FT_Stream stream, - FT_ULong post_limit ) + load_format_20( TT_Post_Names names, + FT_Stream stream, + FT_UShort num_glyphs, + FT_ULong post_len ) { FT_Memory memory = stream->memory; FT_Error error; - FT_Int num_glyphs; - FT_UShort num_names; + FT_UShort n; + FT_UShort num_names = 0; FT_UShort* glyph_indices = NULL; - FT_Char** name_strings = NULL; + FT_Byte** name_strings = NULL; + FT_Byte* q; - if ( FT_READ_USHORT( num_glyphs ) ) - goto Exit; - - /* UNDOCUMENTED! The number of glyphs in this table can be smaller */ - /* than the value in the maxp table (cf. cyberbit.ttf). */ - - /* There already exist fonts which have more than 32768 glyph names */ - /* in this table, so the test for this threshold has been dropped. */ - - if ( num_glyphs > face->max_profile.numGlyphs ) + if ( (FT_ULong)num_glyphs * 2 > post_len ) { error = FT_THROW( Invalid_File_Format ); goto Exit; } - /* load the indices */ - { - FT_Int n; - - - if ( FT_NEW_ARRAY ( glyph_indices, num_glyphs ) || - FT_FRAME_ENTER( num_glyphs * 2L ) ) - goto Fail; - - for ( n = 0; n < num_glyphs; n++ ) - glyph_indices[n] = FT_GET_USHORT(); + /* load the indices and note their maximum */ + if ( FT_QNEW_ARRAY( glyph_indices, num_glyphs ) || + FT_FRAME_ENTER( num_glyphs * 2 ) ) + goto Fail; - FT_FRAME_EXIT(); - } + q = (FT_Byte*)stream->cursor; - /* compute number of names stored in table */ + for ( n = 0; n < num_glyphs; n++ ) { - FT_Int n; + FT_UShort idx = FT_NEXT_USHORT( q ); - num_names = 0; + if ( idx > num_names ) + num_names = idx; - for ( n = 0; n < num_glyphs; n++ ) - { - FT_Int idx; + glyph_indices[n] = idx; + } + FT_FRAME_EXIT(); - idx = glyph_indices[n]; - if ( idx >= 258 ) - { - idx -= 257; - if ( idx > num_names ) - num_names = (FT_UShort)idx; - } - } - } + /* compute number of names stored in the table */ + num_names = num_names > 257 ? num_names - 257 : 0; /* now load the name strings */ + if ( num_names ) { - FT_UShort n; + FT_ULong p; + FT_Byte* strings; - if ( FT_NEW_ARRAY( name_strings, num_names ) ) - goto Fail; + post_len -= (FT_ULong)num_glyphs * 2; - for ( n = 0; n < num_names; n++ ) - { - FT_UInt len; + if ( FT_QALLOC( name_strings, num_names * sizeof ( FT_Byte* ) + + post_len + 1 ) ) + goto Fail; + strings = (FT_Byte*)( name_strings + num_names ); + if ( FT_STREAM_READ( strings, post_len ) ) + goto Fail; - if ( FT_STREAM_POS() >= post_limit ) - break; - else - { - FT_TRACE6(( "load_format_20: %d byte left in post table\n", - post_limit - FT_STREAM_POS() )); + /* convert from Pascal- to C-strings and set pointers */ + for ( p = 0, n = 0; p < post_len && n < num_names; n++ ) + { + FT_UInt len = strings[p]; - if ( FT_READ_BYTE( len ) ) - goto Fail1; - } - if ( len > post_limit || - FT_STREAM_POS() > post_limit - len ) + if ( len > 63U ) { - FT_Int d = (FT_Int)post_limit - (FT_Int)FT_STREAM_POS(); - - - FT_ERROR(( "load_format_20:" - " exceeding string length (%d)," - " truncating at end of post table (%d byte left)\n", - len, d )); - len = (FT_UInt)FT_MAX( 0, d ); + error = FT_THROW( Invalid_File_Format ); + goto Fail; } - if ( FT_NEW_ARRAY( name_strings[n], len + 1 ) || - FT_STREAM_READ( name_strings[n], len ) ) - goto Fail1; - - name_strings[n][len] = '\0'; + strings[p] = 0; + name_strings[n] = strings + p + 1; + p += len + 1; } + strings[post_len] = 0; + /* deal with missing or insufficient string data */ if ( n < num_names ) { - FT_ERROR(( "load_format_20:" - " all entries in post table are already parsed," - " using NULL names for gid %d - %d\n", - n, num_names - 1 )); + FT_TRACE4(( "load_format_20: %hu PostScript names are truncated\n", + num_names - n )); + for ( ; n < num_names; n++ ) - if ( FT_NEW_ARRAY( name_strings[n], 1 ) ) - goto Fail1; - else - name_strings[n][0] = '\0'; + name_strings[n] = strings + post_len; } } /* all right, set table fields and exit successfully */ - { - TT_Post_20 table = &face->postscript_names.names.format_20; + names->num_glyphs = num_glyphs; + names->num_names = num_names; + names->glyph_indices = glyph_indices; + names->glyph_names = name_strings; - - table->num_glyphs = (FT_UShort)num_glyphs; - table->num_names = (FT_UShort)num_names; - table->glyph_indices = glyph_indices; - table->glyph_names = name_strings; - } return FT_Err_Ok; - Fail1: - { - FT_UShort n; - - - for ( n = 0; n < num_names; n++ ) - FT_FREE( name_strings[n] ); - } - Fail: FT_FREE( name_strings ); FT_FREE( glyph_indices ); @@ -312,66 +265,55 @@ static FT_Error - load_format_25( TT_Face face, - FT_Stream stream, - FT_ULong post_limit ) + load_format_25( TT_Post_Names names, + FT_Stream stream, + FT_UShort num_glyphs, + FT_ULong post_len ) { FT_Memory memory = stream->memory; FT_Error error; - FT_Int num_glyphs; - FT_Char* offset_table = NULL; - - FT_UNUSED( post_limit ); - + FT_UShort n; + FT_UShort* glyph_indices = NULL; + FT_Byte* q; - if ( FT_READ_USHORT( num_glyphs ) ) - goto Exit; - /* check the number of glyphs */ - if ( num_glyphs > face->max_profile.numGlyphs || - num_glyphs > 258 || - num_glyphs < 1 ) + /* check the number of glyphs, including the theoretical limit */ + if ( num_glyphs > post_len || + num_glyphs > 258 + 128 ) { error = FT_THROW( Invalid_File_Format ); goto Exit; } - if ( FT_NEW_ARRAY( offset_table, num_glyphs ) || - FT_STREAM_READ( offset_table, num_glyphs ) ) + /* load the indices and check their Mac range */ + if ( FT_QNEW_ARRAY( glyph_indices, num_glyphs ) || + FT_FRAME_ENTER( num_glyphs ) ) goto Fail; - /* now check the offset table */ - { - FT_Int n; + q = (FT_Byte*)stream->cursor; + for ( n = 0; n < num_glyphs; n++ ) + { + FT_Int idx = n + FT_NEXT_CHAR( q ); - for ( n = 0; n < num_glyphs; n++ ) - { - FT_Long idx = (FT_Long)n + offset_table[n]; + if ( idx < 0 || idx > 257 ) + idx = 0; - if ( idx < 0 || idx > num_glyphs ) - { - error = FT_THROW( Invalid_File_Format ); - goto Fail; - } - } + glyph_indices[n] = (FT_UShort)idx; } - /* OK, set table fields and exit successfully */ - { - TT_Post_25 table = &face->postscript_names.names.format_25; - + FT_FRAME_EXIT(); - table->num_glyphs = (FT_UShort)num_glyphs; - table->offsets = offset_table; - } + /* OK, set table fields and exit successfully */ + names->num_glyphs = num_glyphs; + names->glyph_indices = glyph_indices; return FT_Err_Ok; Fail: - FT_FREE( offset_table ); + FT_FREE( glyph_indices ); Exit: return error; @@ -381,40 +323,37 @@ static FT_Error load_post_names( TT_Face face ) { - FT_Stream stream; - FT_Error error; - FT_Fixed format; + FT_Error error = FT_Err_Ok; + FT_Stream stream = face->root.stream; + FT_Fixed format = face->postscript.FormatType; FT_ULong post_len; - FT_ULong post_limit; + FT_UShort num_glyphs; - /* get a stream for the face's resource */ - stream = face->root.stream; - /* seek to the beginning of the PS names table */ error = face->goto_table( face, TTAG_post, stream, &post_len ); if ( error ) goto Exit; - post_limit = FT_STREAM_POS() + post_len; - - format = face->postscript.FormatType; - - /* go to beginning of subtable */ - if ( FT_STREAM_SKIP( 32 ) ) + /* UNDOCUMENTED! The number of glyphs in this table can be smaller */ + /* than the value in the maxp table (cf. cyberbit.ttf). */ + if ( post_len < 34 || + FT_STREAM_SKIP( 32 ) || + FT_READ_USHORT( num_glyphs ) || + num_glyphs > face->max_profile.numGlyphs || + num_glyphs == 0 ) goto Exit; - /* now read postscript table */ + /* now read postscript names data */ if ( format == 0x00020000L ) - error = load_format_20( face, stream, post_limit ); + error = load_format_20( &face->postscript_names, stream, + num_glyphs, post_len - 34 ); else if ( format == 0x00025000L ) - error = load_format_25( face, stream, post_limit ); - else - error = FT_THROW( Invalid_File_Format ); - - face->postscript_names.loaded = 1; + error = load_format_25( &face->postscript_names, stream, + num_glyphs, post_len - 34 ); Exit: + face->postscript_names.loaded = 1; /* even if failed */ return error; } @@ -424,37 +363,20 @@ { FT_Memory memory = face->root.memory; TT_Post_Names names = &face->postscript_names; - FT_Fixed format; - if ( names->loaded ) + if ( names->num_glyphs ) { - format = face->postscript.FormatType; - - if ( format == 0x00020000L ) - { - TT_Post_20 table = &names->names.format_20; - FT_UShort n; - - - FT_FREE( table->glyph_indices ); - table->num_glyphs = 0; - - for ( n = 0; n < table->num_names; n++ ) - FT_FREE( table->glyph_names[n] ); - - FT_FREE( table->glyph_names ); - table->num_names = 0; - } - else if ( format == 0x00025000L ) - { - TT_Post_25 table = &names->names.format_25; - + FT_FREE( names->glyph_indices ); + names->num_glyphs = 0; + } - FT_FREE( table->offsets ); - table->num_glyphs = 0; - } + if ( names->num_names ) + { + FT_FREE( names->glyph_names ); + names->num_names = 0; } + names->loaded = 0; } @@ -490,7 +412,6 @@ FT_String** PSname ) { FT_Error error; - TT_Post_Names names; FT_Fixed format; #ifdef FT_CONFIG_OPTION_POSTSCRIPT_NAMES @@ -510,8 +431,6 @@ return FT_THROW( Unimplemented_Feature ); #endif - names = &face->postscript_names; - /* `.notdef' by default */ *PSname = MAC_NAME( 0 ); @@ -522,9 +441,10 @@ if ( idx < 258 ) /* paranoid checking */ *PSname = MAC_NAME( idx ); } - else if ( format == 0x00020000L ) + else if ( format == 0x00020000L || + format == 0x00025000L ) { - TT_Post_20 table = &names->names.format_20; + TT_Post_Names names = &face->postscript_names; if ( !names->loaded ) @@ -534,43 +454,29 @@ goto End; } - if ( idx < (FT_UInt)table->num_glyphs ) + if ( idx < (FT_UInt)names->num_glyphs ) { - FT_UShort name_index = table->glyph_indices[idx]; + FT_UShort name_index = names->glyph_indices[idx]; if ( name_index < 258 ) *PSname = MAC_NAME( name_index ); - else - *PSname = (FT_String*)table->glyph_names[name_index - 258]; + else /* only for version 2.0 */ + *PSname = (FT_String*)names->glyph_names[name_index - 258]; } } - else if ( format == 0x00025000L ) - { - TT_Post_25 table = &names->names.format_25; - - - if ( !names->loaded ) - { - error = load_post_names( face ); - if ( error ) - goto End; - } - - if ( idx < (FT_UInt)table->num_glyphs ) /* paranoid checking */ - *PSname = MAC_NAME( (FT_Int)idx + table->offsets[idx] ); - } /* nothing to do for format == 0x00030000L */ End: + /* post format errors ignored */ return FT_Err_Ok; } #else /* !TT_CONFIG_OPTION_POSTSCRIPT_NAMES */ /* ANSI C doesn't like empty source files */ - typedef int _tt_post_dummy; + typedef int tt_post_dummy_; #endif /* !TT_CONFIG_OPTION_POSTSCRIPT_NAMES */ diff --git a/src/font/freetype-2.10.2/src/sfnt/ttpost.h b/3rdparty/freetype-2.13.2/src/sfnt/ttpost.h similarity index 93% rename from src/font/freetype-2.10.2/src/sfnt/ttpost.h rename to 3rdparty/freetype-2.13.2/src/sfnt/ttpost.h index 547f2ff84..528f1c5f2 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttpost.h +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttpost.h @@ -5,7 +5,7 @@ * PostScript name table processing for TrueType and OpenType fonts * (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -23,7 +23,7 @@ #include #include FT_CONFIG_CONFIG_H -#include FT_INTERNAL_TRUETYPE_TYPES_H +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/src/sfnt/ttsbit.c b/3rdparty/freetype-2.13.2/src/sfnt/ttsbit.c similarity index 95% rename from src/font/freetype-2.10.2/src/sfnt/ttsbit.c rename to 3rdparty/freetype-2.13.2/src/sfnt/ttsbit.c index 3f8730f7f..03f90a628 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttsbit.c +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttsbit.c @@ -4,7 +4,7 @@ * * TrueType and OpenType embedded bitmap support (body). * - * Copyright (C) 2005-2020 by + * Copyright (C) 2005-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * Copyright 2013 by Google, Inc. @@ -19,11 +19,10 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_STREAM_H -#include FT_TRUETYPE_TAGS_H -#include FT_BITMAP_H +#include +#include +#include +#include #ifdef TT_CONFIG_OPTION_EMBEDDED_BITMAPS @@ -173,13 +172,8 @@ goto Exit; } - /* we currently don't support bit 1; however, it is better to */ - /* draw at least something... */ if ( flags == 3 ) - FT_TRACE1(( "tt_face_load_sbit_strikes:" - " sbix overlay not supported yet\n" - " " - " expect bad rendering results\n" )); + face->root.face_flags |= FT_FACE_FLAG_SBIX_OVERLAY; /* * Count the number of strikes available in the table. We are a bit @@ -241,8 +235,8 @@ if ( !face->ebdt_size ) { FT_TRACE2(( "tt_face_load_sbit_strikes:" - " no embedded bitmap data table found;\n" - " " + " no embedded bitmap data table found;\n" )); + FT_TRACE2(( " " " resetting number of strikes to zero\n" )); face->sbit_num_strikes = 0; } @@ -346,9 +340,9 @@ if ( metrics->ascender == 0 ) { FT_TRACE2(( "tt_face_load_strike_metrics:" - " sanitizing invalid ascender and descender\n" - " " - " values for strike %d (%dppem, %dppem)\n", + " sanitizing invalid ascender and descender\n" )); + FT_TRACE2(( " " + " values for strike %ld (%dppem, %dppem)\n", strike_index, metrics->x_ppem, metrics->y_ppem )); @@ -375,8 +369,8 @@ if ( metrics->height == 0 ) { FT_TRACE2(( "tt_face_load_strike_metrics:" - " sanitizing invalid height value\n" - " " + " sanitizing invalid height value\n" )); + FT_TRACE2(( " " " for strike (%d, %d)\n", metrics->x_ppem, metrics->y_ppem )); metrics->height = metrics->y_ppem * 64; @@ -391,11 +385,9 @@ /* set the scale values (in 16.16 units) so advances */ /* from the hmtx and vmtx table are scaled correctly */ - metrics->x_scale = FT_MulDiv( metrics->x_ppem, - 64 * 0x10000, + metrics->x_scale = FT_DivFix( metrics->x_ppem * 64, face->header.Units_Per_EM ); - metrics->y_scale = FT_MulDiv( metrics->y_ppem, - 64 * 0x10000, + metrics->y_scale = FT_DivFix( metrics->y_ppem * 64, face->header.Units_Per_EM ); return FT_Err_Ok; @@ -405,9 +397,9 @@ { FT_Stream stream = face->root.stream; FT_UInt offset; - FT_UShort upem, ppem, resolution; + FT_UShort ppem, resolution; TT_HoriHeader *hori; - FT_Pos ppem_; /* to reduce casts */ + FT_Fixed scale; FT_Error error; FT_Byte* p; @@ -430,32 +422,23 @@ FT_FRAME_EXIT(); - upem = face->header.Units_Per_EM; - hori = &face->horizontal; - metrics->x_ppem = ppem; metrics->y_ppem = ppem; - ppem_ = (FT_Pos)ppem; + scale = FT_DivFix( ppem * 64, face->header.Units_Per_EM ); + hori = &face->horizontal; - metrics->ascender = - FT_MulDiv( hori->Ascender, ppem_ * 64, upem ); - metrics->descender = - FT_MulDiv( hori->Descender, ppem_ * 64, upem ); - metrics->height = - FT_MulDiv( hori->Ascender - hori->Descender + hori->Line_Gap, - ppem_ * 64, upem ); - metrics->max_advance = - FT_MulDiv( hori->advance_Width_Max, ppem_ * 64, upem ); + metrics->ascender = FT_MulFix( hori->Ascender, scale ); + metrics->descender = FT_MulFix( hori->Descender, scale ); + metrics->height = + FT_MulFix( hori->Ascender - hori->Descender + hori->Line_Gap, + scale ); + metrics->max_advance = FT_MulFix( hori->advance_Width_Max, scale ); /* set the scale values (in 16.16 units) so advances */ /* from the hmtx and vmtx table are scaled correctly */ - metrics->x_scale = FT_MulDiv( metrics->x_ppem, - 64 * 0x10000, - face->header.Units_Per_EM ); - metrics->y_scale = FT_MulDiv( metrics->y_ppem, - 64 * 0x10000, - face->header.Units_Per_EM ); + metrics->x_scale = scale; + metrics->y_scale = scale; return error; } @@ -727,6 +710,9 @@ pitch = bitmap->pitch; line = bitmap->buffer; + if ( !line ) + goto Exit; + width = decoder->metrics->width; height = decoder->metrics->height; @@ -1207,7 +1193,7 @@ goto Fail; p += 1; /* skip padding */ - /* fall-through */ + FALL_THROUGH; case 9: loader = tt_sbit_decoder_load_compound; @@ -1574,23 +1560,40 @@ if ( !error ) { - FT_Short abearing; + FT_Short abearing; /* not used here */ FT_UShort aadvance; tt_face_get_metrics( face, FALSE, glyph_index, &abearing, &aadvance ); metrics->horiBearingX = (FT_Short)originOffsetX; - metrics->horiBearingY = (FT_Short)( -originOffsetY + metrics->height ); + metrics->vertBearingX = (FT_Short)originOffsetX; + + metrics->horiBearingY = (FT_Short)( originOffsetY + metrics->height ); + metrics->vertBearingY = (FT_Short)originOffsetY; + metrics->horiAdvance = (FT_UShort)( aadvance * face->root.size->metrics.x_ppem / face->header.Units_Per_EM ); + + if ( face->vertical_info ) + tt_face_get_metrics( face, TRUE, glyph_index, &abearing, &aadvance ); + else if ( face->os2.version != 0xFFFFU ) + aadvance = (FT_UShort)FT_ABS( face->os2.sTypoAscender - + face->os2.sTypoDescender ); + else + aadvance = (FT_UShort)FT_ABS( face->horizontal.Ascender - + face->horizontal.Descender ); + + metrics->vertAdvance = (FT_UShort)( aadvance * + face->root.size->metrics.x_ppem / + face->header.Units_Per_EM ); } return error; } - FT_LOCAL( FT_Error ) + FT_LOCAL_DEF( FT_Error ) tt_face_load_sbit_image( TT_Face face, FT_ULong strike_index, FT_UInt glyph_index, @@ -1674,7 +1677,7 @@ #else /* !TT_CONFIG_OPTION_EMBEDDED_BITMAPS */ /* ANSI C doesn't like empty source files */ - typedef int _tt_sbit_dummy; + typedef int tt_sbit_dummy_; #endif /* !TT_CONFIG_OPTION_EMBEDDED_BITMAPS */ diff --git a/src/font/freetype-2.10.2/src/sfnt/ttsbit.h b/3rdparty/freetype-2.13.2/src/sfnt/ttsbit.h similarity index 96% rename from src/font/freetype-2.10.2/src/sfnt/ttsbit.h rename to 3rdparty/freetype-2.13.2/src/sfnt/ttsbit.h index dfeb88683..07e2db461 100644 --- a/src/font/freetype-2.10.2/src/sfnt/ttsbit.h +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttsbit.h @@ -4,7 +4,7 @@ * * TrueType and OpenType embedded bitmap support (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,7 +20,6 @@ #define TTSBIT_H_ -#include #include "ttload.h" diff --git a/3rdparty/freetype-2.13.2/src/sfnt/ttsvg.c b/3rdparty/freetype-2.13.2/src/sfnt/ttsvg.c new file mode 100644 index 000000000..4461d483b --- /dev/null +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttsvg.c @@ -0,0 +1,413 @@ +/**************************************************************************** + * + * ttsvg.c + * + * OpenType SVG Color (specification). + * + * Copyright (C) 2022-2023 by + * David Turner, Robert Wilhelm, Werner Lemberg, and Moazin Khatti. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + + /************************************************************************** + * + * 'SVG' table specification: + * + * https://docs.microsoft.com/en-us/typography/opentype/spec/svg + * + */ + +#include +#include +#include +#include +#include +#include +#include + + +#ifdef FT_CONFIG_OPTION_SVG + +#include "ttsvg.h" + + + /* NOTE: These table sizes are given by the specification. */ +#define SVG_TABLE_HEADER_SIZE (10U) +#define SVG_DOCUMENT_RECORD_SIZE (12U) +#define SVG_DOCUMENT_LIST_MINIMUM_SIZE (2U + SVG_DOCUMENT_RECORD_SIZE) +#define SVG_MINIMUM_SIZE (SVG_TABLE_HEADER_SIZE + \ + SVG_DOCUMENT_LIST_MINIMUM_SIZE) + + + typedef struct Svg_ + { + FT_UShort version; /* table version (starting at 0) */ + FT_UShort num_entries; /* number of SVG document records */ + + FT_Byte* svg_doc_list; /* pointer to the start of SVG Document List */ + + void* table; /* memory that backs up SVG */ + FT_ULong table_size; + + } Svg; + + + /************************************************************************** + * + * The macro FT_COMPONENT is used in trace mode. It is an implicit + * parameter of the FT_TRACE() and FT_ERROR() macros, usued to print/log + * messages during execution. + */ +#undef FT_COMPONENT +#define FT_COMPONENT ttsvg + + + FT_LOCAL_DEF( FT_Error ) + tt_face_load_svg( TT_Face face, + FT_Stream stream ) + { + FT_Error error; + FT_Memory memory = face->root.memory; + + FT_ULong table_size; + FT_Byte* table = NULL; + FT_Byte* p = NULL; + Svg* svg = NULL; + FT_ULong offsetToSVGDocumentList; + + + error = face->goto_table( face, TTAG_SVG, stream, &table_size ); + if ( error ) + goto NoSVG; + + if ( table_size < SVG_MINIMUM_SIZE ) + goto InvalidTable; + + if ( FT_FRAME_EXTRACT( table_size, table ) ) + goto NoSVG; + + /* Allocate memory for the SVG object */ + if ( FT_NEW( svg ) ) + goto NoSVG; + + p = table; + svg->version = FT_NEXT_USHORT( p ); + offsetToSVGDocumentList = FT_NEXT_ULONG( p ); + + if ( offsetToSVGDocumentList < SVG_TABLE_HEADER_SIZE || + offsetToSVGDocumentList > table_size - + SVG_DOCUMENT_LIST_MINIMUM_SIZE ) + goto InvalidTable; + + svg->svg_doc_list = (FT_Byte*)( table + offsetToSVGDocumentList ); + + p = svg->svg_doc_list; + svg->num_entries = FT_NEXT_USHORT( p ); + + FT_TRACE3(( "version: %d\n", svg->version )); + FT_TRACE3(( "number of entries: %d\n", svg->num_entries )); + + if ( offsetToSVGDocumentList + 2U + + svg->num_entries * SVG_DOCUMENT_RECORD_SIZE > table_size ) + goto InvalidTable; + + svg->table = table; + svg->table_size = table_size; + + face->svg = svg; + face->root.face_flags |= FT_FACE_FLAG_SVG; + + return FT_Err_Ok; + + InvalidTable: + error = FT_THROW( Invalid_Table ); + + NoSVG: + FT_FRAME_RELEASE( table ); + FT_FREE( svg ); + face->svg = NULL; + + return error; + } + + + FT_LOCAL_DEF( void ) + tt_face_free_svg( TT_Face face ) + { + FT_Memory memory = face->root.memory; + FT_Stream stream = face->root.stream; + + Svg* svg = (Svg*)face->svg; + + + if ( svg ) + { + FT_FRAME_RELEASE( svg->table ); + FT_FREE( svg ); + } + } + + + typedef struct Svg_doc_ + { + FT_UShort start_glyph_id; + FT_UShort end_glyph_id; + + FT_ULong offset; + FT_ULong length; + + } Svg_doc; + + + static Svg_doc + extract_svg_doc( FT_Byte* stream ) + { + Svg_doc doc; + + + doc.start_glyph_id = FT_NEXT_USHORT( stream ); + doc.end_glyph_id = FT_NEXT_USHORT( stream ); + + doc.offset = FT_NEXT_ULONG( stream ); + doc.length = FT_NEXT_ULONG( stream ); + + return doc; + } + + + static FT_Int + compare_svg_doc( Svg_doc doc, + FT_UInt glyph_index ) + { + if ( glyph_index < doc.start_glyph_id ) + return -1; + else if ( glyph_index > doc.end_glyph_id ) + return 1; + else + return 0; + } + + + static FT_Error + find_doc( FT_Byte* document_records, + FT_UShort num_entries, + FT_UInt glyph_index, + FT_ULong *doc_offset, + FT_ULong *doc_length, + FT_UShort *start_glyph, + FT_UShort *end_glyph ) + { + FT_Error error; + + Svg_doc start_doc; + Svg_doc mid_doc = { 0, 0, 0, 0 }; /* pacify compiler */ + Svg_doc end_doc; + + FT_Bool found = FALSE; + FT_UInt i = 0; + + FT_UInt start_index = 0; + FT_UInt end_index = num_entries - 1; + FT_Int comp_res; + + + /* search algorithm */ + if ( num_entries == 0 ) + { + error = FT_THROW( Invalid_Table ); + return error; + } + + start_doc = extract_svg_doc( document_records + start_index * 12 ); + end_doc = extract_svg_doc( document_records + end_index * 12 ); + + if ( ( compare_svg_doc( start_doc, glyph_index ) == -1 ) || + ( compare_svg_doc( end_doc, glyph_index ) == 1 ) ) + { + error = FT_THROW( Invalid_Glyph_Index ); + return error; + } + + while ( start_index <= end_index ) + { + i = ( start_index + end_index ) / 2; + mid_doc = extract_svg_doc( document_records + i * 12 ); + comp_res = compare_svg_doc( mid_doc, glyph_index ); + + if ( comp_res == 1 ) + { + start_index = i + 1; + start_doc = extract_svg_doc( document_records + start_index * 4 ); + } + else if ( comp_res == -1 ) + { + end_index = i - 1; + end_doc = extract_svg_doc( document_records + end_index * 4 ); + } + else + { + found = TRUE; + break; + } + } + /* search algorithm end */ + + if ( found != TRUE ) + { + FT_TRACE5(( "SVG glyph not found\n" )); + error = FT_THROW( Invalid_Glyph_Index ); + } + else + { + *doc_offset = mid_doc.offset; + *doc_length = mid_doc.length; + + *start_glyph = mid_doc.start_glyph_id; + *end_glyph = mid_doc.end_glyph_id; + + error = FT_Err_Ok; + } + + return error; + } + + + FT_LOCAL_DEF( FT_Error ) + tt_face_load_svg_doc( FT_GlyphSlot glyph, + FT_UInt glyph_index ) + { + FT_Error error = FT_Err_Ok; + TT_Face face = (TT_Face)glyph->face; + FT_Memory memory = face->root.memory; + Svg* svg = (Svg*)face->svg; + + FT_Byte* doc_list; + FT_ULong doc_limit; + + FT_Byte* doc; + FT_ULong doc_offset; + FT_ULong doc_length; + FT_UShort doc_start_glyph_id; + FT_UShort doc_end_glyph_id; + + FT_SVG_Document svg_document = (FT_SVG_Document)glyph->other; + + + FT_ASSERT( !( svg == NULL ) ); + + doc_list = svg->svg_doc_list; + + error = find_doc( doc_list + 2, svg->num_entries, glyph_index, + &doc_offset, &doc_length, + &doc_start_glyph_id, &doc_end_glyph_id ); + if ( error != FT_Err_Ok ) + goto Exit; + + doc_limit = svg->table_size - + (FT_ULong)( doc_list - (FT_Byte*)svg->table ); + if ( doc_offset > doc_limit || + doc_length > doc_limit - doc_offset ) + { + error = FT_THROW( Invalid_Table ); + goto Exit; + } + + doc = doc_list + doc_offset; + + if ( doc_length > 6 && + doc[0] == 0x1F && + doc[1] == 0x8B && + doc[2] == 0x08 ) + { +#ifdef FT_CONFIG_OPTION_USE_ZLIB + + FT_ULong uncomp_size; + FT_Byte* uncomp_buffer = NULL; + + + /* + * Get the size of the original document. This helps in allotting the + * buffer to accommodate the uncompressed version. The last 4 bytes + * of the compressed document are equal to the original size modulo + * 2^32. Since the size of SVG documents is less than 2^32 bytes we + * can use this accurately. The four bytes are stored in + * little-endian format. + */ + FT_TRACE4(( "SVG document is GZIP compressed\n" )); + uncomp_size = (FT_ULong)doc[doc_length - 1] << 24 | + (FT_ULong)doc[doc_length - 2] << 16 | + (FT_ULong)doc[doc_length - 3] << 8 | + (FT_ULong)doc[doc_length - 4]; + + if ( FT_QALLOC( uncomp_buffer, uncomp_size ) ) + goto Exit; + + error = FT_Gzip_Uncompress( memory, + uncomp_buffer, + &uncomp_size, + doc, + doc_length ); + if ( error ) + { + FT_FREE( uncomp_buffer ); + error = FT_THROW( Invalid_Table ); + goto Exit; + } + + glyph->internal->flags |= FT_GLYPH_OWN_GZIP_SVG; + + doc = uncomp_buffer; + doc_length = uncomp_size; + +#else /* !FT_CONFIG_OPTION_USE_ZLIB */ + + error = FT_THROW( Unimplemented_Feature ); + goto Exit; + +#endif /* !FT_CONFIG_OPTION_USE_ZLIB */ + } + + svg_document->svg_document = doc; + svg_document->svg_document_length = doc_length; + + svg_document->metrics = glyph->face->size->metrics; + svg_document->units_per_EM = glyph->face->units_per_EM; + + svg_document->start_glyph_id = doc_start_glyph_id; + svg_document->end_glyph_id = doc_end_glyph_id; + + svg_document->transform.xx = 0x10000; + svg_document->transform.xy = 0; + svg_document->transform.yx = 0; + svg_document->transform.yy = 0x10000; + + svg_document->delta.x = 0; + svg_document->delta.y = 0; + + FT_TRACE5(( "start_glyph_id: %d\n", doc_start_glyph_id )); + FT_TRACE5(( "end_glyph_id: %d\n", doc_end_glyph_id )); + FT_TRACE5(( "svg_document:\n" )); + FT_TRACE5(( " %.*s\n", (FT_UInt)doc_length, doc )); + + glyph->other = svg_document; + + Exit: + return error; + } + +#else /* !FT_CONFIG_OPTION_SVG */ + + /* ANSI C doesn't like empty source files */ + typedef int tt_svg_dummy_; + +#endif /* !FT_CONFIG_OPTION_SVG */ + + +/* END */ diff --git a/3rdparty/freetype-2.13.2/src/sfnt/ttsvg.h b/3rdparty/freetype-2.13.2/src/sfnt/ttsvg.h new file mode 100644 index 000000000..3f32321de --- /dev/null +++ b/3rdparty/freetype-2.13.2/src/sfnt/ttsvg.h @@ -0,0 +1,43 @@ +/**************************************************************************** + * + * ttsvg.h + * + * OpenType SVG Color (specification). + * + * Copyright (C) 2022-2023 by + * David Turner, Robert Wilhelm, Werner Lemberg, and Moazin Khatti. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + +#ifndef TTSVG_H_ +#define TTSVG_H_ + +#include +#include + + +FT_BEGIN_HEADER + + FT_LOCAL( FT_Error ) + tt_face_load_svg( TT_Face face, + FT_Stream stream ); + + FT_LOCAL( void ) + tt_face_free_svg( TT_Face face ); + + FT_LOCAL( FT_Error ) + tt_face_load_svg_doc( FT_GlyphSlot glyph, + FT_UInt glyph_index ); + +FT_END_HEADER + +#endif /* TTSVG_H_ */ + + +/* END */ diff --git a/src/font/freetype-2.10.2/src/sfnt/woff2tags.c b/3rdparty/freetype-2.13.2/src/sfnt/woff2tags.c similarity index 91% rename from src/font/freetype-2.10.2/src/sfnt/woff2tags.c rename to 3rdparty/freetype-2.13.2/src/sfnt/woff2tags.c index 246f7fa06..eeedd9906 100644 --- a/src/font/freetype-2.10.2/src/sfnt/woff2tags.c +++ b/3rdparty/freetype-2.13.2/src/sfnt/woff2tags.c @@ -4,7 +4,7 @@ * * WOFF2 Font table tags (base). * - * Copyright (C) 2019-2020 by + * Copyright (C) 2019-2023 by * Nikhil Ramakrishnan, David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,9 +16,11 @@ */ -#include -#include FT_TRUETYPE_TAGS_H +#include +#ifdef FT_CONFIG_OPTION_USE_BROTLI + +#include "woff2tags.h" /* * Return tag from index in the order given in WOFF2 specification. @@ -29,10 +31,10 @@ * * for details. */ - FT_LOCAL_DEF( FT_ULong ) + FT_LOCAL_DEF( FT_Tag ) woff2_known_tags( FT_Byte index ) { - const FT_ULong known_tags[63] = + static const FT_Tag known_tags[63] = { FT_MAKE_TAG('c', 'm', 'a', 'p'), /* 0 */ FT_MAKE_TAG('h', 'e', 'a', 'd'), /* 1 */ @@ -106,5 +108,12 @@ return known_tags[index]; } +#else /* !FT_CONFIG_OPTION_USE_BROTLI */ + + /* ANSI C doesn't like empty source files */ + typedef int woff2tags_dummy_; + +#endif /* !FT_CONFIG_OPTION_USE_BROTLI */ + /* END */ diff --git a/src/font/freetype-2.10.2/src/sfnt/woff2tags.h b/3rdparty/freetype-2.13.2/src/sfnt/woff2tags.h similarity index 74% rename from src/font/freetype-2.10.2/src/sfnt/woff2tags.h rename to 3rdparty/freetype-2.13.2/src/sfnt/woff2tags.h index 13d242e11..1201848e5 100644 --- a/src/font/freetype-2.10.2/src/sfnt/woff2tags.h +++ b/3rdparty/freetype-2.13.2/src/sfnt/woff2tags.h @@ -2,9 +2,9 @@ * * woff2tags.h * - * WOFFF2 Font table tags (specification). + * WOFF2 Font table tags (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 2019-2023 by * Nikhil Ramakrishnan, David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,16 +20,18 @@ #define WOFF2TAGS_H -#include -#include FT_INTERNAL_OBJECTS_H +#include +#include FT_BEGIN_HEADER +#ifdef FT_CONFIG_OPTION_USE_BROTLI - FT_LOCAL( FT_ULong ) + FT_LOCAL( FT_Tag ) woff2_known_tags( FT_Byte index ); +#endif FT_END_HEADER diff --git a/src/font/freetype-2.10.2/src/smooth/ftgrays.c b/3rdparty/freetype-2.13.2/src/smooth/ftgrays.c similarity index 69% rename from src/font/freetype-2.10.2/src/smooth/ftgrays.c rename to 3rdparty/freetype-2.13.2/src/smooth/ftgrays.c index 93538331a..0918272f8 100644 --- a/src/font/freetype-2.10.2/src/smooth/ftgrays.c +++ b/3rdparty/freetype-2.13.2/src/smooth/ftgrays.c @@ -4,7 +4,7 @@ * * A new `perfect' anti-aliasing renderer (body). * - * Copyright (C) 2000-2020 by + * Copyright (C) 2000-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -149,14 +149,10 @@ #define FT_INT_MAX INT_MAX #define FT_ULONG_MAX ULONG_MAX -#define ADD_LONG( a, b ) \ - (long)( (unsigned long)(a) + (unsigned long)(b) ) -#define SUB_LONG( a, b ) \ - (long)( (unsigned long)(a) - (unsigned long)(b) ) -#define MUL_LONG( a, b ) \ - (long)( (unsigned long)(a) * (unsigned long)(b) ) -#define NEG_LONG( a ) \ - (long)( -(unsigned long)(a) ) +#define ADD_INT( a, b ) \ + (int)( (unsigned int)(a) + (unsigned int)(b) ) + +#define FT_STATIC_BYTE_CAST( type, var ) (type)(unsigned char)(var) #define ft_memset memset @@ -168,10 +164,11 @@ typedef ptrdiff_t FT_PtrDist; -#define ErrRaster_Invalid_Mode -2 -#define ErrRaster_Invalid_Outline -1 -#define ErrRaster_Invalid_Argument -3 -#define ErrRaster_Memory_Overflow -4 +#define Smooth_Err_Ok 0 +#define Smooth_Err_Invalid_Outline -1 +#define Smooth_Err_Cannot_Render_Glyph -2 +#define Smooth_Err_Invalid_Argument -3 +#define Smooth_Err_Raster_Overflow -4 #define FT_BEGIN_HEADER #define FT_END_HEADER @@ -229,23 +226,26 @@ typedef ptrdiff_t FT_PtrDist; #define FT_ERROR( varformat ) FT_Message varformat #endif -#define FT_THROW( e ) \ - ( FT_Throw( FT_ERR_CAT( ErrRaster_, e ), \ - __LINE__, \ - __FILE__ ) | \ - FT_ERR_CAT( ErrRaster_, e ) ) +#define FT_THROW( e ) \ + ( FT_Throw( FT_ERR_CAT( Smooth_Err_, e ), \ + __LINE__, \ + __FILE__ ) | \ + FT_ERR_CAT( Smooth_Err_, e ) ) #else /* !FT_DEBUG_LEVEL_TRACE */ #define FT_TRACE5( x ) do { } while ( 0 ) /* nothing */ #define FT_TRACE7( x ) do { } while ( 0 ) /* nothing */ #define FT_ERROR( x ) do { } while ( 0 ) /* nothing */ -#define FT_THROW( e ) FT_ERR_CAT( ErrRaster_, e ) - +#define FT_THROW( e ) FT_ERR_CAT( Smooth_Err_, e ) #endif /* !FT_DEBUG_LEVEL_TRACE */ +#define FT_Trace_Enable() do { } while ( 0 ) /* nothing */ +#define FT_Trace_Disable() do { } while ( 0 ) /* nothing */ + + #define FT_DEFINE_OUTLINE_FUNCS( class_, \ move_to_, line_to_, \ conic_to_, cubic_to_, \ @@ -279,18 +279,15 @@ typedef ptrdiff_t FT_PtrDist; #include +#include FT_CONFIG_CONFIG_H #include "ftgrays.h" -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_CALC_H -#include FT_OUTLINE_H +#include +#include +#include +#include #include "ftsmerrs.h" -#define Smooth_Err_Invalid_Mode Smooth_Err_Cannot_Render_Glyph -#define Smooth_Err_Memory_Overflow Smooth_Err_Out_Of_Memory -#define ErrRaster_Memory_Overflow Smooth_Err_Out_Of_Memory - #endif /* !STANDALONE_ */ @@ -336,7 +333,9 @@ typedef ptrdiff_t FT_PtrDist; #define PIXEL_BITS 8 #define ONE_PIXEL ( 1 << PIXEL_BITS ) +#undef TRUNC #define TRUNC( x ) (TCoord)( (x) >> PIXEL_BITS ) +#undef FRACT #define FRACT( x ) (TCoord)( (x) & ( ONE_PIXEL - 1 ) ) #if PIXEL_BITS >= 6 @@ -363,7 +362,7 @@ typedef ptrdiff_t FT_PtrDist; } \ FT_END_STMNT -#ifdef __arm__ +#if defined( __GNUC__ ) && __GNUC__ < 7 && defined( __arm__ ) /* Work around a bug specific to GCC which make the compiler fail to */ /* optimize a division and modulo operation on the same parameters */ /* into a single call to `__aeabi_idivmod'. See */ @@ -383,14 +382,58 @@ typedef ptrdiff_t FT_PtrDist; #endif /* __arm__ */ - /* These macros speed up repetitive divisions by replacing them */ - /* with multiplications and right shifts. */ -#define FT_UDIVPREP( c, b ) \ - long b ## _r = c ? (long)( FT_ULONG_MAX >> PIXEL_BITS ) / ( b ) \ - : 0 -#define FT_UDIV( a, b ) \ - (TCoord)( ( (unsigned long)( a ) * (unsigned long)( b ## _r ) ) >> \ - ( sizeof( long ) * FT_CHAR_BIT - PIXEL_BITS ) ) + /* Calculating coverages for a slanted line requires a division each */ + /* time the line crosses from cell to cell. These macros speed up */ + /* the repetitive divisions by replacing them with multiplications */ + /* and right shifts so that at most two divisions are performed for */ + /* each slanted line. Nevertheless, these divisions are noticeable */ + /* in the overall performance because flattened curves produce a */ + /* very large number of slanted lines. */ + /* */ + /* The division results here are always within ONE_PIXEL. Therefore */ + /* the shift magnitude should be at least PIXEL_BITS wider than the */ + /* divisors to provide sufficient accuracy of the multiply-shift. */ + /* It should not exceed (64 - PIXEL_BITS) to prevent overflowing and */ + /* leave enough room for 64-bit unsigned multiplication however. */ +#define FT_UDIVPREP( c, b ) \ + FT_Int64 b ## _r = c ? (FT_Int64)0xFFFFFFFF / ( b ) : 0 +#define FT_UDIV( a, b ) \ + (TCoord)( ( (FT_UInt64)( a ) * (FT_UInt64)( b ## _r ) ) >> 32 ) + + + /* Scale area and apply fill rule to calculate the coverage byte. */ + /* The top fill bit is used for the non-zero rule. The eighth */ + /* fill bit is used for the even-odd rule. The higher coverage */ + /* bytes are either clamped for the non-zero-rule or discarded */ + /* later for the even-odd rule. */ +#define FT_FILL_RULE( coverage, area, fill ) \ + FT_BEGIN_STMNT \ + coverage = (int)( area >> ( PIXEL_BITS * 2 + 1 - 8 ) ); \ + if ( coverage & fill ) \ + coverage = ~coverage; \ + if ( coverage > 255 && fill & INT_MIN ) \ + coverage = 255; \ + FT_END_STMNT + + + /* It is faster to write small spans byte-by-byte than calling */ + /* `memset'. This is mainly due to the cost of the function call. */ +#define FT_GRAY_SET( d, s, count ) \ + FT_BEGIN_STMNT \ + unsigned char* q = d; \ + switch ( count ) \ + { \ + case 7: *q++ = (unsigned char)s; FALL_THROUGH; \ + case 6: *q++ = (unsigned char)s; FALL_THROUGH; \ + case 5: *q++ = (unsigned char)s; FALL_THROUGH; \ + case 4: *q++ = (unsigned char)s; FALL_THROUGH; \ + case 3: *q++ = (unsigned char)s; FALL_THROUGH; \ + case 2: *q++ = (unsigned char)s; FALL_THROUGH; \ + case 1: *q = (unsigned char)s; FALL_THROUGH; \ + case 0: break; \ + default: FT_MEM_SET( d, s, count ); \ + } \ + FT_END_STMNT /************************************************************************** @@ -433,7 +476,7 @@ typedef ptrdiff_t FT_PtrDist; #endif /* FT_Span buffer size for direct rendering only */ -#define FT_MAX_GRAY_SPANS 10 +#define FT_MAX_GRAY_SPANS 16 #if defined( _MSC_VER ) /* Visual C++ (and Intel C++) */ @@ -448,28 +491,24 @@ typedef ptrdiff_t FT_PtrDist; { ft_jmp_buf jump_buffer; - TCoord ex, ey; - TCoord min_ex, max_ex; + TCoord min_ex, max_ex; /* min and max integer pixel coordinates */ TCoord min_ey, max_ey; + TCoord count_ey; /* same as (max_ey - min_ey) */ - TArea area; - TCoord cover; - int invalid; + PCell cell; /* current cell */ + PCell cell_free; /* call allocation next free slot */ + PCell cell_null; /* last cell, used as dumpster and limit */ - PCell* ycells; - PCell cells; - FT_PtrDist max_cells; - FT_PtrDist num_cells; + PCell* ycells; /* array of cell linked-lists; one per */ + /* vertical coordinate in the current band */ - TPos x, y; + TPos x, y; /* last point position */ - FT_Outline outline; - TPixmap target; + FT_Outline outline; /* input outline */ + TPixmap target; /* target pixmap */ FT_Raster_Span_Func render_span; void* render_span_data; - FT_Span spans[FT_MAX_GRAY_SPANS]; - int num_spans; } gray_TWorker, *gray_PWorker; @@ -477,17 +516,25 @@ typedef ptrdiff_t FT_PtrDist; #pragma warning( pop ) #endif - #ifndef FT_STATIC_RASTER #define ras (*worker) #else static gray_TWorker ras; #endif + /* The |x| value of the null cell. Must be the largest possible */ + /* integer value stored in a `TCell.x` field. */ +#define CELL_MAX_X_VALUE INT_MAX + + +#define FT_INTEGRATE( ras, a, b ) \ + ras.cell->cover = ADD_INT( ras.cell->cover, a ), \ + ras.cell->area = ADD_INT( ras.cell->area, (a) * (TArea)(b) ) + typedef struct gray_TRaster_ { - void* memory; + void* memory; } gray_TRaster, *gray_PRaster; @@ -509,7 +556,7 @@ typedef ptrdiff_t FT_PtrDist; printf( "%3d:", y ); - for ( ; cell != NULL; cell = cell->next ) + for ( ; cell != ras.cell_null; cell = cell->next ) printf( " (%3d, c:%4d, a:%6d)", cell->x, cell->cover, cell->area ); printf( "\n" ); @@ -521,81 +568,67 @@ typedef ptrdiff_t FT_PtrDist; /************************************************************************** * - * Record the current cell in the linked list. + * Set the current cell to a new position. */ static void - gray_record_cell( RAS_ARG ) + gray_set_cell( RAS_ARG_ TCoord ex, + TCoord ey ) { - PCell *pcell, cell; - TCoord x = ras.ex; - + /* Move the cell pointer to a new position in the linked list. We use */ + /* a dumpster null cell for everything outside of the clipping region */ + /* during the render phase. This means that: */ + /* */ + /* . the new vertical position must be within min_ey..max_ey-1. */ + /* . the new horizontal position must be strictly less than max_ex */ + /* */ + /* Note that if a cell is to the left of the clipping region, it is */ + /* actually set to the (min_ex-1) horizontal position. */ - pcell = &ras.ycells[ras.ey - ras.min_ey]; - while ( ( cell = *pcell ) ) - { - if ( cell->x > x ) - break; + TCoord ey_index = ey - ras.min_ey; - if ( cell->x == x ) - goto Found; - pcell = &cell->next; - } + if ( ey_index < 0 || ey_index >= ras.count_ey || ex >= ras.max_ex ) + ras.cell = ras.cell_null; + else + { + PCell* pcell = ras.ycells + ey_index; + PCell cell; - if ( ras.num_cells >= ras.max_cells ) - ft_longjmp( ras.jump_buffer, 1 ); - /* insert new cell */ - cell = ras.cells + ras.num_cells++; - cell->x = x; - cell->area = ras.area; - cell->cover = ras.cover; + ex = FT_MAX( ex, ras.min_ex - 1 ); - cell->next = *pcell; - *pcell = cell; + while ( 1 ) + { + cell = *pcell; - return; + if ( cell->x > ex ) + break; - Found: - /* update old cell */ - cell->area += ras.area; - cell->cover += ras.cover; - } + if ( cell->x == ex ) + goto Found; + pcell = &cell->next; + } - /************************************************************************** - * - * Set the current cell to a new position. - */ - static void - gray_set_cell( RAS_ARG_ TCoord ex, - TCoord ey ) - { - /* Move the cell pointer to a new position. We set the `invalid' */ - /* flag to indicate that the cell isn't part of those we're interested */ - /* in during the render phase. This means that: */ - /* */ - /* . the new vertical position must be within min_ey..max_ey-1. */ - /* . the new horizontal position must be strictly less than max_ex */ - /* */ - /* Note that if a cell is to the left of the clipping region, it is */ - /* actually set to the (min_ex-1) horizontal position. */ + /* insert new cell */ + cell = ras.cell_free++; + if ( cell >= ras.cell_null ) + ft_longjmp( ras.jump_buffer, 1 ); - /* record the current one if it is valid and substantial */ - if ( !ras.invalid && ( ras.area || ras.cover ) ) - gray_record_cell( RAS_VAR ); + cell->x = ex; + cell->area = 0; + cell->cover = 0; - ras.area = 0; - ras.cover = 0; - ras.ex = FT_MAX( ex, ras.min_ex - 1 ); - ras.ey = ey; + cell->next = *pcell; + *pcell = cell; - ras.invalid = ( ey >= ras.max_ey || ey < ras.min_ey || - ex >= ras.max_ex ); + Found: + ras.cell = cell; + } } -#ifndef FT_LONG64 +#ifndef FT_INT64 /************************************************************************** * @@ -623,8 +656,8 @@ typedef ptrdiff_t FT_PtrDist; return; } - fx1 = FRACT( x1 ); - fx2 = FRACT( x2 ); + fx1 = FRACT( x1 ); + fx2 = FRACT( x2 ); /* everything is located in a single cell. That is easy! */ /* */ @@ -656,10 +689,9 @@ typedef ptrdiff_t FT_PtrDist; /* XXX: y-delta and x-delta below should be related. */ FT_DIV_MOD( TCoord, p, dx, delta, mod ); - ras.area += (TArea)( ( fx1 + first ) * delta ); - ras.cover += delta; - y1 += delta; - ex1 += incr; + FT_INTEGRATE( ras, delta, fx1 + first ); + y1 += delta; + ex1 += incr; gray_set_cell( RAS_VAR_ ex1, ey ); if ( ex1 != ex2 ) @@ -680,10 +712,9 @@ typedef ptrdiff_t FT_PtrDist; delta++; } - ras.area += (TArea)( ONE_PIXEL * delta ); - ras.cover += delta; - y1 += delta; - ex1 += incr; + FT_INTEGRATE( ras, delta, ONE_PIXEL ); + y1 += delta; + ex1 += incr; gray_set_cell( RAS_VAR_ ex1, ey ); } while ( ex1 != ex2 ); } @@ -691,10 +722,7 @@ typedef ptrdiff_t FT_PtrDist; fx1 = ONE_PIXEL - first; End: - dy = y2 - y1; - - ras.area += (TArea)( ( fx1 + fx2 ) * dy ); - ras.cover += dy; + FT_INTEGRATE( ras, y2 - y1, fx1 + fx2 ); } @@ -737,7 +765,6 @@ typedef ptrdiff_t FT_PtrDist; { TCoord ex = TRUNC( ras.x ); TCoord two_fx = FRACT( ras.x ) << 1; - TArea area; if ( dy > 0) @@ -751,27 +778,23 @@ typedef ptrdiff_t FT_PtrDist; incr = -1; } - delta = first - fy1; - ras.area += (TArea)two_fx * delta; - ras.cover += delta; - ey1 += incr; + delta = first - fy1; + FT_INTEGRATE( ras, delta, two_fx); + ey1 += incr; gray_set_cell( RAS_VAR_ ex, ey1 ); delta = first + first - ONE_PIXEL; - area = (TArea)two_fx * delta; while ( ey1 != ey2 ) { - ras.area += area; - ras.cover += delta; - ey1 += incr; + FT_INTEGRATE( ras, delta, two_fx); + ey1 += incr; gray_set_cell( RAS_VAR_ ex, ey1 ); } - delta = fy2 - ONE_PIXEL + first; - ras.area += (TArea)two_fx * delta; - ras.cover += delta; + delta = fy2 - ONE_PIXEL + first; + FT_INTEGRATE( ras, delta, two_fx); goto End; } @@ -884,8 +907,7 @@ typedef ptrdiff_t FT_PtrDist; do { fy2 = ONE_PIXEL; - ras.cover += ( fy2 - fy1 ); - ras.area += ( fy2 - fy1 ) * fx1 * 2; + FT_INTEGRATE( ras, fy2 - fy1, fx1 * 2 ); fy1 = 0; ey1++; gray_set_cell( RAS_VAR_ ex1, ey1 ); @@ -894,8 +916,7 @@ typedef ptrdiff_t FT_PtrDist; do { fy2 = 0; - ras.cover += ( fy2 - fy1 ); - ras.area += ( fy2 - fy1 ) * fx1 * 2; + FT_INTEGRATE( ras, fy2 - fy1, fx1 * 2 ); fy1 = ONE_PIXEL; ey1--; gray_set_cell( RAS_VAR_ ex1, ey1 ); @@ -903,7 +924,7 @@ typedef ptrdiff_t FT_PtrDist; } else /* any other line */ { - TPos prod = dx * (TPos)fy1 - dy * (TPos)fx1; + FT_Int64 prod = dx * (FT_Int64)fy1 - dy * (FT_Int64)fx1; FT_UDIVPREP( ex1 != ex2, dx ); FT_UDIVPREP( ey1 != ey2, dy ); @@ -913,72 +934,309 @@ typedef ptrdiff_t FT_PtrDist; /* also easily updated when moving from one cell to the next. */ do { - if ( prod <= 0 && - prod - dx * ONE_PIXEL > 0 ) /* left */ + if ( prod - dx * ONE_PIXEL > 0 && + prod <= 0 ) /* left */ { fx2 = 0; fy2 = FT_UDIV( -prod, -dx ); prod -= dy * ONE_PIXEL; - ras.cover += ( fy2 - fy1 ); - ras.area += ( fy2 - fy1 ) * ( fx1 + fx2 ); + FT_INTEGRATE( ras, fy2 - fy1, fx1 + fx2 ); fx1 = ONE_PIXEL; fy1 = fy2; ex1--; } - else if ( prod - dx * ONE_PIXEL <= 0 && - prod - dx * ONE_PIXEL + dy * ONE_PIXEL > 0 ) /* up */ + else if ( prod - dx * ONE_PIXEL + dy * ONE_PIXEL > 0 && + prod - dx * ONE_PIXEL <= 0 ) /* up */ { prod -= dx * ONE_PIXEL; fx2 = FT_UDIV( -prod, dy ); fy2 = ONE_PIXEL; - ras.cover += ( fy2 - fy1 ); - ras.area += ( fy2 - fy1 ) * ( fx1 + fx2 ); + FT_INTEGRATE( ras, fy2 - fy1, fx1 + fx2 ); fx1 = fx2; fy1 = 0; ey1++; } - else if ( prod - dx * ONE_PIXEL + dy * ONE_PIXEL <= 0 && - prod + dy * ONE_PIXEL >= 0 ) /* right */ + else if ( prod + dy * ONE_PIXEL >= 0 && + prod - dx * ONE_PIXEL + dy * ONE_PIXEL <= 0 ) /* right */ { prod += dy * ONE_PIXEL; fx2 = ONE_PIXEL; fy2 = FT_UDIV( prod, dx ); - ras.cover += ( fy2 - fy1 ); - ras.area += ( fy2 - fy1 ) * ( fx1 + fx2 ); + FT_INTEGRATE( ras, fy2 - fy1, fx1 + fx2 ); fx1 = 0; fy1 = fy2; ex1++; } - else /* ( prod + dy * ONE_PIXEL < 0 && - prod > 0 ) down */ + else /* ( prod > 0 && + prod + dy * ONE_PIXEL < 0 ) down */ { fx2 = FT_UDIV( prod, -dy ); fy2 = 0; prod += dx * ONE_PIXEL; - ras.cover += ( fy2 - fy1 ); - ras.area += ( fy2 - fy1 ) * ( fx1 + fx2 ); + FT_INTEGRATE( ras, fy2 - fy1, fx1 + fx2 ); fx1 = fx2; fy1 = ONE_PIXEL; ey1--; } gray_set_cell( RAS_VAR_ ex1, ey1 ); + } while ( ex1 != ex2 || ey1 != ey2 ); } fx2 = FRACT( to_x ); fy2 = FRACT( to_y ); - ras.cover += ( fy2 - fy1 ); - ras.area += ( fy2 - fy1 ) * ( fx1 + fx2 ); + FT_INTEGRATE( ras, fy2 - fy1, fx1 + fx2 ); End: - ras.x = to_x; - ras.y = to_y; + ras.x = to_x; + ras.y = to_y; } #endif + /* + * Benchmarking shows that using DDA to flatten the quadratic Bézier arcs + * is slightly faster in the following cases: + * + * - When the host CPU is 64-bit. + * - When SSE2 SIMD registers and instructions are available (even on + * x86). + * + * For other cases, using binary splits is actually slightly faster. + */ +#if ( defined( __SSE2__ ) || \ + defined( __x86_64__ ) || \ + defined( _M_AMD64 ) || \ + ( defined( _M_IX86_FP ) && _M_IX86_FP >= 2 ) ) && \ + !defined( __VMS ) +# define FT_SSE2 1 +#else +# define FT_SSE2 0 +#endif + +#if FT_SSE2 || \ + defined( __aarch64__ ) || \ + defined( _M_ARM64 ) +# define BEZIER_USE_DDA 1 +#else +# define BEZIER_USE_DDA 0 +#endif + + /* + * For now, the code that depends on `BEZIER_USE_DDA` requires `FT_Int64` + * to be defined. If `FT_INT64` is not defined, meaning there is no + * 64-bit type available, disable it to avoid compilation errors. See for + * example https://gitlab.freedesktop.org/freetype/freetype/-/issues/1071. + */ +#if !defined( FT_INT64 ) +# undef BEZIER_USE_DDA +# define BEZIER_USE_DDA 0 +#endif + +#if BEZIER_USE_DDA + +#if FT_SSE2 +# include +#endif + +#define LEFT_SHIFT( a, b ) (FT_Int64)( (FT_UInt64)(a) << (b) ) + + + static void + gray_render_conic( RAS_ARG_ const FT_Vector* control, + const FT_Vector* to ) + { + FT_Vector p0, p1, p2; + TPos ax, ay, bx, by, dx, dy; + int shift; + + FT_Int64 rx, ry; + FT_Int64 qx, qy; + FT_Int64 px, py; + + FT_UInt count; + + + p0.x = ras.x; + p0.y = ras.y; + p1.x = UPSCALE( control->x ); + p1.y = UPSCALE( control->y ); + p2.x = UPSCALE( to->x ); + p2.y = UPSCALE( to->y ); + + /* short-cut the arc that crosses the current band */ + if ( ( TRUNC( p0.y ) >= ras.max_ey && + TRUNC( p1.y ) >= ras.max_ey && + TRUNC( p2.y ) >= ras.max_ey ) || + ( TRUNC( p0.y ) < ras.min_ey && + TRUNC( p1.y ) < ras.min_ey && + TRUNC( p2.y ) < ras.min_ey ) ) + { + ras.x = p2.x; + ras.y = p2.y; + return; + } + + bx = p1.x - p0.x; + by = p1.y - p0.y; + ax = p2.x - p1.x - bx; /* p0.x + p2.x - 2 * p1.x */ + ay = p2.y - p1.y - by; /* p0.y + p2.y - 2 * p1.y */ + + dx = FT_ABS( ax ); + dy = FT_ABS( ay ); + if ( dx < dy ) + dx = dy; + + if ( dx <= ONE_PIXEL / 4 ) + { + gray_render_line( RAS_VAR_ p2.x, p2.y ); + return; + } + + /* We can calculate the number of necessary bisections because */ + /* each bisection predictably reduces deviation exactly 4-fold. */ + /* Even 32-bit deviation would vanish after 16 bisections. */ + shift = 0; + do + { + dx >>= 2; + shift += 1; + + } while ( dx > ONE_PIXEL / 4 ); + + /* + * The (P0,P1,P2) arc equation, for t in [0,1] range: + * + * P(t) = P0*(1-t)^2 + P1*2*t*(1-t) + P2*t^2 + * + * P(t) = P0 + 2*(P1-P0)*t + (P0+P2-2*P1)*t^2 + * = P0 + 2*B*t + A*t^2 + * + * for A = P0 + P2 - 2*P1 + * and B = P1 - P0 + * + * Let's consider the difference when advancing by a small + * parameter h: + * + * Q(h,t) = P(t+h) - P(t) = 2*B*h + A*h^2 + 2*A*h*t + * + * And then its own difference: + * + * R(h,t) = Q(h,t+h) - Q(h,t) = 2*A*h*h = R (constant) + * + * Since R is always a constant, it is possible to compute + * successive positions with: + * + * P = P0 + * Q = Q(h,0) = 2*B*h + A*h*h + * R = 2*A*h*h + * + * loop: + * P += Q + * Q += R + * EMIT(P) + * + * To ensure accurate results, perform computations on 64-bit + * values, after scaling them by 2^32. + * + * h = 1 / 2^N + * + * R << 32 = 2 * A << (32 - N - N) + * = A << (33 - 2*N) + * + * Q << 32 = (2 * B << (32 - N)) + (A << (32 - N - N)) + * = (B << (33 - N)) + (A << (32 - 2*N)) + */ + +#if FT_SSE2 + /* Experience shows that for small shift values, */ + /* SSE2 is actually slower. */ + if ( shift > 2 ) + { + union + { + struct { FT_Int64 ax, ay, bx, by; } i; + struct { __m128i a, b; } vec; + + } u; + + union + { + struct { FT_Int32 px_lo, px_hi, py_lo, py_hi; } i; + __m128i vec; + + } v; + + __m128i a, b; + __m128i r, q, q2; + __m128i p; + + + u.i.ax = ax; + u.i.ay = ay; + u.i.bx = bx; + u.i.by = by; + + a = _mm_load_si128( &u.vec.a ); + b = _mm_load_si128( &u.vec.b ); + + r = _mm_slli_epi64( a, 33 - 2 * shift ); + q = _mm_slli_epi64( b, 33 - shift ); + q2 = _mm_slli_epi64( a, 32 - 2 * shift ); + + q = _mm_add_epi64( q2, q ); + + v.i.px_lo = 0; + v.i.px_hi = p0.x; + v.i.py_lo = 0; + v.i.py_hi = p0.y; + + p = _mm_load_si128( &v.vec ); + + for ( count = 1U << shift; count > 0; count-- ) + { + p = _mm_add_epi64( p, q ); + q = _mm_add_epi64( q, r ); + + _mm_store_si128( &v.vec, p ); + + gray_render_line( RAS_VAR_ v.i.px_hi, v.i.py_hi ); + } + + return; + } +#endif /* FT_SSE2 */ + + rx = LEFT_SHIFT( ax, 33 - 2 * shift ); + ry = LEFT_SHIFT( ay, 33 - 2 * shift ); + + qx = LEFT_SHIFT( bx, 33 - shift ) + LEFT_SHIFT( ax, 32 - 2 * shift ); + qy = LEFT_SHIFT( by, 33 - shift ) + LEFT_SHIFT( ay, 32 - 2 * shift ); + + px = LEFT_SHIFT( p0.x, 32 ); + py = LEFT_SHIFT( p0.y, 32 ); + + for ( count = 1U << shift; count > 0; count-- ) + { + px += qx; + py += qy; + qx += rx; + qy += ry; + + gray_render_line( RAS_VAR_ (FT_Pos)( px >> 32 ), + (FT_Pos)( py >> 32 ) ); + } + } + +#else /* !BEZIER_USE_DDA */ + + /* + * Note that multiple attempts to speed up the function below + * with SSE2 intrinsics, using various data layouts, have turned + * out to be slower than the non-SIMD code below. + */ static void gray_split_conic( FT_Vector* base ) { @@ -1008,7 +1266,7 @@ typedef ptrdiff_t FT_PtrDist; FT_Vector bez_stack[16 * 2 + 1]; /* enough to accommodate bisections */ FT_Vector* arc = bez_stack; TPos dx, dy; - int draw, split; + int draw; arc[0].x = UPSCALE( to->x ); @@ -1051,7 +1309,9 @@ typedef ptrdiff_t FT_PtrDist; /* many times as there are trailing zeros in the counter. */ do { - split = draw & ( -draw ); /* isolate the rightmost 1-bit */ + int split = draw & ( -draw ); /* isolate the rightmost 1-bit */ + + while ( ( split >>= 1 ) ) { gray_split_conic( arc ); @@ -1064,7 +1324,17 @@ typedef ptrdiff_t FT_PtrDist; } while ( --draw ); } +#endif /* !BEZIER_USE_DDA */ + + /* + * For cubic Bézier, binary splits are still faster than DDA + * because the splits are adaptive to how quickly each sub-arc + * approaches their chord trisection points. + * + * It might be useful to experiment with SSE2 to speed up + * `gray_split_cubic`, though. + */ static void gray_split_cubic( FT_Vector* base ) { @@ -1158,8 +1428,10 @@ typedef ptrdiff_t FT_PtrDist; static int gray_move_to( const FT_Vector* to, - gray_PWorker worker ) + void* worker_ ) /* gray_PWorker */ { + gray_PWorker worker = (gray_PWorker)worker_; + TPos x, y; @@ -1177,8 +1449,11 @@ typedef ptrdiff_t FT_PtrDist; static int gray_line_to( const FT_Vector* to, - gray_PWorker worker ) + void* worker_ ) /* gray_PWorker */ { + gray_PWorker worker = (gray_PWorker)worker_; + + gray_render_line( RAS_VAR_ UPSCALE( to->x ), UPSCALE( to->y ) ); return 0; } @@ -1187,8 +1462,11 @@ typedef ptrdiff_t FT_PtrDist; static int gray_conic_to( const FT_Vector* control, const FT_Vector* to, - gray_PWorker worker ) + void* worker_ ) /* gray_PWorker */ { + gray_PWorker worker = (gray_PWorker)worker_; + + gray_render_conic( RAS_VAR_ control, to ); return 0; } @@ -1198,133 +1476,144 @@ typedef ptrdiff_t FT_PtrDist; gray_cubic_to( const FT_Vector* control1, const FT_Vector* control2, const FT_Vector* to, - gray_PWorker worker ) + void* worker_ ) /* gray_PWorker */ { + gray_PWorker worker = (gray_PWorker)worker_; + + gray_render_cubic( RAS_VAR_ control1, control2, to ); return 0; } static void - gray_hline( RAS_ARG_ TCoord x, - TCoord y, - TArea coverage, - TCoord acount ) + gray_sweep( RAS_ARG ) { - /* scale the coverage from 0..(ONE_PIXEL*ONE_PIXEL*2) to 0..256 */ - coverage >>= PIXEL_BITS * 2 + 1 - 8; + int fill = ( ras.outline.flags & FT_OUTLINE_EVEN_ODD_FILL ) ? 0x100 + : INT_MIN; + int coverage; + int y; - /* compute the line's coverage depending on the outline fill rule */ - if ( ras.outline.flags & FT_OUTLINE_EVEN_ODD_FILL ) - { - coverage &= 511; - if ( coverage >= 256 ) - coverage = 511 - coverage; - } - else /* default non-zero winding rule */ + for ( y = ras.min_ey; y < ras.max_ey; y++ ) { - if ( coverage < 0 ) - coverage = ~coverage; /* the same as -coverage - 1 */ + PCell cell = ras.ycells[y - ras.min_ey]; + TCoord x = ras.min_ex; + TArea cover = 0; - if ( coverage >= 256 ) - coverage = 255; - } + unsigned char* line = ras.target.origin - ras.target.pitch * y; - if ( ras.num_spans >= 0 ) /* for FT_RASTER_FLAG_DIRECT only */ - { - FT_Span* span = ras.spans + ras.num_spans++; + for ( ; cell != ras.cell_null; cell = cell->next ) + { + TArea area; - span->x = (short)x; - span->len = (unsigned short)acount; - span->coverage = (unsigned char)coverage; - if ( ras.num_spans == FT_MAX_GRAY_SPANS ) - { - /* flush the span buffer and reset the count */ - ras.render_span( y, ras.num_spans, ras.spans, ras.render_span_data ); - ras.num_spans = 0; - } - } - else - { - unsigned char* q = ras.target.origin - ras.target.pitch * y + x; - unsigned char c = (unsigned char)coverage; + if ( cover != 0 && cell->x > x ) + { + FT_FILL_RULE( coverage, cover, fill ); + FT_GRAY_SET( line + x, coverage, cell->x - x ); + } + + cover += (TArea)cell->cover * ( ONE_PIXEL * 2 ); + area = cover - cell->area; + if ( area != 0 && cell->x >= ras.min_ex ) + { + FT_FILL_RULE( coverage, area, fill ); + line[cell->x] = (unsigned char)coverage; + } + + x = cell->x + 1; + } - /* For small-spans it is faster to do it by ourselves than - * calling `memset'. This is mainly due to the cost of the - * function call. - */ - switch ( acount ) + if ( cover != 0 ) /* only if cropped */ { - case 7: - *q++ = c; - /* fall through */ - case 6: - *q++ = c; - /* fall through */ - case 5: - *q++ = c; - /* fall through */ - case 4: - *q++ = c; - /* fall through */ - case 3: - *q++ = c; - /* fall through */ - case 2: - *q++ = c; - /* fall through */ - case 1: - *q = c; - /* fall through */ - case 0: - break; - default: - FT_MEM_SET( q, c, acount ); + FT_FILL_RULE( coverage, cover, fill ); + FT_GRAY_SET( line + x, coverage, ras.max_ex - x ); } } } static void - gray_sweep( RAS_ARG ) + gray_sweep_direct( RAS_ARG ) { + int fill = ( ras.outline.flags & FT_OUTLINE_EVEN_ODD_FILL ) ? 0x100 + : INT_MIN; + int coverage; int y; + FT_Span span[FT_MAX_GRAY_SPANS]; + int n = 0; + for ( y = ras.min_ey; y < ras.max_ey; y++ ) { PCell cell = ras.ycells[y - ras.min_ey]; TCoord x = ras.min_ex; TArea cover = 0; - TArea area; - for ( ; cell != NULL; cell = cell->next ) + for ( ; cell != ras.cell_null; cell = cell->next ) { + TArea area; + + if ( cover != 0 && cell->x > x ) - gray_hline( RAS_VAR_ x, y, cover, cell->x - x ); + { + FT_FILL_RULE( coverage, cover, fill ); + + span[n].coverage = (unsigned char)coverage; + span[n].x = (short)x; + span[n].len = (unsigned short)( cell->x - x ); + + if ( ++n == FT_MAX_GRAY_SPANS ) + { + /* flush the span buffer and reset the count */ + ras.render_span( y, n, span, ras.render_span_data ); + n = 0; + } + } cover += (TArea)cell->cover * ( ONE_PIXEL * 2 ); area = cover - cell->area; if ( area != 0 && cell->x >= ras.min_ex ) - gray_hline( RAS_VAR_ cell->x, y, area, 1 ); + { + FT_FILL_RULE( coverage, area, fill ); + + span[n].coverage = (unsigned char)coverage; + span[n].x = (short)cell->x; + span[n].len = 1; + + if ( ++n == FT_MAX_GRAY_SPANS ) + { + /* flush the span buffer and reset the count */ + ras.render_span( y, n, span, ras.render_span_data ); + n = 0; + } + } x = cell->x + 1; } - if ( cover != 0 ) - gray_hline( RAS_VAR_ x, y, cover, ras.max_ex - x ); + if ( cover != 0 ) /* only if cropped */ + { + FT_FILL_RULE( coverage, cover, fill ); + + span[n].coverage = (unsigned char)coverage; + span[n].x = (short)x; + span[n].len = (unsigned short)( ras.max_ex - x ); + + ++n; + } - if ( ras.num_spans > 0 ) /* for FT_RASTER_FLAG_DIRECT only */ + if ( n ) { /* flush the span buffer and reset the count */ - ras.render_span( y, ras.num_spans, ras.spans, ras.render_span_data ); - ras.num_spans = 0; + ras.render_span( y, n, span, ras.render_span_data ); + n = 0; } } } @@ -1389,6 +1678,8 @@ typedef ptrdiff_t FT_PtrDist; int n; /* index of contour in outline */ int first; /* index of first point in contour */ + int last; /* index of last point in contour */ + char tag; /* current point's state */ int shift; @@ -1403,18 +1694,17 @@ typedef ptrdiff_t FT_PtrDist; shift = func_interface->shift; delta = func_interface->delta; - first = 0; + last = -1; for ( n = 0; n < outline->n_contours; n++ ) { - int last; /* index of last point in contour */ - - - FT_TRACE5(( "FT_Outline_Decompose: Outline %d\n", n )); + FT_TRACE5(( "FT_Outline_Decompose: Contour %d\n", n )); + first = last + 1; last = outline->contours[n]; - if ( last < 0 ) + if ( last < first ) goto Invalid_Outline; + limit = outline->points + last; v_start = outline->points[first]; @@ -1597,15 +1887,13 @@ typedef ptrdiff_t FT_PtrDist; v_start.x / 64.0, v_start.y / 64.0 )); error = func_interface->line_to( &v_start, user ); - Close: + Close: if ( error ) goto Exit; - - first = last + 1; } FT_TRACE5(( "FT_Outline_Decompose: Done\n", n )); - return 0; + return Smooth_Err_Ok; Exit: FT_TRACE5(( "FT_Outline_Decompose: Error 0x%x\n", error )); @@ -1632,10 +1920,10 @@ typedef ptrdiff_t FT_PtrDist; static int - gray_convert_glyph_inner( RAS_ARG, + gray_convert_glyph_inner( RAS_ARG_ int continued ) { - int error; + volatile int error; if ( ft_setjmp( ras.jump_buffer ) == 0 ) @@ -1646,18 +1934,15 @@ typedef ptrdiff_t FT_PtrDist; if ( continued ) FT_Trace_Enable(); - if ( !ras.invalid ) - gray_record_cell( RAS_VAR ); - - FT_TRACE7(( "band [%d..%d]: %d cell%s\n", + FT_TRACE7(( "band [%d..%d]: %td cell%s remaining/\n", ras.min_ey, ras.max_ey, - ras.num_cells, - ras.num_cells == 1 ? "" : "s" )); + ras.cell_null - ras.cell_free, + ras.cell_null - ras.cell_free == 1 ? "" : "s" )); } else { - error = FT_THROW( Memory_Overflow ); + error = FT_THROW( Raster_Overflow ); FT_TRACE7(( "band [%d..%d]: to be bisected\n", ras.min_ey, ras.max_ey )); @@ -1683,7 +1968,16 @@ typedef ptrdiff_t FT_PtrDist; int continued = 0; + /* Initialize the null cell at the end of the poll. */ + ras.cell_null = buffer + FT_MAX_GRAY_POOL - 1; + ras.cell_null->x = CELL_MAX_X_VALUE; + ras.cell_null->area = 0; + ras.cell_null->cover = 0; + ras.cell_null->next = NULL; + /* set up vertical bands */ + ras.ycells = (PCell*)buffer; + if ( height > n ) { /* two divisions rounded up */ @@ -1691,13 +1985,6 @@ typedef ptrdiff_t FT_PtrDist; height = ( height + n - 1 ) / n; } - /* memory management */ - n = ( height * sizeof ( PCell ) + sizeof ( TCell ) - 1 ) / sizeof ( TCell ); - - ras.cells = buffer + n; - ras.max_cells = (FT_PtrDist)( FT_MAX_GRAY_POOL - n ); - ras.ycells = (PCell*)buffer; - for ( y = yMin; y < yMax; ) { ras.min_ey = y; @@ -1711,27 +1998,37 @@ typedef ptrdiff_t FT_PtrDist; do { TCoord width = band[0] - band[1]; + TCoord w; int error; - FT_MEM_ZERO( ras.ycells, height * sizeof ( PCell ) ); + for ( w = 0; w < width; ++w ) + ras.ycells[w] = ras.cell_null; + + /* memory management: skip ycells */ + n = ( (size_t)width * sizeof ( PCell ) + sizeof ( TCell ) - 1 ) / + sizeof ( TCell ); - ras.num_cells = 0; - ras.invalid = 1; + ras.cell_free = buffer + n; + ras.cell = ras.cell_null; ras.min_ey = band[1]; ras.max_ey = band[0]; + ras.count_ey = width; - error = gray_convert_glyph_inner( RAS_VAR, continued ); + error = gray_convert_glyph_inner( RAS_VAR_ continued ); continued = 1; if ( !error ) { - gray_sweep( RAS_VAR ); + if ( ras.render_span ) /* for FT_RASTER_FLAG_DIRECT only */ + gray_sweep_direct( RAS_VAR ); + else + gray_sweep( RAS_VAR ); band--; continue; } - else if ( error != ErrRaster_Memory_Overflow ) - return 1; + else if ( error != Smooth_Err_Raster_Overflow ) + return error; /* render pool overflow; we will reduce the render band by half */ width >>= 1; @@ -1740,7 +2037,7 @@ typedef ptrdiff_t FT_PtrDist; if ( width == 0 ) { FT_TRACE7(( "gray_convert_glyph: rotten glyph\n" )); - return 1; + return FT_THROW( Raster_Overflow ); } band++; @@ -1749,7 +2046,7 @@ typedef ptrdiff_t FT_PtrDist; } while ( band >= bands ); } - return 0; + return Smooth_Err_Ok; } @@ -1770,14 +2067,14 @@ typedef ptrdiff_t FT_PtrDist; /* this version does not support monochrome rendering */ if ( !( params->flags & FT_RASTER_FLAG_AA ) ) - return FT_THROW( Invalid_Mode ); + return FT_THROW( Cannot_Render_Glyph ); if ( !outline ) return FT_THROW( Invalid_Outline ); /* return immediately if the outline is empty */ if ( outline->n_points == 0 || outline->n_contours <= 0 ) - return 0; + return Smooth_Err_Ok; if ( !outline->contours || !outline->points ) return FT_THROW( Invalid_Outline ); @@ -1791,11 +2088,10 @@ typedef ptrdiff_t FT_PtrDist; if ( params->flags & FT_RASTER_FLAG_DIRECT ) { if ( !params->gray_spans ) - return 0; + return Smooth_Err_Ok; ras.render_span = (FT_Raster_Span_Func)params->gray_spans; ras.render_span_data = params->user; - ras.num_spans = 0; ras.min_ex = params->clip_box.xMin; ras.min_ey = params->clip_box.yMin; @@ -1810,7 +2106,7 @@ typedef ptrdiff_t FT_PtrDist; /* nothing to do */ if ( !target_map->width || !target_map->rows ) - return 0; + return Smooth_Err_Ok; if ( !target_map->buffer ) return FT_THROW( Invalid_Argument ); @@ -1825,7 +2121,6 @@ typedef ptrdiff_t FT_PtrDist; ras.render_span = (FT_Raster_Span_Func)NULL; ras.render_span_data = NULL; - ras.num_spans = -1; /* invalid */ ras.min_ex = 0; ras.min_ey = 0; @@ -1835,7 +2130,7 @@ typedef ptrdiff_t FT_PtrDist; /* exit if nothing to do */ if ( ras.max_ex <= ras.min_ex || ras.max_ey <= ras.min_ey ) - return 0; + return Smooth_Err_Ok; return gray_convert_glyph( RAS_VAR ); } @@ -1872,19 +2167,20 @@ typedef ptrdiff_t FT_PtrDist; #else /* !STANDALONE_ */ static int - gray_raster_new( FT_Memory memory, - FT_Raster* araster ) + gray_raster_new( void* memory_, + FT_Raster* araster_ ) { + FT_Memory memory = (FT_Memory)memory_; + gray_PRaster* araster = (gray_PRaster*)araster_; + FT_Error error; gray_PRaster raster = NULL; - *araster = 0; - if ( !FT_ALLOC( raster, sizeof ( gray_TRaster ) ) ) - { + if ( !FT_NEW( raster ) ) raster->memory = memory; - *araster = (FT_Raster)raster; - } + + *araster = raster; return error; } diff --git a/src/font/freetype-2.10.2/src/smooth/ftgrays.h b/3rdparty/freetype-2.13.2/src/smooth/ftgrays.h similarity index 95% rename from src/font/freetype-2.10.2/src/smooth/ftgrays.h rename to 3rdparty/freetype-2.13.2/src/smooth/ftgrays.h index e10fd039a..a5001bf40 100644 --- a/src/font/freetype-2.10.2/src/smooth/ftgrays.h +++ b/3rdparty/freetype-2.13.2/src/smooth/ftgrays.h @@ -4,7 +4,7 @@ * * FreeType smooth renderer declaration * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -28,7 +28,7 @@ #include "ftimage.h" #else #include -#include FT_IMAGE_H +#include #endif diff --git a/src/font/freetype-2.10.2/src/smooth/ftsmerrs.h b/3rdparty/freetype-2.13.2/src/smooth/ftsmerrs.h similarity index 90% rename from src/font/freetype-2.10.2/src/smooth/ftsmerrs.h rename to 3rdparty/freetype-2.13.2/src/smooth/ftsmerrs.h index 3f8567b0f..f4ac93dc4 100644 --- a/src/font/freetype-2.10.2/src/smooth/ftsmerrs.h +++ b/3rdparty/freetype-2.13.2/src/smooth/ftsmerrs.h @@ -4,7 +4,7 @@ * * smooth renderer error codes (specification only). * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -26,7 +26,7 @@ #ifndef FTSMERRS_H_ #define FTSMERRS_H_ -#include FT_MODULE_ERRORS_H +#include #undef FTERRORS_H_ @@ -34,7 +34,7 @@ #define FT_ERR_PREFIX Smooth_Err_ #define FT_ERR_BASE FT_Mod_Err_Smooth -#include FT_ERRORS_H +#include #endif /* FTSMERRS_H_ */ diff --git a/3rdparty/freetype-2.13.2/src/smooth/ftsmooth.c b/3rdparty/freetype-2.13.2/src/smooth/ftsmooth.c new file mode 100644 index 000000000..9b0e8886c --- /dev/null +++ b/3rdparty/freetype-2.13.2/src/smooth/ftsmooth.c @@ -0,0 +1,605 @@ +/**************************************************************************** + * + * ftsmooth.c + * + * Anti-aliasing renderer interface (body). + * + * Copyright (C) 2000-2023 by + * David Turner, Robert Wilhelm, and Werner Lemberg. + * + * This file is part of the FreeType project, and may only be used, + * modified, and distributed under the terms of the FreeType project + * license, LICENSE.TXT. By continuing to use, modify, or distribute + * this file you indicate that you have read the license and + * understand and accept it fully. + * + */ + + +#include +#include +#include +#include "ftsmooth.h" +#include "ftgrays.h" + +#include "ftsmerrs.h" + + + /* sets render-specific mode */ + static FT_Error + ft_smooth_set_mode( FT_Renderer render, + FT_ULong mode_tag, + FT_Pointer data ) + { + /* we simply pass it to the raster */ + return render->clazz->raster_class->raster_set_mode( render->raster, + mode_tag, + data ); + } + + /* transform a given glyph image */ + static FT_Error + ft_smooth_transform( FT_Renderer render, + FT_GlyphSlot slot, + const FT_Matrix* matrix, + const FT_Vector* delta ) + { + FT_Error error = FT_Err_Ok; + + + if ( slot->format != render->glyph_format ) + { + error = FT_THROW( Invalid_Argument ); + goto Exit; + } + + if ( matrix ) + FT_Outline_Transform( &slot->outline, matrix ); + + if ( delta ) + FT_Outline_Translate( &slot->outline, delta->x, delta->y ); + + Exit: + return error; + } + + + /* return the glyph's control box */ + static void + ft_smooth_get_cbox( FT_Renderer render, + FT_GlyphSlot slot, + FT_BBox* cbox ) + { + FT_ZERO( cbox ); + + if ( slot->format == render->glyph_format ) + FT_Outline_Get_CBox( &slot->outline, cbox ); + } + + typedef struct TOrigin_ + { + unsigned char* origin; /* pixmap origin at the bottom-left */ + int pitch; /* pitch to go down one row */ + + } TOrigin; + +#ifndef FT_CONFIG_OPTION_SUBPIXEL_RENDERING + + /* initialize renderer -- init its raster */ + static FT_Error + ft_smooth_init( FT_Module module ) /* FT_Renderer */ + { + FT_Renderer render = (FT_Renderer)module; + + FT_Vector* sub = render->root.library->lcd_geometry; + + + /* set up default subpixel geometry for striped RGB panels. */ + sub[0].x = -21; + sub[0].y = 0; + sub[1].x = 0; + sub[1].y = 0; + sub[2].x = 21; + sub[2].y = 0; + + render->clazz->raster_class->raster_reset( render->raster, NULL, 0 ); + + return 0; + } + + + /* This function writes every third byte in direct rendering mode */ + static void + ft_smooth_lcd_spans( int y, + int count, + const FT_Span* spans, + void* target_ ) /* TOrigin* */ + { + TOrigin* target = (TOrigin*)target_; + + unsigned char* dst_line = target->origin - y * target->pitch; + unsigned char* dst; + unsigned short w; + + + for ( ; count--; spans++ ) + for ( dst = dst_line + spans->x * 3, w = spans->len; w--; dst += 3 ) + *dst = spans->coverage; + } + + + static FT_Error + ft_smooth_raster_lcd( FT_Renderer render, + FT_Outline* outline, + FT_Bitmap* bitmap ) + { + FT_Error error = FT_Err_Ok; + FT_Vector* sub = render->root.library->lcd_geometry; + FT_Pos x, y; + + FT_Raster_Params params; + TOrigin target; + + + /* Render 3 separate coverage bitmaps, shifting the outline. */ + /* Set up direct rendering to record them on each third byte. */ + params.source = outline; + params.flags = FT_RASTER_FLAG_AA | FT_RASTER_FLAG_DIRECT; + params.gray_spans = ft_smooth_lcd_spans; + params.user = ⌖ + + params.clip_box.xMin = 0; + params.clip_box.yMin = 0; + params.clip_box.xMax = bitmap->width; + params.clip_box.yMax = bitmap->rows; + + if ( bitmap->pitch < 0 ) + target.origin = bitmap->buffer; + else + target.origin = bitmap->buffer + + ( bitmap->rows - 1 ) * (unsigned int)bitmap->pitch; + + target.pitch = bitmap->pitch; + + FT_Outline_Translate( outline, + -sub[0].x, + -sub[0].y ); + error = render->raster_render( render->raster, ¶ms ); + x = sub[0].x; + y = sub[0].y; + if ( error ) + goto Exit; + + target.origin++; + FT_Outline_Translate( outline, + sub[0].x - sub[1].x, + sub[0].y - sub[1].y ); + error = render->raster_render( render->raster, ¶ms ); + x = sub[1].x; + y = sub[1].y; + if ( error ) + goto Exit; + + target.origin++; + FT_Outline_Translate( outline, + sub[1].x - sub[2].x, + sub[1].y - sub[2].y ); + error = render->raster_render( render->raster, ¶ms ); + x = sub[2].x; + y = sub[2].y; + + Exit: + FT_Outline_Translate( outline, x, y ); + + return error; + } + + + static FT_Error + ft_smooth_raster_lcdv( FT_Renderer render, + FT_Outline* outline, + FT_Bitmap* bitmap ) + { + FT_Error error = FT_Err_Ok; + int pitch = bitmap->pitch; + FT_Vector* sub = render->root.library->lcd_geometry; + FT_Pos x, y; + + FT_Raster_Params params; + + + params.target = bitmap; + params.source = outline; + params.flags = FT_RASTER_FLAG_AA; + + /* Render 3 separate coverage bitmaps, shifting the outline. */ + /* Notice that the subpixel geometry vectors are rotated. */ + /* Triple the pitch to render on each third row. */ + bitmap->pitch *= 3; + bitmap->rows /= 3; + + FT_Outline_Translate( outline, + -sub[0].y, + sub[0].x ); + error = render->raster_render( render->raster, ¶ms ); + x = sub[0].y; + y = -sub[0].x; + if ( error ) + goto Exit; + + bitmap->buffer += pitch; + FT_Outline_Translate( outline, + sub[0].y - sub[1].y, + sub[1].x - sub[0].x ); + error = render->raster_render( render->raster, ¶ms ); + x = sub[1].y; + y = -sub[1].x; + bitmap->buffer -= pitch; + if ( error ) + goto Exit; + + bitmap->buffer += 2 * pitch; + FT_Outline_Translate( outline, + sub[1].y - sub[2].y, + sub[2].x - sub[1].x ); + error = render->raster_render( render->raster, ¶ms ); + x = sub[2].y; + y = -sub[2].x; + bitmap->buffer -= 2 * pitch; + + Exit: + FT_Outline_Translate( outline, x, y ); + + bitmap->pitch /= 3; + bitmap->rows *= 3; + + return error; + } + +#else /* FT_CONFIG_OPTION_SUBPIXEL_RENDERING */ + + /* initialize renderer -- init its raster */ + static FT_Error + ft_smooth_init( FT_Module module ) /* FT_Renderer */ + { + FT_Renderer render = (FT_Renderer)module; + + + /* set up default LCD filtering */ + FT_Library_SetLcdFilter( render->root.library, FT_LCD_FILTER_DEFAULT ); + + render->clazz->raster_class->raster_reset( render->raster, NULL, 0 ); + + return 0; + } + + + static FT_Error + ft_smooth_raster_lcd( FT_Renderer render, + FT_Outline* outline, + FT_Bitmap* bitmap ) + { + FT_Error error = FT_Err_Ok; + FT_Vector* points = outline->points; + FT_Vector* points_end = FT_OFFSET( points, outline->n_points ); + FT_Vector* vec; + + FT_Raster_Params params; + + + params.target = bitmap; + params.source = outline; + params.flags = FT_RASTER_FLAG_AA; + + /* implode outline */ + for ( vec = points; vec < points_end; vec++ ) + vec->x *= 3; + + /* render outline into the bitmap */ + error = render->raster_render( render->raster, ¶ms ); + + /* deflate outline */ + for ( vec = points; vec < points_end; vec++ ) + vec->x /= 3; + + return error; + } + + + static FT_Error + ft_smooth_raster_lcdv( FT_Renderer render, + FT_Outline* outline, + FT_Bitmap* bitmap ) + { + FT_Error error = FT_Err_Ok; + FT_Vector* points = outline->points; + FT_Vector* points_end = FT_OFFSET( points, outline->n_points ); + FT_Vector* vec; + + FT_Raster_Params params; + + + params.target = bitmap; + params.source = outline; + params.flags = FT_RASTER_FLAG_AA; + + /* implode outline */ + for ( vec = points; vec < points_end; vec++ ) + vec->y *= 3; + + /* render outline into the bitmap */ + error = render->raster_render( render->raster, ¶ms ); + + /* deflate outline */ + for ( vec = points; vec < points_end; vec++ ) + vec->y /= 3; + + return error; + } + +#endif /* FT_CONFIG_OPTION_SUBPIXEL_RENDERING */ + +/* Oversampling scale to be used in rendering overlaps */ +#define SCALE ( 1 << 2 ) + + /* This function averages inflated spans in direct rendering mode */ + static void + ft_smooth_overlap_spans( int y, + int count, + const FT_Span* spans, + void* target_ ) + { + TOrigin* target = (TOrigin*)target_; + + + unsigned char* dst = target->origin - ( y / SCALE ) * target->pitch; + unsigned short x; + unsigned int cover, sum; + + + /* When accumulating the oversampled spans we need to assure that */ + /* fully covered pixels are equal to 255 and do not overflow. */ + /* It is important that the SCALE is a power of 2, each subpixel */ + /* cover can also reach a power of 2 after rounding, and the total */ + /* is clamped to 255 when it adds up to 256. */ + for ( ; count--; spans++ ) + { + cover = ( spans->coverage + SCALE * SCALE / 2 ) / ( SCALE * SCALE ); + for ( x = 0; x < spans->len; x++ ) + { + sum = dst[( spans->x + x ) / SCALE] + cover; + dst[( spans->x + x ) / SCALE] = (unsigned char)( sum - ( sum >> 8 ) ); + } + } + } + + + static FT_Error + ft_smooth_raster_overlap( FT_Renderer render, + FT_Outline* outline, + FT_Bitmap* bitmap ) + { + FT_Error error = FT_Err_Ok; + FT_Vector* points = outline->points; + FT_Vector* points_end = FT_OFFSET( points, outline->n_points ); + FT_Vector* vec; + + FT_Raster_Params params; + TOrigin target; + + + /* Reject outlines that are too wide for 16-bit FT_Span. */ + /* Other limits are applied upstream with the same error code. */ + if ( bitmap->width * SCALE > 0x7FFF ) + return FT_THROW( Raster_Overflow ); + + /* Set up direct rendering to average oversampled spans. */ + params.source = outline; + params.flags = FT_RASTER_FLAG_AA | FT_RASTER_FLAG_DIRECT; + params.gray_spans = ft_smooth_overlap_spans; + params.user = ⌖ + + params.clip_box.xMin = 0; + params.clip_box.yMin = 0; + params.clip_box.xMax = bitmap->width * SCALE; + params.clip_box.yMax = bitmap->rows * SCALE; + + if ( bitmap->pitch < 0 ) + target.origin = bitmap->buffer; + else + target.origin = bitmap->buffer + + ( bitmap->rows - 1 ) * (unsigned int)bitmap->pitch; + + target.pitch = bitmap->pitch; + + /* inflate outline */ + for ( vec = points; vec < points_end; vec++ ) + { + vec->x *= SCALE; + vec->y *= SCALE; + } + + /* render outline into the bitmap */ + error = render->raster_render( render->raster, ¶ms ); + + /* deflate outline */ + for ( vec = points; vec < points_end; vec++ ) + { + vec->x /= SCALE; + vec->y /= SCALE; + } + + return error; + } + +#undef SCALE + + static FT_Error + ft_smooth_render( FT_Renderer render, + FT_GlyphSlot slot, + FT_Render_Mode mode, + const FT_Vector* origin ) + { + FT_Error error = FT_Err_Ok; + FT_Outline* outline = &slot->outline; + FT_Bitmap* bitmap = &slot->bitmap; + FT_Memory memory = render->root.memory; + FT_Pos x_shift = 0; + FT_Pos y_shift = 0; + + + /* check glyph image format */ + if ( slot->format != render->glyph_format ) + { + error = FT_THROW( Invalid_Argument ); + goto Exit; + } + + /* check mode */ + if ( mode != FT_RENDER_MODE_NORMAL && + mode != FT_RENDER_MODE_LIGHT && + mode != FT_RENDER_MODE_LCD && + mode != FT_RENDER_MODE_LCD_V ) + { + error = FT_THROW( Cannot_Render_Glyph ); + goto Exit; + } + + /* release old bitmap buffer */ + if ( slot->internal->flags & FT_GLYPH_OWN_BITMAP ) + { + FT_FREE( bitmap->buffer ); + slot->internal->flags &= ~FT_GLYPH_OWN_BITMAP; + } + + if ( ft_glyphslot_preset_bitmap( slot, mode, origin ) ) + { + error = FT_THROW( Raster_Overflow ); + goto Exit; + } + + if ( !bitmap->rows || !bitmap->pitch ) + goto Exit; + + /* allocate new one */ + if ( FT_ALLOC_MULT( bitmap->buffer, bitmap->rows, bitmap->pitch ) ) + goto Exit; + + slot->internal->flags |= FT_GLYPH_OWN_BITMAP; + + x_shift = 64 * -slot->bitmap_left; + y_shift = 64 * -slot->bitmap_top; + if ( bitmap->pixel_mode == FT_PIXEL_MODE_LCD_V ) + y_shift += 64 * (FT_Int)bitmap->rows / 3; + else + y_shift += 64 * (FT_Int)bitmap->rows; + + if ( origin ) + { + x_shift += origin->x; + y_shift += origin->y; + } + + /* translate outline to render it into the bitmap */ + if ( x_shift || y_shift ) + FT_Outline_Translate( outline, x_shift, y_shift ); + + if ( mode == FT_RENDER_MODE_NORMAL || + mode == FT_RENDER_MODE_LIGHT ) + { + if ( outline->flags & FT_OUTLINE_OVERLAP ) + error = ft_smooth_raster_overlap( render, outline, bitmap ); + else + { + FT_Raster_Params params; + + + params.target = bitmap; + params.source = outline; + params.flags = FT_RASTER_FLAG_AA; + + error = render->raster_render( render->raster, ¶ms ); + } + } + else + { + if ( mode == FT_RENDER_MODE_LCD ) + error = ft_smooth_raster_lcd ( render, outline, bitmap ); + else if ( mode == FT_RENDER_MODE_LCD_V ) + error = ft_smooth_raster_lcdv( render, outline, bitmap ); + +#ifdef FT_CONFIG_OPTION_SUBPIXEL_RENDERING + + /* finally apply filtering */ + { + FT_Byte* lcd_weights; + FT_Bitmap_LcdFilterFunc lcd_filter_func; + + + /* Per-face LCD filtering takes priority if set up. */ + if ( slot->face && slot->face->internal->lcd_filter_func ) + { + lcd_weights = slot->face->internal->lcd_weights; + lcd_filter_func = slot->face->internal->lcd_filter_func; + } + else + { + lcd_weights = slot->library->lcd_weights; + lcd_filter_func = slot->library->lcd_filter_func; + } + + if ( lcd_filter_func ) + lcd_filter_func( bitmap, lcd_weights ); + } + +#endif /* FT_CONFIG_OPTION_SUBPIXEL_RENDERING */ + + } + + Exit: + if ( !error ) + { + /* everything is fine; the glyph is now officially a bitmap */ + slot->format = FT_GLYPH_FORMAT_BITMAP; + } + else if ( slot->internal->flags & FT_GLYPH_OWN_BITMAP ) + { + FT_FREE( bitmap->buffer ); + slot->internal->flags &= ~FT_GLYPH_OWN_BITMAP; + } + + if ( x_shift || y_shift ) + FT_Outline_Translate( outline, -x_shift, -y_shift ); + + return error; + } + + + FT_DEFINE_RENDERER( + ft_smooth_renderer_class, + + FT_MODULE_RENDERER, + sizeof ( FT_RendererRec ), + + "smooth", + 0x10000L, + 0x20000L, + + NULL, /* module specific interface */ + + (FT_Module_Constructor)ft_smooth_init, /* module_init */ + (FT_Module_Destructor) NULL, /* module_done */ + (FT_Module_Requester) NULL, /* get_interface */ + + FT_GLYPH_FORMAT_OUTLINE, + + (FT_Renderer_RenderFunc) ft_smooth_render, /* render_glyph */ + (FT_Renderer_TransformFunc)ft_smooth_transform, /* transform_glyph */ + (FT_Renderer_GetCBoxFunc) ft_smooth_get_cbox, /* get_glyph_cbox */ + (FT_Renderer_SetModeFunc) ft_smooth_set_mode, /* set_mode */ + + (FT_Raster_Funcs*)&ft_grays_raster /* raster_class */ + ) + + +/* END */ diff --git a/src/font/freetype-2.10.2/src/smooth/ftsmooth.h b/3rdparty/freetype-2.13.2/src/smooth/ftsmooth.h similarity index 78% rename from src/font/freetype-2.10.2/src/smooth/ftsmooth.h rename to 3rdparty/freetype-2.13.2/src/smooth/ftsmooth.h index ee5d2ff61..f8bdc9938 100644 --- a/src/font/freetype-2.10.2/src/smooth/ftsmooth.h +++ b/3rdparty/freetype-2.13.2/src/smooth/ftsmooth.h @@ -4,7 +4,7 @@ * * Anti-aliasing renderer interface (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,8 +20,7 @@ #define FTSMOOTH_H_ -#include -#include FT_RENDER_H +#include FT_BEGIN_HEADER @@ -29,10 +28,6 @@ FT_BEGIN_HEADER FT_DECLARE_RENDERER( ft_smooth_renderer_class ) - FT_DECLARE_RENDERER( ft_smooth_lcd_renderer_class ) - - FT_DECLARE_RENDERER( ft_smooth_lcdv_renderer_class ) - FT_END_HEADER diff --git a/src/font/freetype-2.10.2/src/smooth/module.mk b/3rdparty/freetype-2.13.2/src/smooth/module.mk similarity index 62% rename from src/font/freetype-2.10.2/src/smooth/module.mk rename to 3rdparty/freetype-2.13.2/src/smooth/module.mk index ad8b47dab..82ab2fa59 100644 --- a/src/font/freetype-2.10.2/src/smooth/module.mk +++ b/3rdparty/freetype-2.13.2/src/smooth/module.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 1996-2020 by +# Copyright (C) 1996-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, @@ -18,10 +18,6 @@ FTMODULE_H_COMMANDS += SMOOTH_RENDERER define SMOOTH_RENDERER $(OPEN_DRIVER) FT_Renderer_Class, ft_smooth_renderer_class $(CLOSE_DRIVER) $(ECHO_DRIVER)smooth $(ECHO_DRIVER_DESC)anti-aliased bitmap renderer$(ECHO_DRIVER_DONE) -$(OPEN_DRIVER) FT_Renderer_Class, ft_smooth_lcd_renderer_class $(CLOSE_DRIVER) -$(ECHO_DRIVER)smooth $(ECHO_DRIVER_DESC)anti-aliased bitmap renderer for LCDs$(ECHO_DRIVER_DONE) -$(OPEN_DRIVER) FT_Renderer_Class, ft_smooth_lcdv_renderer_class $(CLOSE_DRIVER) -$(ECHO_DRIVER)smooth $(ECHO_DRIVER_DESC)anti-aliased bitmap renderer for vertical LCDs$(ECHO_DRIVER_DONE) endef # EOF diff --git a/src/font/freetype-2.10.2/src/smooth/rules.mk b/3rdparty/freetype-2.13.2/src/smooth/rules.mk similarity index 98% rename from src/font/freetype-2.10.2/src/smooth/rules.mk rename to 3rdparty/freetype-2.13.2/src/smooth/rules.mk index b08056fac..5d89c7540 100644 --- a/src/font/freetype-2.10.2/src/smooth/rules.mk +++ b/3rdparty/freetype-2.13.2/src/smooth/rules.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 1996-2020 by +# Copyright (C) 1996-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, diff --git a/src/font/freetype-2.10.2/src/smooth/smooth.c b/3rdparty/freetype-2.13.2/src/smooth/smooth.c similarity index 92% rename from src/font/freetype-2.10.2/src/smooth/smooth.c rename to 3rdparty/freetype-2.13.2/src/smooth/smooth.c index 6ad9424f0..9a0b824c2 100644 --- a/src/font/freetype-2.10.2/src/smooth/smooth.c +++ b/3rdparty/freetype-2.13.2/src/smooth/smooth.c @@ -4,7 +4,7 @@ * * FreeType anti-aliasing rasterer module component (body only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -17,7 +17,6 @@ #define FT_MAKE_OPTION_SINGLE_OBJECT -#include #include "ftgrays.c" #include "ftsmooth.c" diff --git a/src/font/freetype-2.10.2/src/truetype/module.mk b/3rdparty/freetype-2.13.2/src/truetype/module.mk similarity index 95% rename from src/font/freetype-2.10.2/src/truetype/module.mk rename to 3rdparty/freetype-2.13.2/src/truetype/module.mk index 2d8d39d1f..5d44ac1f4 100644 --- a/src/font/freetype-2.10.2/src/truetype/module.mk +++ b/3rdparty/freetype-2.13.2/src/truetype/module.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 1996-2020 by +# Copyright (C) 1996-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, diff --git a/src/font/freetype-2.10.2/src/truetype/rules.mk b/3rdparty/freetype-2.13.2/src/truetype/rules.mk similarity index 94% rename from src/font/freetype-2.10.2/src/truetype/rules.mk rename to 3rdparty/freetype-2.13.2/src/truetype/rules.mk index 2f6fecfc4..dde26de1c 100644 --- a/src/font/freetype-2.10.2/src/truetype/rules.mk +++ b/3rdparty/freetype-2.13.2/src/truetype/rules.mk @@ -3,7 +3,7 @@ # -# Copyright (C) 1996-2020 by +# Copyright (C) 1996-2023 by # David Turner, Robert Wilhelm, and Werner Lemberg. # # This file is part of the FreeType project, and may only be used, modified, @@ -33,8 +33,7 @@ TT_DRV_SRC := $(TT_DIR)/ttdriver.c \ $(TT_DIR)/ttgxvar.c \ $(TT_DIR)/ttinterp.c \ $(TT_DIR)/ttobjs.c \ - $(TT_DIR)/ttpload.c \ - $(TT_DIR)/ttsubpix.c + $(TT_DIR)/ttpload.c # TrueType driver headers # diff --git a/src/font/freetype-2.10.2/src/truetype/truetype.c b/3rdparty/freetype-2.13.2/src/truetype/truetype.c similarity index 91% rename from src/font/freetype-2.10.2/src/truetype/truetype.c rename to 3rdparty/freetype-2.13.2/src/truetype/truetype.c index 1f15b29bb..fcc0ea334 100644 --- a/src/font/freetype-2.10.2/src/truetype/truetype.c +++ b/3rdparty/freetype-2.13.2/src/truetype/truetype.c @@ -4,7 +4,7 @@ * * FreeType TrueType driver component (body only). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -17,7 +17,6 @@ #define FT_MAKE_OPTION_SINGLE_OBJECT -#include #include "ttdriver.c" /* driver interface */ #include "ttgload.c" /* glyph loader */ @@ -25,7 +24,6 @@ #include "ttinterp.c" #include "ttobjs.c" /* object manager */ #include "ttpload.c" /* tables loader */ -#include "ttsubpix.c" /* END */ diff --git a/src/font/freetype-2.10.2/src/truetype/ttdriver.c b/3rdparty/freetype-2.13.2/src/truetype/ttdriver.c similarity index 75% rename from src/font/freetype-2.10.2/src/truetype/ttdriver.c rename to 3rdparty/freetype-2.13.2/src/truetype/ttdriver.c index 90fab46e2..d1496fec7 100644 --- a/src/font/freetype-2.10.2/src/truetype/ttdriver.c +++ b/3rdparty/freetype-2.13.2/src/truetype/ttdriver.c @@ -4,7 +4,7 @@ * * TrueType font driver implementation (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,22 +16,21 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_STREAM_H -#include FT_INTERNAL_SFNT_H -#include FT_SERVICE_FONT_FORMAT_H +#include +#include +#include +#include #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT -#include FT_MULTIPLE_MASTERS_H -#include FT_SERVICE_MULTIPLE_MASTERS_H -#include FT_SERVICE_METRICS_VARIATIONS_H +#include +#include +#include #endif -#include FT_SERVICE_TRUETYPE_ENGINE_H -#include FT_SERVICE_TRUETYPE_GLYF_H -#include FT_SERVICE_PROPERTIES_H -#include FT_DRIVER_H +#include +#include +#include +#include #include "ttdriver.h" #include "ttgload.h" @@ -58,7 +57,7 @@ * PROPERTY SERVICE * */ - static FT_Error + FT_CALLBACK_DEF( FT_Error ) tt_property_set( FT_Module module, /* TT_Driver */ const char* property_name, const void* value, @@ -94,31 +93,36 @@ interpreter_version = *iv; } - if ( interpreter_version == TT_INTERPRETER_VERSION_35 -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - || interpreter_version == TT_INTERPRETER_VERSION_38 -#endif + switch ( interpreter_version ) + { + case TT_INTERPRETER_VERSION_35: + driver->interpreter_version = TT_INTERPRETER_VERSION_35; + break; + + case TT_INTERPRETER_VERSION_38: + case TT_INTERPRETER_VERSION_40: #ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL - || interpreter_version == TT_INTERPRETER_VERSION_40 + driver->interpreter_version = TT_INTERPRETER_VERSION_40; + break; #endif - ) - driver->interpreter_version = interpreter_version; - else + + default: error = FT_ERR( Unimplemented_Feature ); + } return error; } - FT_TRACE0(( "tt_property_set: missing property `%s'\n", + FT_TRACE2(( "tt_property_set: missing property `%s'\n", property_name )); return FT_THROW( Missing_Property ); } - static FT_Error + FT_CALLBACK_DEF( FT_Error ) tt_property_get( FT_Module module, /* TT_Driver */ const char* property_name, - const void* value ) + void* value ) { FT_Error error = FT_Err_Ok; TT_Driver driver = (TT_Driver)module; @@ -136,7 +140,7 @@ return error; } - FT_TRACE0(( "tt_property_get: missing property `%s'\n", + FT_TRACE2(( "tt_property_get: missing property `%s'\n", property_name )); return FT_THROW( Missing_Property ); } @@ -145,8 +149,8 @@ FT_DEFINE_SERVICE_PROPERTIESREC( tt_service_properties, - (FT_Properties_SetFunc)tt_property_set, /* set_property */ - (FT_Properties_GetFunc)tt_property_get /* get_property */ + tt_property_set, /* FT_Properties_SetFunc set_property */ + tt_property_get /* FT_Properties_GetFunc get_property */ ) @@ -199,35 +203,35 @@ * * They can be implemented by format-specific interfaces. */ - static FT_Error - tt_get_kerning( FT_Face ttface, /* TT_Face */ + FT_CALLBACK_DEF( FT_Error ) + tt_get_kerning( FT_Face face, /* TT_Face */ FT_UInt left_glyph, FT_UInt right_glyph, FT_Vector* kerning ) { - TT_Face face = (TT_Face)ttface; - SFNT_Service sfnt = (SFNT_Service)face->sfnt; + TT_Face ttface = (TT_Face)face; + SFNT_Service sfnt = (SFNT_Service)ttface->sfnt; kerning->x = 0; kerning->y = 0; if ( sfnt ) - kerning->x = sfnt->get_kerning( face, left_glyph, right_glyph ); + kerning->x = sfnt->get_kerning( ttface, left_glyph, right_glyph ); return 0; } - static FT_Error - tt_get_advances( FT_Face ttface, + FT_CALLBACK_DEF( FT_Error ) + tt_get_advances( FT_Face face, /* TT_Face */ FT_UInt start, FT_UInt count, FT_Int32 flags, FT_Fixed *advances ) { FT_UInt nn; - TT_Face face = (TT_Face)ttface; + TT_Face ttface = (TT_Face)face; /* XXX: TODO: check for sbits */ @@ -236,8 +240,8 @@ { #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT /* no fast retrieval for blended MM fonts without VVAR table */ - if ( ( FT_IS_NAMED_INSTANCE( ttface ) || FT_IS_VARIATION( ttface ) ) && - !( face->variation_support & TT_FACE_FLAG_VAR_VADVANCE ) ) + if ( ( FT_IS_NAMED_INSTANCE( face ) || FT_IS_VARIATION( face ) ) && + !( ttface->variation_support & TT_FACE_FLAG_VAR_VADVANCE ) ) return FT_THROW( Unimplemented_Feature ); #endif @@ -248,7 +252,7 @@ /* since we don't need `tsb', we use zero for `yMax' parameter */ - TT_Get_VMetrics( face, start + nn, 0, &tsb, &ah ); + TT_Get_VMetrics( ttface, start + nn, 0, &tsb, &ah ); advances[nn] = ah; } } @@ -256,8 +260,8 @@ { #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT /* no fast retrieval for blended MM fonts without HVAR table */ - if ( ( FT_IS_NAMED_INSTANCE( ttface ) || FT_IS_VARIATION( ttface ) ) && - !( face->variation_support & TT_FACE_FLAG_VAR_HADVANCE ) ) + if ( ( FT_IS_NAMED_INSTANCE( face ) || FT_IS_VARIATION( face ) ) && + !( ttface->variation_support & TT_FACE_FLAG_VAR_HADVANCE ) ) return FT_THROW( Unimplemented_Feature ); #endif @@ -267,7 +271,7 @@ FT_UShort aw; - TT_Get_HMetrics( face, start + nn, &lsb, &aw ); + TT_Get_HMetrics( ttface, start + nn, &lsb, &aw ); advances[nn] = aw; } } @@ -291,7 +295,7 @@ #ifdef TT_CONFIG_OPTION_EMBEDDED_BITMAPS - static FT_Error + FT_CALLBACK_DEF( FT_Error ) tt_size_select( FT_Size size, FT_ULong strike_index ) { @@ -307,7 +311,7 @@ /* use the scaled metrics, even when tt_size_reset fails */ FT_Select_Metrics( size->face, strike_index ); - tt_size_reset( ttsize, 0 ); /* ignore return value */ + tt_size_reset( ttsize ); /* ignore return value */ } else { @@ -328,7 +332,7 @@ #endif /* TT_CONFIG_OPTION_EMBEDDED_BITMAPS */ - static FT_Error + FT_CALLBACK_DEF( FT_Error ) tt_size_request( FT_Size size, FT_Size_Request req ) { @@ -355,11 +359,20 @@ #endif /* TT_CONFIG_OPTION_EMBEDDED_BITMAPS */ - FT_Request_Metrics( size->face, req ); + { + FT_Error err = FT_Request_Metrics( size->face, req ); + + + if ( err ) + { + error = err; + goto Exit; + } + } if ( FT_IS_SCALABLE( size->face ) ) { - error = tt_size_reset( ttsize, 0 ); + error = tt_size_reset( ttsize ); #ifdef TT_USE_BYTECODE_INTERPRETER /* for the `MPS' bytecode instruction we need the point size */ @@ -383,6 +396,7 @@ #endif } + Exit: return error; } @@ -417,15 +431,15 @@ * @Return: * FreeType error code. 0 means success. */ - static FT_Error - tt_glyph_load( FT_GlyphSlot ttslot, /* TT_GlyphSlot */ - FT_Size ttsize, /* TT_Size */ + FT_CALLBACK_DEF( FT_Error ) + tt_glyph_load( FT_GlyphSlot slot, /* TT_GlyphSlot */ + FT_Size size, /* TT_Size */ FT_UInt glyph_index, FT_Int32 load_flags ) { - TT_GlyphSlot slot = (TT_GlyphSlot)ttslot; - TT_Size size = (TT_Size)ttsize; - FT_Face face = ttslot->face; + TT_GlyphSlot ttslot = (TT_GlyphSlot)slot; + TT_Size ttsize = (TT_Size)size; + FT_Face face = ttslot->face; FT_Error error; @@ -467,12 +481,12 @@ } /* use hinted metrics only if we load a glyph with hinting */ - size->metrics = ( load_flags & FT_LOAD_NO_HINTING ) - ? &ttsize->metrics - : &size->hinted_metrics; + ttsize->metrics = ( load_flags & FT_LOAD_NO_HINTING ) + ? &size->metrics + : &ttsize->hinted_metrics; /* now fill in the glyph slot with outline/bitmap/layered */ - error = TT_Load_Glyph( size, slot, glyph_index, load_flags ); + error = TT_Load_Glyph( ttsize, ttslot, glyph_index, load_flags ); /* force drop-out mode to 2 - irrelevant now */ /* slot->outline.dropout_mode = 2; */ @@ -498,34 +512,47 @@ FT_DEFINE_SERVICE_MULTIMASTERSREC( tt_service_gx_multi_masters, - (FT_Get_MM_Func) NULL, /* get_mm */ - (FT_Set_MM_Design_Func) NULL, /* set_mm_design */ - (FT_Set_MM_Blend_Func) TT_Set_MM_Blend, /* set_mm_blend */ - (FT_Get_MM_Blend_Func) TT_Get_MM_Blend, /* get_mm_blend */ - (FT_Get_MM_Var_Func) TT_Get_MM_Var, /* get_mm_var */ - (FT_Set_Var_Design_Func) TT_Set_Var_Design, /* set_var_design */ - (FT_Get_Var_Design_Func) TT_Get_Var_Design, /* get_var_design */ - (FT_Set_Instance_Func) TT_Set_Named_Instance, /* set_instance */ - (FT_Set_MM_WeightVector_Func)NULL, /* set_mm_weightvector */ - (FT_Get_MM_WeightVector_Func)NULL, /* get_mm_weightvector */ - - (FT_Get_Var_Blend_Func) tt_get_var_blend, /* get_var_blend */ - (FT_Done_Blend_Func) tt_done_blend /* done_blend */ + NULL, /* FT_Get_MM_Func get_mm */ + NULL, /* FT_Set_MM_Design_Func set_mm_design */ + TT_Set_MM_Blend, /* FT_Set_MM_Blend_Func set_mm_blend */ + TT_Get_MM_Blend, /* FT_Get_MM_Blend_Func get_mm_blend */ + TT_Get_MM_Var, /* FT_Get_MM_Var_Func get_mm_var */ + TT_Set_Var_Design, /* FT_Set_Var_Design_Func set_var_design */ + TT_Get_Var_Design, /* FT_Get_Var_Design_Func get_var_design */ + TT_Set_Named_Instance, /* FT_Set_Named_Instance_Func set_named_instance */ + TT_Get_Default_Named_Instance, + /* FT_Get_Default_Named_Instance_Func get_default_named_instance */ + NULL, /* FT_Set_MM_WeightVector_Func set_mm_weightvector */ + NULL, /* FT_Get_MM_WeightVector_Func get_mm_weightvector */ + + tt_construct_ps_name, /* FT_Construct_PS_Name_Func construct_ps_name */ + tt_var_load_delta_set_index_mapping, + /* FT_Var_Load_Delta_Set_Idx_Map_Func load_delta_set_idx_map */ + tt_var_load_item_variation_store, + /* FT_Var_Load_Item_Var_Store_Func load_item_variation_store */ + tt_var_get_item_delta, /* FT_Var_Get_Item_Delta_Func get_item_delta */ + tt_var_done_item_variation_store, + /* FT_Var_Done_Item_Var_Store_Func done_item_variation_store */ + tt_var_done_delta_set_index_map, + /* FT_Var_Done_Delta_Set_Idx_Map_Func done_delta_set_index_map */ + tt_get_var_blend, /* FT_Get_Var_Blend_Func get_var_blend */ + tt_done_blend /* FT_Done_Blend_Func done_blend */ ) FT_DEFINE_SERVICE_METRICSVARIATIONSREC( tt_service_metrics_variations, - (FT_HAdvance_Adjust_Func)tt_hadvance_adjust, /* hadvance_adjust */ - (FT_LSB_Adjust_Func) NULL, /* lsb_adjust */ - (FT_RSB_Adjust_Func) NULL, /* rsb_adjust */ + tt_hadvance_adjust, /* FT_HAdvance_Adjust_Func hadvance_adjust */ + NULL, /* FT_LSB_Adjust_Func lsb_adjust */ + NULL, /* FT_RSB_Adjust_Func rsb_adjust */ - (FT_VAdvance_Adjust_Func)tt_vadvance_adjust, /* vadvance_adjust */ - (FT_TSB_Adjust_Func) NULL, /* tsb_adjust */ - (FT_BSB_Adjust_Func) NULL, /* bsb_adjust */ - (FT_VOrg_Adjust_Func) NULL, /* vorg_adjust */ + tt_vadvance_adjust, /* FT_VAdvance_Adjust_Func vadvance_adjust */ + NULL, /* FT_TSB_Adjust_Func tsb_adjust */ + NULL, /* FT_BSB_Adjust_Func bsb_adjust */ + NULL, /* FT_VOrg_Adjust_Func vorg_adjust */ - (FT_Metrics_Adjust_Func) tt_apply_mvar /* metrics_adjust */ + tt_apply_mvar, /* FT_Metrics_Adjust_Func metrics_adjust */ + tt_size_reset_height /* FT_Size_Reset_Func size_reset */ ) #endif /* TT_CONFIG_OPTION_GX_VAR_SUPPORT */ diff --git a/src/font/freetype-2.10.2/src/truetype/ttdriver.h b/3rdparty/freetype-2.13.2/src/truetype/ttdriver.h similarity index 89% rename from src/font/freetype-2.10.2/src/truetype/ttdriver.h rename to 3rdparty/freetype-2.13.2/src/truetype/ttdriver.h index d1cfa47c8..757a66f42 100644 --- a/src/font/freetype-2.10.2/src/truetype/ttdriver.h +++ b/3rdparty/freetype-2.13.2/src/truetype/ttdriver.h @@ -4,7 +4,7 @@ * * High-level TrueType driver interface (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,8 +20,7 @@ #define TTDRIVER_H_ -#include -#include FT_INTERNAL_DRIVER_H +#include FT_BEGIN_HEADER diff --git a/src/font/freetype-2.10.2/src/truetype/tterrors.h b/3rdparty/freetype-2.13.2/src/truetype/tterrors.h similarity index 90% rename from src/font/freetype-2.10.2/src/truetype/tterrors.h rename to 3rdparty/freetype-2.13.2/src/truetype/tterrors.h index 71d66023c..008ee9985 100644 --- a/src/font/freetype-2.10.2/src/truetype/tterrors.h +++ b/3rdparty/freetype-2.13.2/src/truetype/tterrors.h @@ -4,7 +4,7 @@ * * TrueType error codes (specification only). * - * Copyright (C) 2001-2020 by + * Copyright (C) 2001-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -26,7 +26,7 @@ #ifndef TTERRORS_H_ #define TTERRORS_H_ -#include FT_MODULE_ERRORS_H +#include #undef FTERRORS_H_ @@ -34,7 +34,7 @@ #define FT_ERR_PREFIX TT_Err_ #define FT_ERR_BASE FT_Mod_Err_TrueType -#include FT_ERRORS_H +#include #endif /* TTERRORS_H_ */ diff --git a/src/font/freetype-2.10.2/src/truetype/ttgload.c b/3rdparty/freetype-2.13.2/src/truetype/ttgload.c similarity index 75% rename from src/font/freetype-2.10.2/src/truetype/ttgload.c rename to 3rdparty/freetype-2.13.2/src/truetype/ttgload.c index 2a1742839..dc427e8a1 100644 --- a/src/font/freetype-2.10.2/src/truetype/ttgload.c +++ b/3rdparty/freetype-2.13.2/src/truetype/ttgload.c @@ -4,7 +4,7 @@ * * TrueType Glyph Loader (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -17,15 +17,15 @@ #include -#include FT_INTERNAL_DEBUG_H +#include #include FT_CONFIG_CONFIG_H -#include FT_INTERNAL_CALC_H -#include FT_INTERNAL_STREAM_H -#include FT_INTERNAL_SFNT_H -#include FT_TRUETYPE_TAGS_H -#include FT_OUTLINE_H -#include FT_DRIVER_H -#include FT_LIST_H +#include +#include +#include +#include +#include +#include +#include #include "ttgload.h" #include "ttpload.h" @@ -35,7 +35,6 @@ #endif #include "tterrors.h" -#include "ttsubpix.h" /************************************************************************** @@ -60,7 +59,7 @@ #define SAME_X 0x10 #define Y_POSITIVE 0x20 /* two meanings depending on Y_SHORT_VECTOR */ #define SAME_Y 0x20 -#define OVERLAP_SIMPLE 0x40 /* we ignore this value */ +#define OVERLAP_SIMPLE 0x40 /* retained as FT_OUTLINE_OVERLAP */ /************************************************************************** @@ -77,7 +76,7 @@ #define WE_HAVE_A_2X2 0x0080 #define WE_HAVE_INSTR 0x0100 #define USE_MY_METRICS 0x0200 -#define OVERLAP_COMPOUND 0x0400 /* we ignore this value */ +#define OVERLAP_COMPOUND 0x0400 /* retained as FT_OUTLINE_OVERLAP */ #define SCALED_COMPONENT_OFFSET 0x0800 #define UNSCALED_COMPONENT_OFFSET 0x1000 @@ -137,6 +136,11 @@ face->horizontal.Descender ); } +#ifdef FT_DEBUG_LEVEL_TRACE + if ( !face->vertical_info ) + FT_TRACE5(( " [vertical metrics missing, computing values]\n" )); +#endif + FT_TRACE5(( " advance height (font units): %d\n", *ah )); FT_TRACE5(( " top side bearing (font units): %d\n", *tsb )); } @@ -147,9 +151,6 @@ FT_UInt glyph_index ) { TT_Face face = loader->face; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - TT_Driver driver = (TT_Driver)FT_FACE_DRIVER( face ); -#endif FT_Error error; FT_Stream stream = loader->stream; @@ -178,24 +179,17 @@ loader->top_bearing = top_bearing; loader->vadvance = advance_height; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( driver->interpreter_version == TT_INTERPRETER_VERSION_38 && - loader->exec ) - { - loader->exec->sph_tweak_flags = 0; - - /* This may not be the right place for this, but it works... */ - /* Note that we have to unconditionally load the tweaks since */ - /* it is possible that glyphs individually switch ClearType's */ - /* backward compatibility mode on and off. */ - sph_set_tweaks( loader, glyph_index ); - } -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - - if ( !loader->linear_def ) +#ifdef FT_CONFIG_OPTION_INCREMENTAL + /* With the incremental interface, these values are set by */ + /* a call to `tt_get_metrics_incremental'. */ + if ( face->root.internal->incremental_interface == NULL ) +#endif { - loader->linear_def = 1; - loader->linear = advance_width; + if ( !loader->linear_def ) + { + loader->linear_def = 1; + loader->linear = advance_width; + } } return FT_Err_Ok; @@ -205,8 +199,8 @@ #ifdef FT_CONFIG_OPTION_INCREMENTAL static void - tt_get_metrics_incr_overrides( TT_Loader loader, - FT_UInt glyph_index ) + tt_get_metrics_incremental( TT_Loader loader, + FT_UInt glyph_index ) { TT_Face face = loader->face; @@ -333,9 +327,9 @@ loader->bbox.yMax = FT_NEXT_SHORT( p ); FT_TRACE5(( " # of contours: %d\n", loader->n_contours )); - FT_TRACE5(( " xMin: %4d xMax: %4d\n", loader->bbox.xMin, + FT_TRACE5(( " xMin: %4ld xMax: %4ld\n", loader->bbox.xMin, loader->bbox.xMax )); - FT_TRACE5(( " yMin: %4d yMax: %4d\n", loader->bbox.yMin, + FT_TRACE5(( " yMin: %4ld yMax: %4ld\n", loader->bbox.yMin, loader->bbox.yMax )); loader->cursor = p; @@ -350,17 +344,16 @@ FT_Byte* p = load->cursor; FT_Byte* limit = load->limit; FT_GlyphLoader gloader = load->gloader; + FT_Outline* outline = &gloader->current.outline; FT_Int n_contours = load->n_contours; - FT_Outline* outline; - FT_UShort n_ins; FT_Int n_points; + FT_UShort n_ins; FT_Byte *flag, *flag_limit; FT_Byte c, count; FT_Vector *vec, *vec_limit; FT_Pos x, y; - FT_Short *cont, *cont_limit, prev_cont; - FT_Int xy_size = 0; + FT_Short *cont, *cont_limit, last; /* check that we can add the contours to the glyph */ @@ -368,41 +361,27 @@ if ( error ) goto Fail; - /* reading the contours' endpoints & number of points */ - cont = gloader->current.outline.contours; - cont_limit = cont + n_contours; - /* check space for contours array + instructions count */ - if ( n_contours >= 0xFFF || p + ( n_contours + 1 ) * 2 > limit ) + if ( n_contours >= 0xFFF || p + 2 * n_contours + 2 > limit ) goto Invalid_Outline; - prev_cont = FT_NEXT_SHORT( p ); - - if ( n_contours > 0 ) - cont[0] = prev_cont; - - if ( prev_cont < 0 ) - goto Invalid_Outline; + /* reading the contours' endpoints & number of points */ + cont = outline->contours; + cont_limit = cont + n_contours; - for ( cont++; cont < cont_limit; cont++ ) + last = -1; + for ( ; cont < cont_limit; cont++ ) { - cont[0] = FT_NEXT_SHORT( p ); - if ( cont[0] <= prev_cont ) - { - /* unordered contours: this is invalid */ - goto Invalid_Outline; - } - prev_cont = cont[0]; - } + *cont = FT_NEXT_SHORT( p ); - n_points = 0; - if ( n_contours > 0 ) - { - n_points = cont[-1] + 1; - if ( n_points < 0 ) + if ( *cont <= last ) goto Invalid_Outline; + + last = *cont; } + n_points = last + 1; + FT_TRACE5(( " # of points: %d\n", n_points )); /* note that we will add four phantom points later */ @@ -410,59 +389,48 @@ if ( error ) goto Fail; - /* reading the bytecode instructions */ - load->glyph->control_len = 0; - load->glyph->control_data = NULL; - - if ( p + 2 > limit ) - goto Invalid_Outline; - + /* space checked above */ n_ins = FT_NEXT_USHORT( p ); FT_TRACE5(( " Instructions size: %u\n", n_ins )); + /* check instructions size */ + if ( p + n_ins > limit ) + { + FT_TRACE1(( "TT_Load_Simple_Glyph: excessive instruction count\n" )); + error = FT_THROW( Too_Many_Hints ); + goto Fail; + } + #ifdef TT_USE_BYTECODE_INTERPRETER if ( IS_HINTED( load->load_flags ) ) { - FT_ULong tmp; + TT_ExecContext exec = load->exec; + FT_Memory memory = exec->memory; - /* check instructions size */ - if ( ( limit - p ) < n_ins ) - { - FT_TRACE1(( "TT_Load_Simple_Glyph: instruction count mismatch\n" )); - error = FT_THROW( Too_Many_Hints ); - goto Fail; - } + if ( exec->glyphSize ) + FT_FREE( exec->glyphIns ); + exec->glyphSize = 0; /* we don't trust `maxSizeOfInstructions' in the `maxp' table */ - /* and thus update the bytecode array size by ourselves */ - - tmp = load->exec->glyphSize; - error = Update_Max( load->exec->memory, - &tmp, - sizeof ( FT_Byte ), - (void*)&load->exec->glyphIns, - n_ins ); - - load->exec->glyphSize = (FT_UShort)tmp; - if ( error ) - return error; + /* and thus allocate the bytecode array size by ourselves */ + if ( n_ins ) + { + if ( FT_QNEW_ARRAY( exec->glyphIns, n_ins ) ) + return error; - load->glyph->control_len = n_ins; - load->glyph->control_data = load->exec->glyphIns; + FT_MEM_COPY( exec->glyphIns, p, (FT_Long)n_ins ); - if ( n_ins ) - FT_MEM_COPY( load->exec->glyphIns, p, (FT_Long)n_ins ); + exec->glyphSize = n_ins; + } } #endif /* TT_USE_BYTECODE_INTERPRETER */ p += n_ins; - outline = &gloader->current.outline; - /* reading the point tags */ flag = (FT_Byte*)outline->tags; flag_limit = flag + n_points; @@ -489,6 +457,10 @@ } } + /* retain the overlap flag */ + if ( n_points && outline->tags[0] & OVERLAP_SIMPLE ) + gloader->base.outline.flags |= FT_OUTLINE_OVERLAP; + /* reading the X coordinates */ vec = outline->points; @@ -496,9 +468,6 @@ flag = (FT_Byte*)outline->tags; x = 0; - if ( p + xy_size > limit ) - goto Invalid_Outline; - for ( ; vec < vec_limit; vec++, flag++ ) { FT_Pos delta = 0; @@ -528,7 +497,7 @@ /* reading the Y coordinates */ - vec = gloader->current.outline.points; + vec = outline->points; vec_limit = vec + n_points; flag = (FT_Byte*)outline->tags; y = 0; @@ -721,18 +690,20 @@ if ( subglyph->flags & WE_HAVE_A_SCALE ) FT_TRACE7(( " scaling: %f\n", - subglyph->transform.xx / 65536.0 )); + (double)subglyph->transform.xx / 65536 )); else if ( subglyph->flags & WE_HAVE_AN_XY_SCALE ) FT_TRACE7(( " scaling: x=%f, y=%f\n", - subglyph->transform.xx / 65536.0, - subglyph->transform.yy / 65536.0 )); + (double)subglyph->transform.xx / 65536, + (double)subglyph->transform.yy / 65536 )); else if ( subglyph->flags & WE_HAVE_A_2X2 ) - FT_TRACE7(( " scaling: xx=%f, yx=%f\n" - " xy=%f, yy=%f\n", - subglyph->transform.xx / 65536.0, - subglyph->transform.yx / 65536.0, - subglyph->transform.xy / 65536.0, - subglyph->transform.yy / 65536.0 )); + { + FT_TRACE7(( " scaling: xx=%f, yx=%f\n", + (double)subglyph->transform.xx / 65536, + (double)subglyph->transform.yx / 65536 )); + FT_TRACE7(( " xy=%f, yy=%f\n", + (double)subglyph->transform.xy / 65536, + (double)subglyph->transform.yy / 65536 )); + } subglyph++; } @@ -783,7 +754,7 @@ FT_UInt start_point, FT_UInt start_contour ) { - zone->n_points = (FT_UShort)load->outline.n_points - + zone->n_points = (FT_UShort)load->outline.n_points + 4 - (FT_UShort)start_point; zone->n_contours = load->outline.n_contours - (FT_Short)start_contour; @@ -809,8 +780,7 @@ TT_Hint_Glyph( TT_Loader loader, FT_Bool is_composite ) { -#if defined TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY || \ - defined TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL +#ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL TT_Face face = loader->face; TT_Driver driver = (TT_Driver)FT_FACE_DRIVER( face ); #endif @@ -818,35 +788,34 @@ TT_GlyphZone zone = &loader->zone; #ifdef TT_USE_BYTECODE_INTERPRETER - FT_Long n_ins; + TT_ExecContext exec = loader->exec; + FT_Long n_ins = exec->glyphSize; #else FT_UNUSED( is_composite ); #endif #ifdef TT_USE_BYTECODE_INTERPRETER - n_ins = loader->glyph->control_len; - /* save original point positions in `org' array */ if ( n_ins > 0 ) FT_ARRAY_COPY( zone->org, zone->cur, zone->n_points ); /* Reset graphics state. */ - loader->exec->GS = loader->size->GS; + exec->GS = loader->size->GS; /* XXX: UNDOCUMENTED! Hinting instructions of a composite glyph */ /* completely refer to the (already) hinted subglyphs. */ if ( is_composite ) { - loader->exec->metrics.x_scale = 1 << 16; - loader->exec->metrics.y_scale = 1 << 16; + exec->metrics.x_scale = 1 << 16; + exec->metrics.y_scale = 1 << 16; FT_ARRAY_COPY( zone->orus, zone->cur, zone->n_points ); } else { - loader->exec->metrics.x_scale = loader->size->metrics->x_scale; - loader->exec->metrics.y_scale = loader->size->metrics->y_scale; + exec->metrics.x_scale = loader->size->metrics->x_scale; + exec->metrics.y_scale = loader->size->metrics->y_scale; } #endif @@ -866,53 +835,37 @@ { FT_Error error; - FT_GlyphLoader gloader = loader->gloader; - FT_Outline current_outline = gloader->current.outline; + TT_Set_CodeRange( exec, tt_coderange_glyph, exec->glyphIns, n_ins ); - TT_Set_CodeRange( loader->exec, tt_coderange_glyph, - loader->exec->glyphIns, n_ins ); + exec->is_composite = is_composite; + exec->pts = *zone; - loader->exec->is_composite = is_composite; - loader->exec->pts = *zone; - - error = TT_Run_Context( loader->exec ); - if ( error && loader->exec->pedantic_hinting ) + error = TT_Run_Context( exec ); + if ( error && exec->pedantic_hinting ) return error; /* store drop-out mode in bits 5-7; set bit 2 also as a marker */ - current_outline.tags[0] |= - ( loader->exec->GS.scan_type << 5 ) | FT_CURVE_TAG_HAS_SCANMODE; + loader->gloader->current.outline.tags[0] |= + ( exec->GS.scan_type << 5 ) | FT_CURVE_TAG_HAS_SCANMODE; } #endif -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL /* Save possibly modified glyph phantom points unless in v40 backward */ /* compatibility mode, where no movement on the x axis means no reason */ /* to change bearings or advance widths. */ - if ( !( driver->interpreter_version == TT_INTERPRETER_VERSION_40 && - loader->exec->backward_compatibility ) ) - { -#endif - loader->pp1 = zone->cur[zone->n_points - 4]; - loader->pp2 = zone->cur[zone->n_points - 3]; - loader->pp3 = zone->cur[zone->n_points - 2]; - loader->pp4 = zone->cur[zone->n_points - 1]; + #ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL - } + if ( driver->interpreter_version == TT_INTERPRETER_VERSION_40 && + exec->backward_compatibility ) + return FT_Err_Ok; #endif -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( driver->interpreter_version == TT_INTERPRETER_VERSION_38 ) - { - if ( loader->exec->sph_tweak_flags & SPH_TWEAK_DEEMBOLDEN ) - FT_Outline_EmboldenXY( &loader->gloader->current.outline, -24, 0 ); - - else if ( loader->exec->sph_tweak_flags & SPH_TWEAK_EMBOLDEN ) - FT_Outline_EmboldenXY( &loader->gloader->current.outline, 24, 0 ); - } -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ + loader->pp1 = zone->cur[zone->n_points - 4]; + loader->pp2 = zone->cur[zone->n_points - 3]; + loader->pp3 = zone->cur[zone->n_points - 2]; + loader->pp4 = zone->cur[zone->n_points - 1]; return FT_Err_Ok; } @@ -931,10 +884,10 @@ static FT_Error TT_Process_Simple_Glyph( TT_Loader loader ) { - FT_GlyphLoader gloader = loader->gloader; - FT_Error error = FT_Err_Ok; - FT_Outline* outline; - FT_Int n_points; + FT_Error error = FT_Err_Ok; + FT_GlyphLoader gloader = loader->gloader; + FT_Outline* outline = &gloader->current.outline; + FT_Int n_points = outline->n_points; #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT FT_Memory memory = loader->face->root.memory; @@ -942,49 +895,25 @@ #endif - outline = &gloader->current.outline; - n_points = outline->n_points; - /* set phantom points */ - outline->points[n_points ] = loader->pp1; outline->points[n_points + 1] = loader->pp2; outline->points[n_points + 2] = loader->pp3; outline->points[n_points + 3] = loader->pp4; - outline->tags[n_points ] = 0; - outline->tags[n_points + 1] = 0; - outline->tags[n_points + 2] = 0; - outline->tags[n_points + 3] = 0; - n_points += 4; #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT if ( !IS_DEFAULT_INSTANCE( FT_FACE( loader->face ) ) ) { - if ( FT_NEW_ARRAY( unrounded, n_points ) ) + if ( FT_QNEW_ARRAY( unrounded, n_points ) ) goto Exit; /* Deltas apply to the unscaled data. */ - error = TT_Vary_Apply_Glyph_Deltas( loader->face, - loader->glyph_index, + error = TT_Vary_Apply_Glyph_Deltas( loader, outline, - unrounded, - (FT_UInt)n_points ); - - /* recalculate linear horizontal and vertical advances */ - /* if we don't have HVAR and VVAR, respectively */ - - /* XXX: change all FreeType modules to store `linear' and `vadvance' */ - /* in 26.6 format before the `base' module scales them to 16.16 */ - if ( !( loader->face->variation_support & TT_FACE_FLAG_VAR_HADVANCE ) ) - loader->linear = FT_PIX_ROUND( unrounded[n_points - 3].x - - unrounded[n_points - 4].x ) / 64; - if ( !( loader->face->variation_support & TT_FACE_FLAG_VAR_VADVANCE ) ) - loader->vadvance = FT_PIX_ROUND( unrounded[n_points - 1].x - - unrounded[n_points - 2].x ) / 64; - + unrounded ); if ( error ) goto Exit; } @@ -996,20 +925,10 @@ tt_prepare_zone( &loader->zone, &gloader->current, 0, 0 ); FT_ARRAY_COPY( loader->zone.orus, loader->zone.cur, - loader->zone.n_points + 4 ); + loader->zone.n_points ); } { -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - TT_Face face = loader->face; - TT_Driver driver = (TT_Driver)FT_FACE_DRIVER( face ); - - FT_String* family = face->root.family_name; - FT_UInt ppem = loader->size->metrics->x_ppem; - FT_String* style = face->root.style_name; - FT_UInt x_scale_factor = 1000; -#endif - FT_Vector* vec = outline->points; FT_Vector* limit = outline->points + n_points; @@ -1019,52 +938,6 @@ FT_Bool do_scale = FALSE; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - - if ( driver->interpreter_version == TT_INTERPRETER_VERSION_38 ) - { - /* scale, but only if enabled and only if TT hinting is being used */ - if ( IS_HINTED( loader->load_flags ) ) - x_scale_factor = sph_test_tweak_x_scaling( face, - family, - ppem, - style, - loader->glyph_index ); - /* scale the glyph */ - if ( ( loader->load_flags & FT_LOAD_NO_SCALE ) == 0 || - x_scale_factor != 1000 ) - { - x_scale = FT_MulDiv( loader->size->metrics->x_scale, - (FT_Long)x_scale_factor, 1000 ); - y_scale = loader->size->metrics->y_scale; - - /* compensate for any scaling by de/emboldening; */ - /* the amount was determined via experimentation */ - if ( x_scale_factor != 1000 && ppem > 11 ) - { -#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT - FT_Vector* orig_points = outline->points; - - - if ( !IS_DEFAULT_INSTANCE( FT_FACE( loader->face ) ) ) - outline->points = unrounded; -#endif - FT_Outline_EmboldenXY( outline, - FT_MulFix( 1280 * ppem, - 1000 - x_scale_factor ), - 0 ); -#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT - if ( !IS_DEFAULT_INSTANCE( FT_FACE( loader->face ) ) ) - outline->points = orig_points; -#endif - } - do_scale = TRUE; - } - } - else - -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - { /* scale the glyph */ if ( ( loader->load_flags & FT_LOAD_NO_SCALE ) == 0 ) @@ -1086,8 +959,8 @@ for ( ; vec < limit; vec++, u++ ) { - vec->x = ( FT_MulFix( u->x, x_scale ) + 32 ) >> 6; - vec->y = ( FT_MulFix( u->y, y_scale ) + 32 ) >> 6; + vec->x = ADD_LONG( FT_MulFix( u->x, x_scale ), 32 ) >> 6; + vec->y = ADD_LONG( FT_MulFix( u->y, y_scale ), 32 ) >> 6; } } else @@ -1138,11 +1011,7 @@ } if ( IS_HINTED( loader->load_flags ) ) - { - loader->zone.n_points += 4; - error = TT_Hint_Glyph( loader, 0 ); - } #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT Exit: @@ -1210,8 +1079,8 @@ p1 = gloader->base.outline.points + k; p2 = gloader->base.outline.points + l; - x = p1->x - p2->x; - y = p1->y - p2->y; + x = SUB_LONG( p1->x, p2->x ); + y = SUB_LONG( p1->y, p2->y ); } else { @@ -1337,12 +1206,12 @@ FT_UInt start_contour ) { FT_Error error; - FT_Outline* outline; + FT_Outline* outline = &loader->gloader->base.outline; + FT_Stream stream = loader->stream; + FT_UShort n_ins; FT_UInt i; - outline = &loader->gloader->base.outline; - /* make room for phantom points */ error = FT_GLYPHLOADER_CHECK_POINTS( loader->gloader, outline->n_points + 4, @@ -1355,60 +1224,43 @@ outline->points[outline->n_points + 2] = loader->pp3; outline->points[outline->n_points + 3] = loader->pp4; - outline->tags[outline->n_points ] = 0; - outline->tags[outline->n_points + 1] = 0; - outline->tags[outline->n_points + 2] = 0; - outline->tags[outline->n_points + 3] = 0; - #ifdef TT_USE_BYTECODE_INTERPRETER { - FT_Stream stream = loader->stream; - FT_UShort n_ins, max_ins; - FT_ULong tmp; + TT_ExecContext exec = loader->exec; + FT_Memory memory = exec->memory; + if ( exec->glyphSize ) + FT_FREE( exec->glyphIns ); + exec->glyphSize = 0; + /* TT_Load_Composite_Glyph only gives us the offset of instructions */ /* so we read them here */ if ( FT_STREAM_SEEK( loader->ins_pos ) || FT_READ_USHORT( n_ins ) ) return error; - FT_TRACE5(( " Instructions size = %d\n", n_ins )); - - /* check it */ - max_ins = loader->face->max_profile.maxSizeOfInstructions; - if ( n_ins > max_ins ) - { - /* don't trust `maxSizeOfInstructions'; */ - /* only do a rough safety check */ - if ( (FT_Int)n_ins > loader->byte_len ) - { - FT_TRACE1(( "TT_Process_Composite_Glyph:" - " too many instructions (%d) for glyph with length %d\n", - n_ins, loader->byte_len )); - return FT_THROW( Too_Many_Hints ); - } + FT_TRACE5(( " Instructions size = %hu\n", n_ins )); - tmp = loader->exec->glyphSize; - error = Update_Max( loader->exec->memory, - &tmp, - sizeof ( FT_Byte ), - (void*)&loader->exec->glyphIns, - n_ins ); + if ( !n_ins ) + return FT_Err_Ok; - loader->exec->glyphSize = (FT_UShort)tmp; - if ( error ) - return error; + /* don't trust `maxSizeOfInstructions'; */ + /* only do a rough safety check */ + if ( n_ins > loader->byte_len ) + { + FT_TRACE1(( "TT_Process_Composite_Glyph:" + " too many instructions (%hu) for glyph with length %u\n", + n_ins, loader->byte_len )); + return FT_THROW( Too_Many_Hints ); } - else if ( n_ins == 0 ) - return FT_Err_Ok; - if ( FT_STREAM_READ( loader->exec->glyphIns, n_ins ) ) + if ( FT_QNEW_ARRAY( exec->glyphIns, n_ins ) || + FT_STREAM_READ( exec->glyphIns, n_ins ) ) return error; - loader->glyph->control_data = loader->exec->glyphIns; - loader->glyph->control_len = n_ins; + exec->glyphSize = n_ins; } #endif @@ -1418,11 +1270,9 @@ /* Some points are likely touched during execution of */ /* instructions on components. So let's untouch them. */ - for ( i = 0; i < loader->zone.n_points; i++ ) + for ( i = 0; i < loader->zone.n_points - 4U; i++ ) loader->zone.tags[i] &= ~FT_CURVE_TAG_TOUCH_BOTH; - loader->zone.n_points += 4; - return TT_Hint_Glyph( loader, 1 ); } @@ -1514,45 +1364,31 @@ static void tt_loader_set_pp( TT_Loader loader ) { - FT_Bool subpixel_hinting = 0; - FT_Bool grayscale = 0; - FT_Bool use_aw_2 = 0; - -#ifdef TT_CONFIG_OPTION_SUBPIXEL_HINTING - TT_Driver driver = (TT_Driver)FT_FACE_DRIVER( loader->face ); -#endif - - -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( driver->interpreter_version == TT_INTERPRETER_VERSION_38 ) - { - subpixel_hinting = loader->exec ? loader->exec->subpixel_hinting - : 0; - grayscale = loader->exec ? loader->exec->grayscale - : 0; - } -#endif -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL - if ( driver->interpreter_version == TT_INTERPRETER_VERSION_40 ) - { - subpixel_hinting = loader->exec ? loader->exec->subpixel_hinting_lean - : 0; - grayscale = loader->exec ? loader->exec->grayscale_cleartype - : 0; - } -#endif - - use_aw_2 = FT_BOOL( subpixel_hinting && grayscale ); - loader->pp1.x = loader->bbox.xMin - loader->left_bearing; loader->pp1.y = 0; loader->pp2.x = loader->pp1.x + loader->advance; loader->pp2.y = 0; - loader->pp3.x = use_aw_2 ? loader->advance / 2 : 0; + loader->pp3.x = 0; loader->pp3.y = loader->bbox.yMax + loader->top_bearing; - loader->pp4.x = use_aw_2 ? loader->advance / 2 : 0; + loader->pp4.x = 0; loader->pp4.y = loader->pp3.y - loader->vadvance; + +#ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL + { + TT_Driver driver = (TT_Driver)FT_FACE_DRIVER( loader->face ); + + + if ( driver->interpreter_version == TT_INTERPRETER_VERSION_40 && + loader->exec && + loader->exec->subpixel_hinting_lean && + loader->exec->grayscale_cleartype ) + { + loader->pp3.x = loader->advance / 2; + loader->pp4.x = loader->advance / 2; + } + } +#endif } @@ -1668,16 +1504,21 @@ FT_ZERO( &inc_stream ); FT_Stream_OpenMemory( &inc_stream, glyph_data.pointer, - (FT_ULong)glyph_data.length ); + glyph_data.length ); loader->stream = &inc_stream; } else #endif /* FT_CONFIG_OPTION_INCREMENTAL */ + { + FT_ULong len; + - offset = tt_face_get_location( face, glyph_index, - (FT_UInt*)&loader->byte_len ); + offset = tt_face_get_location( FT_FACE( face ), glyph_index, &len ); + + loader->byte_len = (FT_UInt)len; + } if ( loader->byte_len > 0 ) { @@ -1696,7 +1537,7 @@ error = face->access_glyph_frame( loader, glyph_index, face->glyf_offset + offset, - (FT_UInt)loader->byte_len ); + loader->byte_len ); if ( error ) goto Exit; @@ -1730,13 +1571,11 @@ if ( loader->byte_len == 0 || loader->n_contours == 0 ) { - /* must initialize points before (possibly) overriding */ - /* glyph metrics from the incremental interface */ - tt_loader_set_pp( loader ); - #ifdef FT_CONFIG_OPTION_INCREMENTAL - tt_get_metrics_incr_overrides( loader, glyph_index ); + tt_get_metrics_incremental( loader, glyph_index ); #endif + tt_loader_set_pp( loader ); + #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT @@ -1746,57 +1585,29 @@ /* a small outline structure with four elements for */ /* communication with `TT_Vary_Apply_Glyph_Deltas' */ FT_Vector points[4]; - char tags[4] = { 1, 1, 1, 1 }; - short contours[4] = { 0, 1, 2, 3 }; FT_Outline outline; /* unrounded values */ FT_Vector unrounded[4] = { {0, 0}, {0, 0}, {0, 0}, {0, 0} }; - points[0].x = loader->pp1.x; - points[0].y = loader->pp1.y; - points[1].x = loader->pp2.x; - points[1].y = loader->pp2.y; + points[0] = loader->pp1; + points[1] = loader->pp2; + points[2] = loader->pp3; + points[3] = loader->pp4; - points[2].x = loader->pp3.x; - points[2].y = loader->pp3.y; - points[3].x = loader->pp4.x; - points[3].y = loader->pp4.y; - - outline.n_points = 4; - outline.n_contours = 4; + outline.n_points = 0; + outline.n_contours = 0; outline.points = points; - outline.tags = tags; - outline.contours = contours; + outline.tags = NULL; + outline.contours = NULL; /* this must be done before scaling */ - error = TT_Vary_Apply_Glyph_Deltas( loader->face, - glyph_index, + error = TT_Vary_Apply_Glyph_Deltas( loader, &outline, - unrounded, - (FT_UInt)outline.n_points ); + unrounded ); if ( error ) goto Exit; - - loader->pp1.x = points[0].x; - loader->pp1.y = points[0].y; - loader->pp2.x = points[1].x; - loader->pp2.y = points[1].y; - - loader->pp3.x = points[2].x; - loader->pp3.y = points[2].y; - loader->pp4.x = points[3].x; - loader->pp4.y = points[3].y; - - /* recalculate linear horizontal and vertical advances */ - /* if we don't have HVAR and VVAR, respectively */ - if ( !( loader->face->variation_support & TT_FACE_FLAG_VAR_HADVANCE ) ) - loader->linear = FT_PIX_ROUND( unrounded[1].x - - unrounded[0].x ) / 64; - if ( !( loader->face->variation_support & TT_FACE_FLAG_VAR_VADVANCE ) ) - loader->vadvance = FT_PIX_ROUND( unrounded[3].x - - unrounded[2].x ) / 64; } #endif /* TT_CONFIG_OPTION_GX_VAR_SUPPORT */ @@ -1819,13 +1630,11 @@ goto Exit; } - /* must initialize phantom points before (possibly) overriding */ - /* glyph metrics from the incremental interface */ - tt_loader_set_pp( loader ); - #ifdef FT_CONFIG_OPTION_INCREMENTAL - tt_get_metrics_incr_overrides( loader, glyph_index ); + tt_get_metrics_incremental( loader, glyph_index ); #endif + tt_loader_set_pp( loader ); + /***********************************************************************/ /***********************************************************************/ @@ -1835,7 +1644,7 @@ /* (which consists of 10 bytes) */ error = face->access_glyph_frame( loader, glyph_index, face->glyf_offset + offset + 10, - (FT_UInt)loader->byte_len - 10 ); + loader->byte_len - 10 ); if ( error ) goto Exit; @@ -1889,7 +1698,7 @@ /* clear the nodes filled by sibling chains */ node = ft_list_get_node_at( &loader->composites, recurse_count ); for ( node2 = node; node2; node2 = node2->next ) - node2->data = (void*)FT_ULONG_MAX; + node2->data = (void*)-1; /* check whether we already have a composite glyph with this index */ if ( FT_List_Find( &loader->composites, @@ -1906,7 +1715,7 @@ else { - if ( FT_NEW( node ) ) + if ( FT_QNEW( node ) ) goto Exit; node->data = FT_UINT_TO_POINTER( glyph_index ); FT_List_Add( &loader->composites, node ); @@ -1935,10 +1744,7 @@ short i, limit; FT_SubGlyph subglyph; - FT_Outline outline; - FT_Vector* points = NULL; - char* tags = NULL; - short* contours = NULL; + FT_Outline outline = { 0, 0, NULL, NULL, NULL, 0 }; FT_Vector* unrounded = NULL; @@ -1946,19 +1752,14 @@ /* construct an outline structure for */ /* communication with `TT_Vary_Apply_Glyph_Deltas' */ - outline.n_points = (short)( gloader->current.num_subglyphs + 4 ); - outline.n_contours = outline.n_points; - - outline.points = NULL; - outline.tags = NULL; - outline.contours = NULL; - - if ( FT_NEW_ARRAY( points, outline.n_points ) || - FT_NEW_ARRAY( tags, outline.n_points ) || - FT_NEW_ARRAY( contours, outline.n_points ) || - FT_NEW_ARRAY( unrounded, outline.n_points ) ) + if ( FT_QNEW_ARRAY( outline.points, limit + 4 ) || + FT_QNEW_ARRAY( outline.tags, limit ) || + FT_QNEW_ARRAY( outline.contours, limit ) || + FT_QNEW_ARRAY( unrounded, limit + 4 ) ) goto Exit1; + outline.n_contours = outline.n_points = limit; + subglyph = gloader->current.subglyphs; for ( i = 0; i < limit; i++, subglyph++ ) @@ -1966,47 +1767,22 @@ /* applying deltas for anchor points doesn't make sense, */ /* but we don't have to specially check this since */ /* unused delta values are zero anyways */ - points[i].x = subglyph->arg1; - points[i].y = subglyph->arg2; - tags[i] = 1; - contours[i] = i; + outline.points[i].x = subglyph->arg1; + outline.points[i].y = subglyph->arg2; + outline.tags[i] = ON_CURVE_POINT; + outline.contours[i] = i; } - points[i].x = loader->pp1.x; - points[i].y = loader->pp1.y; - tags[i] = 1; - contours[i] = i; - - i++; - points[i].x = loader->pp2.x; - points[i].y = loader->pp2.y; - tags[i] = 1; - contours[i] = i; - - i++; - points[i].x = loader->pp3.x; - points[i].y = loader->pp3.y; - tags[i] = 1; - contours[i] = i; - - i++; - points[i].x = loader->pp4.x; - points[i].y = loader->pp4.y; - tags[i] = 1; - contours[i] = i; - - outline.points = points; - outline.tags = tags; - outline.contours = contours; + outline.points[i++] = loader->pp1; + outline.points[i++] = loader->pp2; + outline.points[i++] = loader->pp3; + outline.points[i ] = loader->pp4; /* this call provides additional offsets */ /* for each component's translation */ - if ( FT_SET_ERROR( TT_Vary_Apply_Glyph_Deltas( - face, - glyph_index, - &outline, - unrounded, - (FT_UInt)outline.n_points ) ) ) + if ( FT_SET_ERROR( TT_Vary_Apply_Glyph_Deltas( loader, + &outline, + unrounded ) ) ) goto Exit1; subglyph = gloader->current.subglyphs; @@ -2015,32 +1791,11 @@ { if ( subglyph->flags & ARGS_ARE_XY_VALUES ) { - subglyph->arg1 = (FT_Int16)points[i].x; - subglyph->arg2 = (FT_Int16)points[i].y; + subglyph->arg1 = (FT_Int16)outline.points[i].x; + subglyph->arg2 = (FT_Int16)outline.points[i].y; } } - loader->pp1.x = points[i + 0].x; - loader->pp1.y = points[i + 0].y; - loader->pp2.x = points[i + 1].x; - loader->pp2.y = points[i + 1].y; - - loader->pp3.x = points[i + 2].x; - loader->pp3.y = points[i + 2].y; - loader->pp4.x = points[i + 3].x; - loader->pp4.y = points[i + 3].y; - - /* recalculate linear horizontal and vertical advances */ - /* if we don't have HVAR and VVAR, respectively */ - if ( !( face->variation_support & TT_FACE_FLAG_VAR_HADVANCE ) ) - loader->linear = - FT_PIX_ROUND( unrounded[outline.n_points - 3].x - - unrounded[outline.n_points - 4].x ) / 64; - if ( !( face->variation_support & TT_FACE_FLAG_VAR_VADVANCE ) ) - loader->vadvance = - FT_PIX_ROUND( unrounded[outline.n_points - 1].x - - unrounded[outline.n_points - 2].x ) / 64; - Exit1: FT_FREE( outline.points ); FT_FREE( outline.tags ); @@ -2091,7 +1846,7 @@ FT_UInt num_base_subgs = gloader->base.num_subglyphs; FT_Stream old_stream = loader->stream; - FT_Int old_byte_len = loader->byte_len; + FT_UInt old_byte_len = loader->byte_len; FT_GlyphLoader_Add( gloader ); @@ -2183,6 +1938,11 @@ goto Exit; } } + + /* retain the overlap flag */ + if ( gloader->base.num_subglyphs && + gloader->base.subglyphs[0].flags & OVERLAP_COMPOUND ) + gloader->base.outline.flags |= FT_OUTLINE_OVERLAP; } /***********************************************************************/ @@ -2211,16 +1971,11 @@ compute_glyph_metrics( TT_Loader loader, FT_UInt glyph_index ) { - TT_Face face = loader->face; -#if defined TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY || \ - defined TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL - TT_Driver driver = (TT_Driver)FT_FACE_DRIVER( face ); -#endif - + TT_Face face = loader->face; + TT_Size size = loader->size; + TT_GlyphSlot glyph = loader->glyph; FT_BBox bbox; FT_Fixed y_scale; - TT_GlyphSlot glyph = loader->glyph; - TT_Size size = loader->size; y_scale = 0x10000L; @@ -2238,53 +1993,10 @@ glyph->metrics.horiBearingX = bbox.xMin; glyph->metrics.horiBearingY = bbox.yMax; - glyph->metrics.horiAdvance = SUB_LONG(loader->pp2.x, loader->pp1.x); - - /* Adjust advance width to the value contained in the hdmx table */ - /* unless FT_LOAD_COMPUTE_METRICS is set or backward compatibility */ - /* mode of the v40 interpreter is active. See `ttinterp.h' for */ - /* details on backward compatibility mode. */ - if ( -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL - !( driver->interpreter_version == TT_INTERPRETER_VERSION_40 && - ( loader->exec && loader->exec->backward_compatibility ) ) && -#endif - !face->postscript.isFixedPitch && - IS_HINTED( loader->load_flags ) && - !( loader->load_flags & FT_LOAD_COMPUTE_METRICS ) ) - { - FT_Byte* widthp; - - - widthp = tt_face_get_device_metrics( face, - size->metrics->x_ppem, - glyph_index ); - -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - - if ( driver->interpreter_version == TT_INTERPRETER_VERSION_38 ) - { - FT_Bool ignore_x_mode; - - - ignore_x_mode = FT_BOOL( FT_LOAD_TARGET_MODE( loader->load_flags ) != - FT_RENDER_MODE_MONO ); - - if ( widthp && - ( ( ignore_x_mode && loader->exec->compatible_widths ) || - !ignore_x_mode || - SPH_OPTION_BITMAP_WIDTHS ) ) - glyph->metrics.horiAdvance = *widthp * 64; - } - else - -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - - { - if ( widthp ) - glyph->metrics.horiAdvance = *widthp * 64; - } - } + if ( loader->widthp ) + glyph->metrics.horiAdvance = loader->widthp[glyph_index] * 64; + else + glyph->metrics.horiAdvance = SUB_LONG( loader->pp2.x, loader->pp1.x ); /* set glyph dimensions */ glyph->metrics.width = SUB_LONG( bbox.xMax, bbox.xMin ); @@ -2401,17 +2113,13 @@ FT_UInt glyph_index, FT_Int32 load_flags ) { - TT_Face face; - SFNT_Service sfnt; - FT_Stream stream; + TT_Face face = (TT_Face)glyph->face; + SFNT_Service sfnt = (SFNT_Service)face->sfnt; + FT_Stream stream = face->root.stream; FT_Error error; TT_SBit_MetricsRec sbit_metrics; - face = (TT_Face)glyph->face; - sfnt = (SFNT_Service)face->sfnt; - stream = face->root.stream; - error = sfnt->load_sbit_image( face, size->strike_index, glyph_index, @@ -2462,22 +2170,18 @@ FT_Int32 load_flags, FT_Bool glyf_table_only ) { - TT_Face face; - FT_Stream stream; + TT_Face face = (TT_Face)glyph->face; + FT_Stream stream = face->root.stream; #ifdef TT_USE_BYTECODE_INTERPRETER FT_Error error; FT_Bool pedantic = FT_BOOL( load_flags & FT_LOAD_PEDANTIC ); -#if defined TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY || \ - defined TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL - TT_Driver driver = (TT_Driver)FT_FACE_DRIVER( (TT_Face)glyph->face ); +#ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL + TT_Driver driver = (TT_Driver)FT_FACE_DRIVER( glyph->face ); #endif #endif - face = (TT_Face)glyph->face; - stream = face->root.stream; - FT_ZERO( loader ); #ifdef TT_USE_BYTECODE_INTERPRETER @@ -2492,20 +2196,6 @@ FT_Bool grayscale_cleartype; #endif -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - FT_Bool subpixel_hinting = FALSE; - -#if 0 - /* not used yet */ - FT_Bool compatible_widths; - FT_Bool symmetrical_smoothing; - FT_Bool bgr; - FT_Bool vertical_lcd; - FT_Bool subpixel_positioned; - FT_Bool gray_cleartype; -#endif -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - FT_Bool reexecute = FALSE; @@ -2525,6 +2215,9 @@ if ( !exec ) return FT_THROW( Could_Not_Find_Context ); + grayscale = FT_BOOL( FT_LOAD_TARGET_MODE( load_flags ) != + FT_RENDER_MODE_MONO ); + #ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL if ( driver->interpreter_version == TT_INTERPRETER_VERSION_40 ) { @@ -2541,6 +2234,7 @@ FT_BOOL( subpixel_hinting_lean && ( load_flags & FT_LOAD_TARGET_LCD_V ) ); + grayscale = FT_BOOL( grayscale && !subpixel_hinting_lean ); } else { @@ -2550,111 +2244,11 @@ } #endif -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - - if ( driver->interpreter_version == TT_INTERPRETER_VERSION_38 ) - { - subpixel_hinting = FT_BOOL( ( FT_LOAD_TARGET_MODE( load_flags ) != - FT_RENDER_MODE_MONO ) && - SPH_OPTION_SET_SUBPIXEL ); - - if ( subpixel_hinting ) - grayscale = FALSE; - else if ( SPH_OPTION_SET_GRAYSCALE ) - { - grayscale = TRUE; - subpixel_hinting = FALSE; - } - else - grayscale = FALSE; - - if ( FT_IS_TRICKY( glyph->face ) ) - subpixel_hinting = FALSE; - - exec->ignore_x_mode = subpixel_hinting || grayscale; - exec->rasterizer_version = SPH_OPTION_SET_RASTERIZER_VERSION; - if ( exec->sph_tweak_flags & SPH_TWEAK_RASTERIZER_35 ) - exec->rasterizer_version = TT_INTERPRETER_VERSION_35; - -#if 1 - exec->compatible_widths = SPH_OPTION_SET_COMPATIBLE_WIDTHS; - exec->symmetrical_smoothing = TRUE; - exec->bgr = FALSE; - exec->vertical_lcd = FALSE; - exec->subpixel_positioned = TRUE; - exec->gray_cleartype = FALSE; -#else /* 0 */ - exec->compatible_widths = - FT_BOOL( FT_LOAD_TARGET_MODE( load_flags ) != - TT_LOAD_COMPATIBLE_WIDTHS ); - exec->symmetrical_smoothing = - FT_BOOL( FT_LOAD_TARGET_MODE( load_flags ) != - TT_LOAD_SYMMETRICAL_SMOOTHING ); - exec->bgr = - FT_BOOL( FT_LOAD_TARGET_MODE( load_flags ) != - TT_LOAD_BGR ); - exec->vertical_lcd = - FT_BOOL( FT_LOAD_TARGET_MODE( load_flags ) != - TT_LOAD_VERTICAL_LCD ); - exec->subpixel_positioned = - FT_BOOL( FT_LOAD_TARGET_MODE( load_flags ) != - TT_LOAD_SUBPIXEL_POSITIONED ); - exec->gray_cleartype = - FT_BOOL( FT_LOAD_TARGET_MODE( load_flags ) != - TT_LOAD_GRAY_CLEARTYPE ); -#endif /* 0 */ - - } - else - -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL - if ( driver->interpreter_version == TT_INTERPRETER_VERSION_40 ) - grayscale = FT_BOOL( !subpixel_hinting_lean && - FT_LOAD_TARGET_MODE( load_flags ) != - FT_RENDER_MODE_MONO ); - else -#endif - grayscale = FT_BOOL( FT_LOAD_TARGET_MODE( load_flags ) != - FT_RENDER_MODE_MONO ); - error = TT_Load_Context( exec, face, size ); if ( error ) return error; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - - if ( driver->interpreter_version == TT_INTERPRETER_VERSION_38 ) - { - /* a change from mono to subpixel rendering (and vice versa) */ - /* requires a re-execution of the CVT program */ - if ( subpixel_hinting != exec->subpixel_hinting ) - { - FT_TRACE4(( "tt_loader_init: subpixel hinting change," - " re-executing `prep' table\n" )); - - exec->subpixel_hinting = subpixel_hinting; - reexecute = TRUE; - } - - /* a change from mono to grayscale rendering (and vice versa) */ - /* requires a re-execution of the CVT program */ - if ( grayscale != exec->grayscale ) - { - FT_TRACE4(( "tt_loader_init: grayscale hinting change," - " re-executing `prep' table\n" )); - - exec->grayscale = grayscale; - reexecute = TRUE; - } - } - else - -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - { - #ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL if ( driver->interpreter_version == TT_INTERPRETER_VERSION_40 ) { @@ -2699,6 +2293,9 @@ error = tt_size_run_prep( size, pedantic ); if ( error ) return error; + error = TT_Load_Context( exec, face, size ); + if ( error ) + return error; } /* check whether the cvt program has disabled hinting */ @@ -2709,17 +2306,48 @@ if ( exec->GS.instruct_control & 2 ) exec->GS = tt_default_graphics_state; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - /* check whether we have a font hinted for ClearType -- */ - /* note that this flag can also be modified in a glyph's bytecode */ - if ( driver->interpreter_version == TT_INTERPRETER_VERSION_38 && - exec->GS.instruct_control & 4 ) - exec->ignore_x_mode = 0; -#endif +#ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL + /* + * Toggle backward compatibility according to what font wants, except + * when + * + * 1) we have a `tricky' font that heavily relies on the interpreter to + * render glyphs correctly, for example DFKai-SB, or + * 2) FT_RENDER_MODE_MONO (i.e, monochome rendering) is requested. + * + * In those cases, backward compatibility needs to be turned off to get + * correct rendering. The rendering is then completely up to the + * font's programming. + * + */ + if ( driver->interpreter_version == TT_INTERPRETER_VERSION_40 && + subpixel_hinting_lean && + !FT_IS_TRICKY( glyph->face ) ) + exec->backward_compatibility = !( exec->GS.instruct_control & 4 ); + else + exec->backward_compatibility = FALSE; +#endif /* TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL */ exec->pedantic_hinting = FT_BOOL( load_flags & FT_LOAD_PEDANTIC ); loader->exec = exec; loader->instructions = exec->glyphIns; + + /* Use the hdmx table if any unless FT_LOAD_COMPUTE_METRICS */ + /* is set or backward compatibility mode of the v38 or v40 */ + /* interpreters is active. See `ttinterp.h' for details on */ + /* backward compatibility mode. */ + if ( IS_HINTED( loader->load_flags ) && + !( loader->load_flags & FT_LOAD_COMPUTE_METRICS ) && +#ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL + !( driver->interpreter_version == TT_INTERPRETER_VERSION_40 && + exec->backward_compatibility ) && +#endif + !face->postscript.isFixedPitch ) + { + loader->widthp = size->widthp; + } + else + loader->widthp = NULL; } #endif /* TT_USE_BYTECODE_INTERPRETER */ @@ -2767,11 +2395,12 @@ * A function used to load a single glyph within a given glyph slot, * for a given size. * - * @Input: + * @InOut: * glyph :: * A handle to a target slot object where the glyph * will be loaded. * + * @Input: * size :: * A handle to the source face size at which the glyph * must be scaled/loaded. @@ -2795,6 +2424,7 @@ FT_UInt glyph_index, FT_Int32 load_flags ) { + TT_Face face = (TT_Face)glyph->face; FT_Error error; TT_LoaderRec loader; @@ -2819,8 +2449,6 @@ /* if we have a bitmap-only font, return an empty glyph */ if ( !FT_IS_SCALABLE( glyph->face ) ) { - TT_Face face = (TT_Face)glyph->face; - FT_Short left_bearing = 0; FT_Short top_bearing = 0; @@ -2876,7 +2504,8 @@ } else { - if ( FT_IS_SCALABLE( glyph->face ) ) + if ( FT_IS_SCALABLE( glyph->face ) || + FT_HAS_SBIX( glyph->face ) ) { /* for the bbox we need the header only */ (void)tt_loader_init( &loader, size, glyph, load_flags, TRUE ); @@ -2885,6 +2514,35 @@ glyph->linearHoriAdvance = loader.linear; glyph->linearVertAdvance = loader.vadvance; + /* Bitmaps from the 'sbix' table need special treatment: */ + /* if there is a glyph contour, the bitmap origin must be */ + /* shifted to be relative to the lower left corner of the */ + /* glyph bounding box, also taking the left-side bearing */ + /* (or top bearing) into account. */ + if ( face->sbit_table_type == TT_SBIT_TABLE_TYPE_SBIX && + loader.n_contours > 0 ) + { + FT_Int bitmap_left; + FT_Int bitmap_top; + + + if ( load_flags & FT_LOAD_VERTICAL_LAYOUT ) + { + /* This is a guess, since Apple's CoreText engine doesn't */ + /* really do vertical typesetting. */ + bitmap_left = loader.bbox.xMin; + bitmap_top = loader.top_bearing; + } + else + { + bitmap_left = loader.left_bearing; + bitmap_top = loader.bbox.yMin; + } + + glyph->bitmap_left += FT_MulFix( bitmap_left, x_scale ) >> 6; + glyph->bitmap_top += FT_MulFix( bitmap_top, y_scale ) >> 6; + } + /* sanity checks: if `xxxAdvance' in the sbit metric */ /* structure isn't set, use `linearXXXAdvance' */ if ( !glyph->metrics.horiAdvance && glyph->linearHoriAdvance ) @@ -2899,6 +2557,12 @@ } } + if ( load_flags & FT_LOAD_SBITS_ONLY ) + { + error = FT_THROW( Invalid_Argument ); + goto Exit; + } + #endif /* TT_CONFIG_OPTION_EMBEDDED_BITMAPS */ /* if FT_LOAD_NO_SCALE is not set, `ttmetrics' must be valid */ @@ -2908,16 +2572,79 @@ goto Exit; } - if ( load_flags & FT_LOAD_SBITS_ONLY ) +#ifdef FT_CONFIG_OPTION_SVG + + /* check for OT-SVG */ + if ( ( load_flags & FT_LOAD_NO_SVG ) == 0 && + ( load_flags & FT_LOAD_COLOR ) && + face->svg ) + { + SFNT_Service sfnt = (SFNT_Service)face->sfnt; + + + FT_TRACE3(( "Trying to load SVG glyph\n" )); + + error = sfnt->load_svg_doc( glyph, glyph_index ); + if ( !error ) + { + FT_Fixed x_scale = size->root.metrics.x_scale; + FT_Fixed y_scale = size->root.metrics.y_scale; + + FT_Short leftBearing; + FT_Short topBearing; + FT_UShort advanceX; + FT_UShort advanceY; + + + FT_TRACE3(( "Successfully loaded SVG glyph\n" )); + + glyph->format = FT_GLYPH_FORMAT_SVG; + + sfnt->get_metrics( face, + FALSE, + glyph_index, + &leftBearing, + &advanceX ); + sfnt->get_metrics( face, + TRUE, + glyph_index, + &topBearing, + &advanceY ); + + glyph->linearHoriAdvance = advanceX; + glyph->linearVertAdvance = advanceY; + + glyph->metrics.horiAdvance = FT_MulFix( advanceX, x_scale ); + glyph->metrics.vertAdvance = FT_MulFix( advanceY, y_scale ); + + return error; + } + + FT_TRACE3(( "Failed to load SVG glyph\n" )); + } + + /* return immediately if we only want SVG glyphs */ + if ( load_flags & FT_LOAD_SVG_ONLY ) { error = FT_THROW( Invalid_Argument ); goto Exit; } +#endif /* FT_CONFIG_OPTION_SVG */ + error = tt_loader_init( &loader, size, glyph, load_flags, FALSE ); if ( error ) goto Exit; + /* done if we are only interested in the `hdmx` advance */ + if ( load_flags & FT_LOAD_ADVANCE_ONLY && + !( load_flags & FT_LOAD_VERTICAL_LAYOUT ) && + loader.widthp ) + { + glyph->metrics.horiAdvance = loader.widthp[glyph_index] * 64; + goto Done; + } + glyph->format = FT_GLYPH_FORMAT_OUTLINE; glyph->num_subglyphs = 0; glyph->outline.flags = 0; @@ -2948,6 +2675,9 @@ if ( IS_HINTED( load_flags ) ) { + glyph->control_data = loader.exec->glyphIns; + glyph->control_len = loader.exec->glyphSize; + if ( loader.exec->GS.scan_control ) { /* convert scan conversion mode to FT_OUTLINE_XXX flags */ @@ -2981,8 +2711,6 @@ error = compute_glyph_metrics( &loader, glyph_index ); } - tt_loader_done( &loader ); - /* Set the `high precision' bit flag. */ /* This is _critical_ to get correct output for monochrome */ /* TrueType glyphs at all sizes using the bytecode interpreter. */ @@ -2991,6 +2719,16 @@ size->metrics->y_ppem < 24 ) glyph->outline.flags |= FT_OUTLINE_HIGH_PRECISION; + FT_TRACE1(( " subglyphs = %u, contours = %hd, points = %hd," + " flags = 0x%.3x\n", + loader.gloader->base.num_subglyphs, + glyph->outline.n_contours, + glyph->outline.n_points, + glyph->outline.flags )); + + Done: + tt_loader_done( &loader ); + Exit: #ifdef FT_DEBUG_LEVEL_TRACE if ( error ) diff --git a/src/font/freetype-2.10.2/src/truetype/ttgload.h b/3rdparty/freetype-2.13.2/src/truetype/ttgload.h similarity index 96% rename from src/font/freetype-2.10.2/src/truetype/ttgload.h rename to 3rdparty/freetype-2.13.2/src/truetype/ttgload.h index 9a8c3e71d..f18637dce 100644 --- a/src/font/freetype-2.10.2/src/truetype/ttgload.h +++ b/3rdparty/freetype-2.13.2/src/truetype/ttgload.h @@ -4,7 +4,7 @@ * * TrueType Glyph Loader (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,7 +20,6 @@ #define TTGLOAD_H_ -#include #include "ttobjs.h" #ifdef TT_USE_BYTECODE_INTERPRETER diff --git a/src/font/freetype-2.10.2/src/truetype/ttgxvar.c b/3rdparty/freetype-2.13.2/src/truetype/ttgxvar.c similarity index 75% rename from src/font/freetype-2.10.2/src/truetype/ttgxvar.c rename to 3rdparty/freetype-2.13.2/src/truetype/ttgxvar.c index 110f24a11..ad4f266b2 100644 --- a/src/font/freetype-2.10.2/src/truetype/ttgxvar.c +++ b/3rdparty/freetype-2.13.2/src/truetype/ttgxvar.c @@ -4,7 +4,7 @@ * * TrueType GX Font Variation loader * - * Copyright (C) 2004-2020 by + * Copyright (C) 2004-2023 by * David Turner, Robert Wilhelm, Werner Lemberg, and George Williams. * * This file is part of the FreeType project, and may only be used, @@ -40,14 +40,16 @@ #include -#include FT_INTERNAL_DEBUG_H +#include #include FT_CONFIG_CONFIG_H -#include FT_INTERNAL_STREAM_H -#include FT_INTERNAL_SFNT_H -#include FT_TRUETYPE_TAGS_H -#include FT_TRUETYPE_IDS_H -#include FT_MULTIPLE_MASTERS_H -#include FT_LIST_H +#include +#include +#include +#include +#include +#include +#include +#include #include "ttpload.h" #include "ttgxvar.h" @@ -151,9 +153,7 @@ FT_UInt i, j; FT_UShort first; FT_Memory memory = stream->memory; - FT_Error error = FT_Err_Ok; - - FT_UNUSED( error ); + FT_Error error; *point_cnt = 0; @@ -178,7 +178,7 @@ /* in the nested loops below we increase `i' twice; */ /* it is faster to simply allocate one more slot */ /* than to add another test within the loop */ - if ( FT_NEW_ARRAY( points, n + 1 ) ) + if ( FT_QNEW_ARRAY( points, n + 1 ) ) return NULL; *point_cnt = n; @@ -264,55 +264,78 @@ FT_Fixed *deltas = NULL; FT_UInt runcnt, cnt; FT_UInt i, j; + FT_UInt bytes_used; FT_Memory memory = stream->memory; - FT_Error error = FT_Err_Ok; - - FT_UNUSED( error ); + FT_Error error; - if ( delta_cnt > size ) - { - FT_TRACE1(( "ft_var_readpackeddeltas: number of points too large\n" )); + if ( FT_QNEW_ARRAY( deltas, delta_cnt ) ) return NULL; - } - if ( FT_NEW_ARRAY( deltas, delta_cnt ) ) - return NULL; + i = 0; + bytes_used = 0; - i = 0; - while ( i < delta_cnt ) + while ( i < delta_cnt && bytes_used < size ) { runcnt = FT_GET_BYTE(); cnt = runcnt & GX_DT_DELTA_RUN_COUNT_MASK; + bytes_used++; + if ( runcnt & GX_DT_DELTAS_ARE_ZERO ) { - /* `runcnt' zeroes get added */ + /* `cnt` + 1 zeroes get added */ for ( j = 0; j <= cnt && i < delta_cnt; j++ ) deltas[i++] = 0; } else if ( runcnt & GX_DT_DELTAS_ARE_WORDS ) { - /* `runcnt' shorts from the stack */ + /* `cnt` + 1 shorts from the stack */ + bytes_used += 2 * ( cnt + 1 ); + if ( bytes_used > size ) + { + FT_TRACE1(( "ft_var_readpackeddeltas:" + " number of short deltas too large\n" )); + goto Fail; + } + for ( j = 0; j <= cnt && i < delta_cnt; j++ ) deltas[i++] = FT_intToFixed( FT_GET_SHORT() ); } else { - /* `runcnt' signed bytes from the stack */ + /* `cnt` + 1 signed bytes from the stack */ + bytes_used += cnt + 1; + if ( bytes_used > size ) + { + FT_TRACE1(( "ft_var_readpackeddeltas:" + " number of byte deltas too large\n" )); + goto Fail; + } + for ( j = 0; j <= cnt && i < delta_cnt; j++ ) deltas[i++] = FT_intToFixed( FT_GET_CHAR() ); } if ( j <= cnt ) { - /* bad format */ - FT_FREE( deltas ); - return NULL; + FT_TRACE1(( "ft_var_readpackeddeltas:" + " number of deltas too large\n" )); + goto Fail; } } + if ( i < delta_cnt ) + { + FT_TRACE1(( "ft_var_readpackeddeltas: not enough deltas\n" )); + goto Fail; + } + return deltas; + + Fail: + FT_FREE( deltas ); + return NULL; } @@ -332,17 +355,24 @@ static void ft_var_load_avar( TT_Face face ) { - FT_Stream stream = FT_FACE_STREAM( face ); - FT_Memory memory = stream->memory; + FT_Error error; + FT_Stream stream = FT_FACE_STREAM( face ); + FT_Memory memory = stream->memory; + FT_Int i, j; + GX_Blend blend = face->blend; GX_AVarSegment segment; - FT_Error error = FT_Err_Ok; - FT_Long version; - FT_Long axisCount; - FT_Int i, j; - FT_ULong table_len; + GX_AVarTable table; - FT_UNUSED( error ); + FT_Long version; + FT_Long axisCount; + FT_ULong table_len; + +#ifndef TT_CONFIG_OPTION_NO_BORING_EXPANSION + FT_ULong table_offset; + FT_ULong store_offset; + FT_ULong axisMap_offset; +#endif FT_TRACE2(( "AVAR " )); @@ -355,13 +385,21 @@ return; } +#ifndef TT_CONFIG_OPTION_NO_BORING_EXPANSION + table_offset = FT_STREAM_POS(); +#endif + if ( FT_FRAME_ENTER( table_len ) ) return; version = FT_GET_LONG(); axisCount = FT_GET_LONG(); - if ( version != 0x00010000L ) + if ( version != 0x00010000L +#ifndef TT_CONFIG_OPTION_NO_BORING_EXPANSION + && version != 0x00020000L +#endif + ) { FT_TRACE2(( "bad table version\n" )); goto Exit; @@ -371,31 +409,35 @@ if ( axisCount != (FT_Long)blend->mmvar->num_axis ) { - FT_TRACE2(( "ft_var_load_avar: number of axes in `avar' and `fvar'\n" - " table are different\n" )); + FT_TRACE2(( "ft_var_load_avar:" + " number of axes in `avar' and `fvar'\n" )); + FT_TRACE2(( " table are different\n" )); goto Exit; } - if ( FT_NEW_ARRAY( blend->avar_segment, axisCount ) ) + if ( FT_NEW( blend->avar_table ) ) goto Exit; + table = blend->avar_table; - segment = &blend->avar_segment[0]; + if ( FT_QNEW_ARRAY( table->avar_segment, axisCount ) ) + goto Exit; + + segment = &table->avar_segment[0]; for ( i = 0; i < axisCount; i++, segment++ ) { FT_TRACE5(( " axis %d:\n", i )); segment->pairCount = FT_GET_USHORT(); - if ( (FT_ULong)segment->pairCount * 4 > table_len || - FT_NEW_ARRAY( segment->correspondence, segment->pairCount ) ) + if ( (FT_ULong)segment->pairCount * 4 > table_len || + FT_QNEW_ARRAY( segment->correspondence, segment->pairCount ) ) { /* Failure. Free everything we have done so far. We must do */ /* it right now since loading the `avar' table is optional. */ for ( j = i - 1; j >= 0; j-- ) - FT_FREE( blend->avar_segment[j].correspondence ); + FT_FREE( table->avar_segment[j].correspondence ); - FT_FREE( blend->avar_segment ); - blend->avar_segment = NULL; + FT_FREE( table->avar_segment ); goto Exit; } @@ -407,35 +449,70 @@ FT_fdot14ToFixed( FT_GET_SHORT() ); FT_TRACE5(( " mapping %.5f to %.5f\n", - segment->correspondence[j].fromCoord / 65536.0, - segment->correspondence[j].toCoord / 65536.0 )); + (double)segment->correspondence[j].fromCoord / 65536, + (double)segment->correspondence[j].toCoord / 65536 )); } FT_TRACE5(( "\n" )); } +#ifndef TT_CONFIG_OPTION_NO_BORING_EXPANSION + if ( version < 0x00020000L ) + goto Exit; + + axisMap_offset = FT_GET_ULONG(); + store_offset = FT_GET_ULONG(); + + if ( store_offset ) + { + error = tt_var_load_item_variation_store( + FT_FACE( face ), + table_offset + store_offset, + &table->itemStore ); + if ( error ) + goto Exit; + } + + if ( axisMap_offset ) + { + error = tt_var_load_delta_set_index_mapping( + FT_FACE( face ), + table_offset + axisMap_offset, + &table->axisMap, + &table->itemStore, + table_len ); + if ( error ) + goto Exit; + } +#endif + + Exit: FT_FRAME_EXIT(); } - static FT_Error - ft_var_load_item_variation_store( TT_Face face, + FT_LOCAL_DEF( FT_Error ) + tt_var_load_item_variation_store( FT_Face face, /* TT_Face */ FT_ULong offset, GX_ItemVarStore itemStore ) { + TT_Face ttface = (TT_Face)face; FT_Stream stream = FT_FACE_STREAM( face ); FT_Memory memory = stream->memory; FT_Error error; FT_UShort format; FT_ULong region_offset; - FT_UInt i, j, k; - FT_UInt shortDeltaCount; - GX_Blend blend = face->blend; - GX_ItemVarData varData; + FT_UInt data_count; + FT_UShort axis_count; + FT_UInt region_count; + FT_UInt i, j; + FT_Bool long_words; + + GX_Blend blend = ttface->blend; FT_ULong* dataOffsetArray = NULL; @@ -445,31 +522,31 @@ if ( format != 1 ) { - FT_TRACE2(( "ft_var_load_item_variation_store: bad store format %d\n", + FT_TRACE2(( "tt_var_load_item_variation_store: bad store format %d\n", format )); error = FT_THROW( Invalid_Table ); goto Exit; } /* read top level fields */ - if ( FT_READ_ULONG( region_offset ) || - FT_READ_USHORT( itemStore->dataCount ) ) + if ( FT_READ_ULONG( region_offset ) || + FT_READ_USHORT( data_count ) ) goto Exit; /* we need at least one entry in `itemStore->varData' */ - if ( !itemStore->dataCount ) + if ( !data_count ) { - FT_TRACE2(( "ft_var_load_item_variation_store: missing varData\n" )); + FT_TRACE2(( "tt_var_load_item_variation_store: missing varData\n" )); error = FT_THROW( Invalid_Table ); goto Exit; } /* make temporary copy of item variation data offsets; */ /* we will parse region list first, then come back */ - if ( FT_NEW_ARRAY( dataOffsetArray, itemStore->dataCount ) ) + if ( FT_QNEW_ARRAY( dataOffsetArray, data_count ) ) goto Exit; - for ( i = 0; i < itemStore->dataCount; i++ ) + for ( i = 0; i < data_count; i++ ) { if ( FT_READ_ULONG( dataOffsetArray[i] ) ) goto Exit; @@ -479,30 +556,40 @@ if ( FT_STREAM_SEEK( offset + region_offset ) ) goto Exit; - if ( FT_READ_USHORT( itemStore->axisCount ) || - FT_READ_USHORT( itemStore->regionCount ) ) + if ( FT_READ_USHORT( axis_count ) || + FT_READ_USHORT( region_count ) ) goto Exit; - if ( itemStore->axisCount != (FT_Long)blend->mmvar->num_axis ) + if ( axis_count != (FT_Long)blend->mmvar->num_axis ) { - FT_TRACE2(( "ft_var_load_item_variation_store:" - " number of axes in item variation store\n" - " " + FT_TRACE2(( "tt_var_load_item_variation_store:" + " number of axes in item variation store\n" )); + FT_TRACE2(( " " " and `fvar' table are different\n" )); error = FT_THROW( Invalid_Table ); goto Exit; } + itemStore->axisCount = axis_count; + + /* new constraint in OpenType 1.8.4 */ + if ( region_count >= 32768U ) + { + FT_TRACE2(( "tt_var_load_item_variation_store:" + " too many variation region tables\n" )); + error = FT_THROW( Invalid_Table ); + goto Exit; + } - if ( FT_NEW_ARRAY( itemStore->varRegionList, itemStore->regionCount ) ) + if ( FT_NEW_ARRAY( itemStore->varRegionList, region_count ) ) goto Exit; + itemStore->regionCount = region_count; for ( i = 0; i < itemStore->regionCount; i++ ) { GX_AxisCoords axisCoords; - if ( FT_NEW_ARRAY( itemStore->varRegionList[i].axisList, - itemStore->axisCount ) ) + if ( FT_NEW_ARRAY( itemStore->varRegionList[i].axisList, axis_count ) ) goto Exit; axisCoords = itemStore->varRegionList[i].axisList; @@ -526,44 +613,56 @@ /* end of region list parse */ /* use dataOffsetArray now to parse varData items */ - if ( FT_NEW_ARRAY( itemStore->varData, itemStore->dataCount ) ) + if ( FT_NEW_ARRAY( itemStore->varData, data_count ) ) goto Exit; + itemStore->dataCount = data_count; - for ( i = 0; i < itemStore->dataCount; i++ ) + for ( i = 0; i < data_count; i++ ) { - varData = &itemStore->varData[i]; + GX_ItemVarData varData = &itemStore->varData[i]; + + FT_UInt item_count; + FT_UShort word_delta_count; + FT_UInt region_idx_count; + FT_UInt per_region_size; + if ( FT_STREAM_SEEK( offset + dataOffsetArray[i] ) ) goto Exit; - if ( FT_READ_USHORT( varData->itemCount ) || - FT_READ_USHORT( shortDeltaCount ) || - FT_READ_USHORT( varData->regionIdxCount ) ) + if ( FT_READ_USHORT( item_count ) || + FT_READ_USHORT( word_delta_count ) || + FT_READ_USHORT( region_idx_count ) ) goto Exit; + long_words = !!( word_delta_count & 0x8000 ); + word_delta_count &= 0x7FFF; + /* check some data consistency */ - if ( shortDeltaCount > varData->regionIdxCount ) + if ( word_delta_count > region_idx_count ) { FT_TRACE2(( "bad short count %d or region count %d\n", - shortDeltaCount, - varData->regionIdxCount )); + word_delta_count, + region_idx_count )); error = FT_THROW( Invalid_Table ); goto Exit; } - if ( varData->regionIdxCount > itemStore->regionCount ) + if ( region_idx_count > itemStore->regionCount ) { FT_TRACE2(( "inconsistent regionCount %d in varData[%d]\n", - varData->regionIdxCount, + region_idx_count, i )); error = FT_THROW( Invalid_Table ); goto Exit; } /* parse region indices */ - if ( FT_NEW_ARRAY( varData->regionIndices, - varData->regionIdxCount ) ) + if ( FT_NEW_ARRAY( varData->regionIndices, region_idx_count ) ) goto Exit; + varData->regionIdxCount = region_idx_count; + varData->wordDeltaCount = word_delta_count; + varData->longWords = long_words; for ( j = 0; j < varData->regionIdxCount; j++ ) { @@ -579,43 +678,22 @@ } } - /* Parse delta set. */ - /* */ - /* On input, deltas are (shortDeltaCount + regionIdxCount) bytes */ - /* each; on output, deltas are expanded to `regionIdxCount' shorts */ - /* each. */ - if ( FT_NEW_ARRAY( varData->deltaSet, - varData->regionIdxCount * varData->itemCount ) ) - goto Exit; + per_region_size = word_delta_count + region_idx_count; + if ( long_words ) + per_region_size *= 2; - /* the delta set is stored as a 2-dimensional array of shorts; */ - /* sign-extend signed bytes to signed shorts */ - for ( j = 0; j < varData->itemCount * varData->regionIdxCount; ) + if ( FT_NEW_ARRAY( varData->deltaSet, per_region_size * item_count ) ) + goto Exit; + if ( FT_Stream_Read( stream, + varData->deltaSet, + per_region_size * item_count ) ) { - for ( k = 0; k < shortDeltaCount; k++, j++ ) - { - /* read the short deltas */ - FT_Short delta; - - - if ( FT_READ_SHORT( delta ) ) - goto Exit; - - varData->deltaSet[j] = delta; - } - - for ( ; k < varData->regionIdxCount; k++, j++ ) - { - /* read the (signed) byte deltas */ - FT_Char delta; - - - if ( FT_READ_CHAR( delta ) ) - goto Exit; - - varData->deltaSet[j] = delta; - } + FT_TRACE2(( "deltaSet read failed." )); + error = FT_THROW( Invalid_Table ); + goto Exit; } + + varData->itemCount = item_count; } Exit: @@ -625,41 +703,70 @@ } - static FT_Error - ft_var_load_delta_set_index_mapping( TT_Face face, + FT_LOCAL_DEF( FT_Error ) + tt_var_load_delta_set_index_mapping( FT_Face face, /* TT_Face */ FT_ULong offset, GX_DeltaSetIdxMap map, - GX_ItemVarStore itemStore ) + GX_ItemVarStore itemStore, + FT_ULong table_len ) { FT_Stream stream = FT_FACE_STREAM( face ); FT_Memory memory = stream->memory; - FT_Error error; + FT_Error error; - FT_UShort format; - FT_UInt entrySize; - FT_UInt innerBitCount; - FT_UInt innerIndexMask; - FT_UInt i, j; + FT_Byte format; + FT_Byte entryFormat; + FT_UInt entrySize; + FT_UInt innerBitCount; + FT_UInt innerIndexMask; + FT_ULong i; + FT_UInt j; - if ( FT_STREAM_SEEK( offset ) || - FT_READ_USHORT( format ) || - FT_READ_USHORT( map->mapCount ) ) + if ( FT_STREAM_SEEK( offset ) || + FT_READ_BYTE( format ) || + FT_READ_BYTE( entryFormat ) ) goto Exit; - if ( format & 0xFFC0 ) + if ( format == 0 ) + { + if ( FT_READ_USHORT( map->mapCount ) ) + goto Exit; + } + else if ( format == 1 ) /* new in OpenType 1.9 */ + { + if ( FT_READ_ULONG( map->mapCount ) ) + goto Exit; + } + else { FT_TRACE2(( "bad map format %d\n", format )); error = FT_THROW( Invalid_Table ); goto Exit; } + if ( entryFormat & 0xC0 ) + { + FT_TRACE2(( "bad entry format %d\n", format )); + error = FT_THROW( Invalid_Table ); + goto Exit; + } + /* bytes per entry: 1, 2, 3, or 4 */ - entrySize = ( ( format & 0x0030 ) >> 4 ) + 1; - innerBitCount = ( format & 0x000F ) + 1; + entrySize = ( ( entryFormat & 0x30 ) >> 4 ) + 1; + innerBitCount = ( entryFormat & 0x0F ) + 1; innerIndexMask = ( 1 << innerBitCount ) - 1; + /* rough sanity check */ + if ( map->mapCount * entrySize > table_len ) + { + FT_TRACE1(( "tt_var_load_delta_set_index_mapping:" + " invalid number of delta-set index mappings\n" )); + error = FT_THROW( Invalid_Table ); + goto Exit; + } + if ( FT_NEW_ARRAY( map->innerIndex, map->mapCount ) ) goto Exit; @@ -684,11 +791,21 @@ mapData = ( mapData << 8 ) | data; } + /* new in OpenType 1.8.4 */ + if ( mapData == 0xFFFFFFFFUL ) + { + /* no variation data for this item */ + map->outerIndex[i] = 0xFFFFU; + map->innerIndex[i] = 0xFFFFU; + + continue; + } + outerIndex = mapData >> innerBitCount; if ( outerIndex >= itemStore->dataCount ) { - FT_TRACE2(( "outerIndex[%d] == %d out of range\n", + FT_TRACE2(( "outerIndex[%ld] == %d out of range\n", i, outerIndex )); error = FT_THROW( Invalid_Table ); @@ -701,7 +818,7 @@ if ( innerIndex >= itemStore->varData[outerIndex].itemCount ) { - FT_TRACE2(( "innerIndex[%d] == %d out of range\n", + FT_TRACE2(( "innerIndex[%ld] == %d out of range\n", i, innerIndex )); error = FT_THROW( Invalid_Table ); @@ -813,8 +930,8 @@ table = blend->hvar_table; } - error = ft_var_load_item_variation_store( - face, + error = tt_var_load_item_variation_store( + FT_FACE( face ), table_offset + store_offset, &table->itemStore ); if ( error ) @@ -822,11 +939,12 @@ if ( widthMap_offset ) { - error = ft_var_load_delta_set_index_mapping( - face, + error = tt_var_load_delta_set_index_mapping( + FT_FACE( face ), table_offset + widthMap_offset, &table->widthMap, - &table->itemStore ); + &table->itemStore, + table_len ); if ( error ) goto Exit; } @@ -863,26 +981,86 @@ } - static FT_Int - ft_var_get_item_delta( TT_Face face, + FT_LOCAL_DEF( FT_ItemVarDelta ) + tt_var_get_item_delta( FT_Face face, /* TT_Face */ GX_ItemVarStore itemStore, FT_UInt outerIndex, FT_UInt innerIndex ) { - GX_ItemVarData varData; - FT_Short* deltaSet; + TT_Face ttface = (TT_Face)face; + FT_Stream stream = FT_FACE_STREAM( face ); + FT_Memory memory = stream->memory; + FT_Error error = FT_Err_Ok; + + GX_ItemVarData varData; + FT_ItemVarDelta* deltaSet = NULL; + FT_ItemVarDelta deltaSetStack[16]; + + FT_Fixed* scalars = NULL; + FT_Fixed scalarsStack[16]; - FT_UInt master, j; - FT_Fixed netAdjustment = 0; /* accumulated adjustment */ - FT_Fixed scaledDelta; - FT_Fixed delta; + FT_UInt master, j; + FT_ItemVarDelta returnValue = 0; + FT_UInt per_region_size; + FT_Byte* bytes; + if ( !ttface->blend || !ttface->blend->normalizedcoords ) + return 0; + + /* OpenType 1.8.4+: No variation data for this item */ + /* as indices have special value 0xFFFF. */ + if ( outerIndex == 0xFFFF && innerIndex == 0xFFFF ) + return 0; + /* See pseudo code from `Font Variations Overview' */ /* in the OpenType specification. */ - varData = &itemStore->varData[outerIndex]; - deltaSet = &varData->deltaSet[varData->regionIdxCount * innerIndex]; + if ( outerIndex >= itemStore->dataCount ) + return 0; /* Out of range. */ + + varData = &itemStore->varData[outerIndex]; + + if ( innerIndex >= varData->itemCount ) + return 0; /* Out of range. */ + + if ( varData->regionIdxCount < 16 ) + { + deltaSet = deltaSetStack; + scalars = scalarsStack; + } + else + { + if ( FT_QNEW_ARRAY( deltaSet, varData->regionIdxCount ) ) + goto Exit; + if ( FT_QNEW_ARRAY( scalars, varData->regionIdxCount ) ) + goto Exit; + } + + /* Parse delta set. */ + /* */ + /* Deltas are (word_delta_count + region_idx_count) bytes each */ + /* if `longWords` isn't set, and twice as much otherwise. */ + per_region_size = varData->wordDeltaCount + varData->regionIdxCount; + if ( varData->longWords ) + per_region_size *= 2; + + bytes = varData->deltaSet + per_region_size * innerIndex; + + if ( varData->longWords ) + { + for ( master = 0; master < varData->wordDeltaCount; master++ ) + deltaSet[master] = FT_NEXT_LONG( bytes ); + for ( ; master < varData->regionIdxCount; master++ ) + deltaSet[master] = FT_NEXT_SHORT( bytes ); + } + else + { + for ( master = 0; master < varData->wordDeltaCount; master++ ) + deltaSet[master] = FT_NEXT_SHORT( bytes ); + for ( ; master < varData->regionIdxCount; master++ ) + deltaSet[master] = FT_NEXT_CHAR( bytes ); + } /* outer loop steps through master designs to be blended */ for ( master = 0; master < varData->regionIdxCount; master++ ) @@ -911,40 +1089,59 @@ else if ( axis->peakCoord == 0 ) continue; - else if ( face->blend->normalizedcoords[j] == axis->peakCoord ) + else if ( ttface->blend->normalizedcoords[j] == axis->peakCoord ) continue; /* ignore this region if coords are out of range */ - else if ( face->blend->normalizedcoords[j] <= axis->startCoord || - face->blend->normalizedcoords[j] >= axis->endCoord ) + else if ( ttface->blend->normalizedcoords[j] <= axis->startCoord || + ttface->blend->normalizedcoords[j] >= axis->endCoord ) { scalar = 0; break; } /* cumulative product of all the axis scalars */ - else if ( face->blend->normalizedcoords[j] < axis->peakCoord ) + else if ( ttface->blend->normalizedcoords[j] < axis->peakCoord ) scalar = FT_MulDiv( scalar, - face->blend->normalizedcoords[j] - axis->startCoord, + ttface->blend->normalizedcoords[j] - axis->startCoord, axis->peakCoord - axis->startCoord ); else scalar = FT_MulDiv( scalar, - axis->endCoord - face->blend->normalizedcoords[j], + axis->endCoord - ttface->blend->normalizedcoords[j], axis->endCoord - axis->peakCoord ); - } /* per-axis loop */ - /* get the scaled delta for this region */ - delta = FT_intToFixed( deltaSet[master] ); - scaledDelta = FT_MulFix( scalar, delta ); + } /* per-axis loop */ - /* accumulate the adjustments from each region */ - netAdjustment = netAdjustment + scaledDelta; + scalars[master] = scalar; } /* per-region loop */ - return FT_fixedToInt( netAdjustment ); + + /* Compute the scaled delta for this region. + * + * From: https://docs.microsoft.com/en-us/typography/opentype/spec/otvarcommonformats#item-variation-store-header-and-item-variation-data-subtables: + * + * `Fixed` is a 32-bit (16.16) type and, in the general case, requires + * 32-bit deltas. As described above, the `DeltaSet` record can + * accommodate deltas that are, logically, either 16-bit or 32-bit. + * When scaled deltas are applied to `Fixed` values, the `Fixed` value + * is treated like a 32-bit integer. + * + * `FT_MulAddFix` internally uses 64-bit precision; it thus can handle + * deltas ranging from small 8-bit to large 32-bit values that are + * applied to 16.16 `FT_Fixed` / OpenType `Fixed` values. + */ + returnValue = FT_MulAddFix( scalars, deltaSet, varData->regionIdxCount ); + + Exit: + if ( scalars != scalarsStack ) + FT_FREE( scalars ); + if ( deltaSet != deltaSetStack ) + FT_FREE( deltaSet ); + + return returnValue; } @@ -1037,35 +1234,27 @@ } else { - GX_ItemVarData varData; - - /* no widthMap data */ outerIndex = 0; innerIndex = gindex; - - varData = &table->itemStore.varData[outerIndex]; - if ( gindex >= varData->itemCount ) - { - FT_TRACE2(( "gindex %d out of range\n", gindex )); - error = FT_THROW( Invalid_Argument ); - goto Exit; - } } - delta = ft_var_get_item_delta( face, + delta = tt_var_get_item_delta( FT_FACE( face ), &table->itemStore, outerIndex, innerIndex ); - FT_TRACE5(( "%s value %d adjusted by %d unit%s (%s)\n", - vertical ? "vertical height" : "horizontal width", - *avalue, - delta, - delta == 1 ? "" : "s", - vertical ? "VVAR" : "HVAR" )); - - *avalue += delta; + if ( delta ) + { + FT_TRACE5(( "%s value %d adjusted by %d unit%s (%s)\n", + vertical ? "vertical height" : "horizontal width", + *avalue, + delta, + delta == 1 ? "" : "s", + vertical ? "VVAR" : "HVAR" )); + + *avalue = ADD_INT( *avalue, delta ); + } Exit: return error; @@ -1073,20 +1262,20 @@ FT_LOCAL_DEF( FT_Error ) - tt_hadvance_adjust( TT_Face face, + tt_hadvance_adjust( FT_Face face, /* TT_Face */ FT_UInt gindex, FT_Int *avalue ) { - return tt_hvadvance_adjust( face, gindex, avalue, 0 ); + return tt_hvadvance_adjust( (TT_Face)face, gindex, avalue, 0 ); } FT_LOCAL_DEF( FT_Error ) - tt_vadvance_adjust( TT_Face face, + tt_vadvance_adjust( FT_Face face, /* TT_Face */ FT_UInt gindex, FT_Int *avalue ) { - return tt_hvadvance_adjust( face, gindex, avalue, 1 ); + return tt_hvadvance_adjust( (TT_Face)face, gindex, avalue, 1 ); } @@ -1232,8 +1421,8 @@ records_offset = FT_STREAM_POS(); - error = ft_var_load_item_variation_store( - face, + error = tt_var_load_item_variation_store( + FT_FACE( face ), table_offset + store_offset, &blend->mvar_table->itemStore ); if ( error ) @@ -1248,7 +1437,7 @@ return; value = blend->mvar_table->values; - limit = value + blend->mvar_table->valueCount; + limit = FT_OFFSET( value, blend->mvar_table->valueCount ); itemStore = &blend->mvar_table->itemStore; for ( ; value < limit; value++ ) @@ -1257,6 +1446,13 @@ value->outerIndex = FT_GET_USHORT(); value->innerIndex = FT_GET_USHORT(); + /* new in OpenType 1.8.4 */ + if ( value->outerIndex == 0xFFFFU && value->innerIndex == 0xFFFFU ) + { + /* no variation data for this item */ + continue; + } + if ( value->outerIndex >= itemStore->dataCount || value->innerIndex >= itemStore->varData[value->outerIndex] .itemCount ) @@ -1274,7 +1470,7 @@ FT_TRACE2(( "loaded\n" )); value = blend->mvar_table->values; - limit = value + blend->mvar_table->valueCount; + limit = FT_OFFSET( value, blend->mvar_table->valueCount ); /* save original values of the data MVAR is going to modify */ for ( ; value < limit; value++ ) @@ -1299,15 +1495,14 @@ static FT_Error - tt_size_reset_iterator( FT_ListNode node, + ft_size_reset_iterator( FT_ListNode node, void* user ) { - TT_Size size = (TT_Size)node->data; - - FT_UNUSED( user ); + FT_Size size = (FT_Size)node->data; + FT_Service_MetricsVariations var = (FT_Service_MetricsVariations)user; - tt_size_reset( size, 1 ); + var->size_reset( size ); return FT_Err_Ok; } @@ -1326,33 +1521,36 @@ * The font face. */ FT_LOCAL_DEF( void ) - tt_apply_mvar( TT_Face face ) + tt_apply_mvar( FT_Face face ) /* TT_Face */ { - GX_Blend blend = face->blend; + TT_Face ttface = (TT_Face)face; + + GX_Blend blend = ttface->blend; GX_Value value, limit; + FT_Short mvar_hasc_delta = 0; FT_Short mvar_hdsc_delta = 0; FT_Short mvar_hlgp_delta = 0; - if ( !( face->variation_support & TT_FACE_FLAG_VAR_MVAR ) ) + if ( !( ttface->variation_support & TT_FACE_FLAG_VAR_MVAR ) ) return; value = blend->mvar_table->values; - limit = value + blend->mvar_table->valueCount; + limit = FT_OFFSET( value, blend->mvar_table->valueCount ); for ( ; value < limit; value++ ) { - FT_Short* p = ft_var_get_value_pointer( face, value->tag ); + FT_Short* p = ft_var_get_value_pointer( ttface, value->tag ); FT_Int delta; - delta = ft_var_get_item_delta( face, + delta = tt_var_get_item_delta( face, &blend->mvar_table->itemStore, value->outerIndex, value->innerIndex ); - if ( p ) + if ( p && delta ) { FT_TRACE5(( "value %c%c%c%c (%d unit%s) adjusted by %d unit%s (MVAR)\n", (FT_Char)( value->tag >> 24 ), @@ -1380,7 +1578,8 @@ /* adjust all derived values */ { - FT_Face root = &face->root; + FT_Service_MetricsVariations var = + (FT_Service_MetricsVariations)ttface->face_var; /* * Apply the deltas of hasc, hdsc and hlgp to the FT_Face's ascender, @@ -1408,24 +1607,25 @@ * whether they were actually changed or the font had the OS/2 table's * fsSelection's bit 7 (USE_TYPO_METRICS) set. */ - FT_Short current_line_gap = root->height - root->ascender + - root->descender; + FT_Short current_line_gap = face->height - face->ascender + + face->descender; - root->ascender = root->ascender + mvar_hasc_delta; - root->descender = root->descender + mvar_hdsc_delta; - root->height = root->ascender - root->descender + + face->ascender = face->ascender + mvar_hasc_delta; + face->descender = face->descender + mvar_hdsc_delta; + face->height = face->ascender - face->descender + current_line_gap + mvar_hlgp_delta; - root->underline_position = face->postscript.underlinePosition - - face->postscript.underlineThickness / 2; - root->underline_thickness = face->postscript.underlineThickness; + face->underline_position = ttface->postscript.underlinePosition - + ttface->postscript.underlineThickness / 2; + face->underline_thickness = ttface->postscript.underlineThickness; - /* iterate over all FT_Size objects and call `tt_size_reset' */ - /* to propagate the metrics changes */ - FT_List_Iterate( &root->sizes_list, - tt_size_reset_iterator, - NULL ); + /* iterate over all FT_Size objects and call `var->size_reset' */ + /* to propagate the metrics changes */ + if ( var && var->size_reset ) + FT_List_Iterate( &face->sizes_list, + ft_size_reset_iterator, + (void*)var ); } } @@ -1515,8 +1715,9 @@ if ( gvar_head.axisCount != (FT_UShort)blend->mmvar->num_axis ) { - FT_TRACE1(( "ft_var_load_gvar: number of axes in `gvar' and `cvar'\n" - " table are different\n" )); + FT_TRACE1(( "ft_var_load_gvar:" + " number of axes in `gvar' and `cvar'\n" )); + FT_TRACE1(( " table are different\n" )); error = FT_THROW( Invalid_Table ); goto Exit; } @@ -1558,7 +1759,7 @@ goto Exit; /* offsets (one more offset than glyphs, to mark size of last) */ - if ( FT_NEW_ARRAY( blend->glyphoffsets, gvar_head.glyphCount + 1 ) ) + if ( FT_QNEW_ARRAY( blend->glyphoffsets, gvar_head.glyphCount + 1 ) ) goto Fail2; if ( gvar_head.flags & 1 ) @@ -1637,8 +1838,8 @@ goto Fail; } - if ( FT_NEW_ARRAY( blend->tuplecoords, - gvar_head.axisCount * gvar_head.globalCoordCount ) ) + if ( FT_QNEW_ARRAY( blend->tuplecoords, + gvar_head.axisCount * gvar_head.globalCoordCount ) ) goto Fail2; for ( i = 0; i < gvar_head.globalCoordCount; i++ ) @@ -1649,7 +1850,7 @@ blend->tuplecoords[i * gvar_head.axisCount + j] = FT_fdot14ToFixed( FT_GET_SHORT() ); FT_TRACE5(( "%.5f ", - blend->tuplecoords[i * gvar_head.axisCount + j] / 65536.0 )); + (double)blend->tuplecoords[i * gvar_head.axisCount + j] / 65536 )); } FT_TRACE5(( "]\n" )); } @@ -1720,7 +1921,7 @@ for ( i = 0; i < blend->num_axis; i++ ) { FT_TRACE6(( " axis %d coordinate %.5f:\n", - i, blend->normalizedcoords[i] / 65536.0 )); + i, (double)blend->normalizedcoords[i] / 65536 )); /* It's not clear why (for intermediate tuples) we don't need */ /* to check against start/end -- the documentation says we don't. */ @@ -1729,7 +1930,7 @@ if ( tuple_coords[i] == 0 ) { - FT_TRACE6(( " tuple coordinate is zero, ignore\n", i )); + FT_TRACE6(( " tuple coordinate is zero, ignore\n" )); continue; } @@ -1743,7 +1944,7 @@ if ( blend->normalizedcoords[i] == tuple_coords[i] ) { FT_TRACE6(( " tuple coordinate %.5f fits perfectly\n", - tuple_coords[i] / 65536.0 )); + (double)tuple_coords[i] / 65536 )); /* `apply' does not change */ continue; } @@ -1756,13 +1957,13 @@ blend->normalizedcoords[i] > FT_MAX( 0, tuple_coords[i] ) ) { FT_TRACE6(( " tuple coordinate %.5f is exceeded, stop\n", - tuple_coords[i] / 65536.0 )); + (double)tuple_coords[i] / 65536 )); apply = 0; break; } FT_TRACE6(( " tuple coordinate %.5f fits\n", - tuple_coords[i] / 65536.0 )); + (double)tuple_coords[i] / 65536 )); apply = FT_MulDiv( apply, blend->normalizedcoords[i], tuple_coords[i] ); @@ -1776,15 +1977,15 @@ { FT_TRACE6(( " intermediate tuple range ]%.5f;%.5f[ is exceeded," " stop\n", - im_start_coords[i] / 65536.0, - im_end_coords[i] / 65536.0 )); + (double)im_start_coords[i] / 65536, + (double)im_end_coords[i] / 65536 )); apply = 0; break; } FT_TRACE6(( " intermediate tuple range ]%.5f;%.5f[ fits\n", - im_start_coords[i] / 65536.0, - im_end_coords[i] / 65536.0 )); + (double)im_start_coords[i] / 65536, + (double)im_end_coords[i] / 65536 )); if ( blend->normalizedcoords[i] < tuple_coords[i] ) apply = FT_MulDiv( apply, blend->normalizedcoords[i] - im_start_coords[i], @@ -1796,7 +1997,7 @@ } } - FT_TRACE6(( " apply factor is %.5f\n", apply / 65536.0 )); + FT_TRACE6(( " apply factor is %.5f\n", (double)apply / 65536 )); return apply; } @@ -1810,12 +2011,18 @@ FT_Fixed* coords, FT_Fixed* normalized ) { + FT_Error error = FT_Err_Ok; + FT_Memory memory = face->root.memory; + FT_UInt i, j; + GX_Blend blend; FT_MM_Var* mmvar; - FT_UInt i, j; FT_Var_Axis* a; GX_AVarSegment av; + FT_Fixed* new_normalized = NULL; + FT_Fixed* old_normalized; + blend = face->blend; mmvar = blend->mmvar; @@ -1838,28 +2045,25 @@ FT_Fixed coord = coords[i]; - FT_TRACE5(( " %d: %.5f\n", i, coord / 65536.0 )); + FT_TRACE5(( " %d: %.5f\n", i, (double)coord / 65536 )); if ( coord > a->maximum || coord < a->minimum ) { - FT_TRACE1(( - "ft_var_to_normalized: design coordinate %.5f\n" - " is out of range [%.5f;%.5f]; clamping\n", - coord / 65536.0, - a->minimum / 65536.0, - a->maximum / 65536.0 )); - - if ( coord > a->maximum ) - coord = a->maximum; - else - coord = a->minimum; + FT_TRACE1(( "ft_var_to_normalized: design coordinate %.5f\n", + (double)coord / 65536 )); + FT_TRACE1(( " is out of range [%.5f;%.5f];" + " clamping\n", + (double)a->minimum / 65536, + (double)a->maximum / 65536 )); } - if ( coord < a->def ) - normalized[i] = -FT_DivFix( SUB_LONG( coord, a->def ), - SUB_LONG( a->minimum, a->def ) ); - else if ( coord > a->def ) - normalized[i] = FT_DivFix( SUB_LONG( coord, a->def ), + if ( coord > a->def ) + normalized[i] = coord >= a->maximum ? 0x10000L : + FT_DivFix( SUB_LONG( coord, a->def ), SUB_LONG( a->maximum, a->def ) ); + else if ( coord < a->def ) + normalized[i] = coord <= a->minimum ? -0x10000L : + FT_DivFix( SUB_LONG( coord, a->def ), + SUB_LONG( a->def, a->minimum ) ); else normalized[i] = 0; } @@ -1869,30 +2073,91 @@ for ( ; i < mmvar->num_axis; i++ ) normalized[i] = 0; - if ( blend->avar_segment ) + if ( blend->avar_table ) { + GX_AVarTable table = blend->avar_table; + + FT_TRACE5(( "normalized design coordinates" " before applying `avar' data:\n" )); - av = blend->avar_segment; - for ( i = 0; i < mmvar->num_axis; i++, av++ ) + if ( table->avar_segment ) { - for ( j = 1; j < (FT_UInt)av->pairCount; j++ ) + av = table->avar_segment; + + for ( i = 0; i < mmvar->num_axis; i++, av++ ) { - if ( normalized[i] < av->correspondence[j].fromCoord ) + for ( j = 1; j < (FT_UInt)av->pairCount; j++ ) { - FT_TRACE5(( " %.5f\n", normalized[i] / 65536.0 )); + if ( normalized[i] < av->correspondence[j].fromCoord ) + { + FT_TRACE5(( " %.5f\n", (double)normalized[i] / 65536 )); + + normalized[i] = + FT_MulDiv( normalized[i] - av->correspondence[j - 1].fromCoord, + av->correspondence[j].toCoord - + av->correspondence[j - 1].toCoord, + av->correspondence[j].fromCoord - + av->correspondence[j - 1].fromCoord ) + + av->correspondence[j - 1].toCoord; + break; + } + } + } + } - normalized[i] = - FT_MulDiv( normalized[i] - av->correspondence[j - 1].fromCoord, - av->correspondence[j].toCoord - - av->correspondence[j - 1].toCoord, - av->correspondence[j].fromCoord - - av->correspondence[j - 1].fromCoord ) + - av->correspondence[j - 1].toCoord; - break; + if ( table->itemStore.varData ) + { + if ( FT_QNEW_ARRAY( new_normalized, mmvar->num_axis ) ) + return; + + /* Install our half-normalized coordinates for the next */ + /* Item Variation Store to work with. */ + old_normalized = face->blend->normalizedcoords; + face->blend->normalizedcoords = normalized; + + for ( i = 0; i < mmvar->num_axis; i++ ) + { + FT_Fixed v = normalized[i]; + FT_UInt innerIndex = i; + FT_UInt outerIndex = 0; + FT_Int delta; + + + if ( table->axisMap.innerIndex ) + { + FT_UInt idx = i; + + + if ( idx >= table->axisMap.mapCount ) + idx = table->axisMap.mapCount - 1; + + outerIndex = table->axisMap.outerIndex[idx]; + innerIndex = table->axisMap.innerIndex[idx]; } + + delta = tt_var_get_item_delta( FT_FACE( face ), + &table->itemStore, + outerIndex, + innerIndex ); + + v += delta << 2; + + /* Clamp value range. */ + v = v >= 0x10000L ? 0x10000 : v; + v = v <= -0x10000L ? -0x10000 : v; + + new_normalized[i] = v; } + + for ( i = 0; i < mmvar->num_axis; i++ ) + { + normalized[i] = new_normalized[i]; + } + + face->blend->normalizedcoords = old_normalized; + + FT_FREE( new_normalized ); } } } @@ -1930,9 +2195,9 @@ for ( ; i < num_coords; i++ ) design[i] = 0; - if ( blend->avar_segment ) + if ( blend->avar_table && blend->avar_table->avar_segment ) { - GX_AVarSegment av = blend->avar_segment; + GX_AVarSegment av = blend->avar_table->avar_segment; FT_TRACE5(( "design coordinates" @@ -1952,7 +2217,7 @@ av->correspondence[j - 1].toCoord ) + av->correspondence[j - 1].fromCoord; - FT_TRACE5(( " %.5f\n", design[i] / 65536.0 )); + FT_TRACE5(( " %.5f\n", (double)design[i] / 65536 )); break; } } @@ -2033,11 +2298,12 @@ * FreeType error code. 0 means success. */ FT_LOCAL_DEF( FT_Error ) - TT_Get_MM_Var( TT_Face face, + TT_Get_MM_Var( FT_Face face, /* TT_Face */ FT_MM_Var* *master ) { - FT_Stream stream = face->root.stream; - FT_Memory memory = face->root.memory; + TT_Face ttface = (TT_Face)face; + FT_Stream stream = FT_FACE_STREAM( face ); + FT_Memory memory = FT_FACE_MEMORY( face ); FT_ULong table_len; FT_Error error = FT_Err_Ok; FT_ULong fvar_start = 0; @@ -2049,7 +2315,7 @@ FT_Var_Axis* a; FT_Fixed* c; FT_Var_Named_Style* ns; - GX_FVar_Head fvar_head; + GX_FVar_Head fvar_head = { 0, 0, 0, 0, 0, 0 }; FT_Bool usePsName = 0; FT_UInt num_instances; FT_UInt num_axes; @@ -2097,32 +2363,23 @@ FT_FRAME_END }; + /* `num_instances` holds the number of all named instances including */ + /* the default instance, which might be missing in the table of named */ + /* instances (in 'fvar'). This value is validated in `sfobjs.c` and */ + /* may be reset to 0 if consistency checks fail. */ + num_instances = (FT_UInt)face->style_flags >> 16; /* read the font data and set up the internal representation */ /* if not already done */ - need_init = !face->blend; + need_init = !ttface->blend; if ( need_init ) { FT_TRACE2(( "FVAR " )); - /* both `fvar' and `gvar' must be present */ - if ( FT_SET_ERROR( face->goto_table( face, TTAG_gvar, - stream, &table_len ) ) ) - { - /* CFF2 is an alternate to gvar here */ - if ( FT_SET_ERROR( face->goto_table( face, TTAG_CFF2, + if ( FT_SET_ERROR( ttface->goto_table( ttface, TTAG_fvar, stream, &table_len ) ) ) - { - FT_TRACE1(( "\n" - "TT_Get_MM_Var: `gvar' or `CFF2' table is missing\n" )); - goto Exit; - } - } - - if ( FT_SET_ERROR( face->goto_table( face, TTAG_fvar, - stream, &table_len ) ) ) { FT_TRACE1(( "is missing\n" )); goto Exit; @@ -2135,6 +2392,17 @@ if ( FT_STREAM_READ_FIELDS( fvar_fields, &fvar_head ) ) goto Exit; + /* If `num_instances` is larger, synthetization of the default */ + /* instance is required. If `num_instances` is smaller, */ + /* however, the value has been reset to 0 in `sfnt_init_face` */ + /* (in `sfobjs.c`); in this case we have underallocated `mmvar` */ + /* structs. */ + if ( num_instances < fvar_head.instanceCount ) + { + error = FT_THROW( Invalid_Table ); + goto Exit; + } + usePsName = FT_BOOL( fvar_head.instanceSize == 6 + 4 * fvar_head.axisCount ); @@ -2144,19 +2412,14 @@ fvar_head.axisCount, fvar_head.axisCount == 1 ? "is" : "es" )); - if ( FT_NEW( face->blend ) ) + if ( FT_NEW( ttface->blend ) ) goto Exit; - num_axes = fvar_head.axisCount; - face->blend->num_axis = num_axes; + num_axes = fvar_head.axisCount; + ttface->blend->num_axis = num_axes; } else - num_axes = face->blend->num_axis; - - /* `num_instances' holds the number of all named instances, */ - /* including the default instance which might be missing */ - /* in fvar's table of named instances */ - num_instances = (FT_UInt)face->root.style_flags >> 16; + num_axes = ttface->blend->num_axis; /* prepare storage area for MM data; this cannot overflow */ /* 32-bit arithmetic because of the size limits used in the */ @@ -2185,16 +2448,16 @@ if ( need_init ) { - face->blend->mmvar_len = mmvar_size + - axis_flags_size + - axis_size + - namedstyle_size + - next_coords_size + - next_name_size; - - if ( FT_ALLOC( mmvar, face->blend->mmvar_len ) ) + ttface->blend->mmvar_len = mmvar_size + + axis_flags_size + + axis_size + + namedstyle_size + + next_coords_size + + next_name_size; + + if ( FT_ALLOC( mmvar, ttface->blend->mmvar_len ) ) goto Exit; - face->blend->mmvar = mmvar; + ttface->blend->mmvar = mmvar; /* set up pointers and offsets into the `mmvar' array; */ /* the data gets filled in later on */ @@ -2285,9 +2548,9 @@ " %10.5f %10.5f %10.5f 0x%04X%s\n", i, a->name, - a->minimum / 65536.0, - a->def / 65536.0, - a->maximum / 65536.0, + (double)a->minimum / 65536, + (double)a->def / 65536, + (double)a->maximum / 65536, *axis_flags, invalid ? " (invalid, disabled)" : "" )); #endif @@ -2300,27 +2563,27 @@ /* named instance coordinates are stored as design coordinates; */ /* we have to convert them to normalized coordinates also */ - if ( FT_NEW_ARRAY( face->blend->normalized_stylecoords, + if ( FT_NEW_ARRAY( ttface->blend->normalized_stylecoords, num_axes * num_instances ) ) goto Exit; - if ( fvar_head.instanceCount && !face->blend->avar_loaded ) + if ( fvar_head.instanceCount && !ttface->blend->avar_loaded ) { FT_ULong offset = FT_STREAM_POS(); - ft_var_load_avar( face ); + ft_var_load_avar( ttface ); if ( FT_STREAM_SEEK( offset ) ) goto Exit; } - FT_TRACE5(( "%d instance%s\n", + FT_TRACE5(( "%d named instance%s\n", fvar_head.instanceCount, fvar_head.instanceCount == 1 ? "" : "s" )); ns = mmvar->namedstyle; - nsc = face->blend->normalized_stylecoords; + nsc = ttface->blend->normalized_stylecoords; for ( i = 0; i < fvar_head.instanceCount; i++, ns++ ) { /* PostScript names add 2 bytes to the instance record size */ @@ -2343,7 +2606,7 @@ #ifdef FT_DEBUG_LEVEL_TRACE { - SFNT_Service sfnt = (SFNT_Service)face->sfnt; + SFNT_Service sfnt = (SFNT_Service)ttface->sfnt; FT_String* strname = NULL; FT_String* psname = NULL; @@ -2355,7 +2618,7 @@ if ( ns->strid != 0xFFFF ) { - (void)sfnt->get_name( face, + (void)sfnt->get_name( ttface, (FT_UShort)ns->strid, &strname ); if ( strname && !ft_strcmp( strname, ".notdef" ) ) @@ -2364,7 +2627,7 @@ if ( ns->psid != 0xFFFF ) { - (void)sfnt->get_name( face, + (void)sfnt->get_name( ttface, (FT_UShort)ns->psid, &psname ); if ( psname && !ft_strcmp( psname, ".notdef" ) ) @@ -2373,7 +2636,7 @@ (void)FT_STREAM_SEEK( pos ); - FT_TRACE5(( " instance %d (%s%s%s, %s%s%s)\n", + FT_TRACE5(( " named instance %d (%s%s%s, %s%s%s)\n", i, strname ? "name: `" : "", strname ? strname : "unnamed", @@ -2387,7 +2650,7 @@ } #endif /* FT_DEBUG_LEVEL_TRACE */ - ft_var_to_normalized( face, num_axes, ns->coords, nsc ); + ft_var_to_normalized( ttface, num_axes, ns->coords, nsc ); nsc += num_axes; FT_FRAME_EXIT(); @@ -2395,15 +2658,17 @@ if ( num_instances != fvar_head.instanceCount ) { - SFNT_Service sfnt = (SFNT_Service)face->sfnt; + SFNT_Service sfnt = (SFNT_Service)ttface->sfnt; FT_Int found, dummy1, dummy2; FT_UInt strid = ~0U; - /* the default instance is missing in array the */ - /* of named instances; try to synthesize an entry */ - found = sfnt->get_name_id( face, + /* The default instance is missing in array the */ + /* of named instances; try to synthesize an entry. */ + /* If this fails, `default_named_instance` remains */ + /* at value zero, which doesn't do any harm. */ + found = sfnt->get_name_id( ttface, TT_NAME_ID_TYPOGRAPHIC_SUBFAMILY, &dummy1, &dummy2 ); @@ -2411,7 +2676,7 @@ strid = TT_NAME_ID_TYPOGRAPHIC_SUBFAMILY; else { - found = sfnt->get_name_id( face, + found = sfnt->get_name_id( ttface, TT_NAME_ID_FONT_SUBFAMILY, &dummy1, &dummy2 ); @@ -2421,7 +2686,7 @@ if ( found ) { - found = sfnt->get_name_id( face, + found = sfnt->get_name_id( ttface, TT_NAME_ID_PS_NAME, &dummy1, &dummy2 ); @@ -2430,6 +2695,9 @@ FT_TRACE5(( "TT_Get_MM_Var:" " Adding default instance to named instances\n" )); + /* named instance indices start with value 1 */ + ttface->var_default_named_instance = num_instances; + ns = &mmvar->namedstyle[fvar_head.instanceCount]; ns->strid = strid; @@ -2443,7 +2711,7 @@ } } - ft_var_load_mvar( face ); + ft_var_load_mvar( ttface ); } /* fill the output array if requested */ @@ -2453,9 +2721,9 @@ FT_UInt n; - if ( FT_ALLOC( mmvar, face->blend->mmvar_len ) ) + if ( FT_ALLOC( mmvar, ttface->blend->mmvar_len ) ) goto Exit; - FT_MEM_COPY( mmvar, face->blend->mmvar, face->blend->mmvar_len ); + FT_MEM_COPY( mmvar, ttface->blend->mmvar, ttface->blend->mmvar_len ); axis_flags = (FT_UShort*)( (char*)mmvar + mmvar_size ); @@ -2488,6 +2756,8 @@ a->name = (char*)"OpticalSize"; else if ( a->tag == TTAG_slnt ) a->name = (char*)"Slant"; + else if ( a->tag == TTAG_ital ) + a->name = (char*)"Italic"; next_name += 5; a++; @@ -2529,7 +2799,7 @@ if ( !face->blend ) { - if ( FT_SET_ERROR( TT_Get_MM_Var( face, NULL ) ) ) + if ( FT_SET_ERROR( TT_Get_MM_Var( FT_FACE( face ), NULL ) ) ) goto Exit; } @@ -2544,17 +2814,17 @@ num_coords = mmvar->num_axis; } - FT_TRACE5(( "TT_Set_MM_Blend:\n" - " normalized design coordinates:\n" )); + FT_TRACE5(( "TT_Set_MM_Blend:\n" )); + FT_TRACE5(( " normalized design coordinates:\n" )); for ( i = 0; i < num_coords; i++ ) { - FT_TRACE5(( " %.5f\n", coords[i] / 65536.0 )); + FT_TRACE5(( " %.5f\n", (double)coords[i] / 65536 )); if ( coords[i] < -0x00010000L || coords[i] > 0x00010000L ) { - FT_TRACE1(( "TT_Set_MM_Blend: normalized design coordinate %.5f\n" - " is out of range [-1;1]\n", - coords[i] / 65536.0 )); + FT_TRACE1(( "TT_Set_MM_Blend: normalized design coordinate %.5f\n", + (double)coords[i] / 65536 )); + FT_TRACE1(( " is out of range [-1;1]\n" )); error = FT_THROW( Invalid_Argument ); goto Exit; } @@ -2563,8 +2833,16 @@ FT_TRACE5(( "\n" )); if ( !face->is_cff2 && !blend->glyphoffsets ) - if ( FT_SET_ERROR( ft_var_load_gvar( face ) ) ) + { + /* While a missing 'gvar' table is acceptable, for example for */ + /* fonts that only vary metrics information or 'COLR' v1 */ + /* `PaintVar*` tables, an incorrect SFNT table offset or size */ + /* for 'gvar', or an inconsistent 'gvar' table is not. */ + error = ft_var_load_gvar( face ); + if ( error != FT_Err_Table_Missing && error != FT_Err_Ok ) goto Exit; + error = FT_Err_Ok; + } if ( !blend->coords ) { @@ -2606,26 +2884,29 @@ } } - if ( FT_IS_NAMED_INSTANCE( FT_FACE( face ) ) ) + if ( !have_diff ) { - FT_UInt instance_index = (FT_UInt)face->root.face_index >> 16; + if ( FT_IS_NAMED_INSTANCE( FT_FACE( face ) ) ) + { + FT_UInt instance_index = (FT_UInt)face->root.face_index >> 16; - c = blend->normalizedcoords + i; - n = blend->normalized_stylecoords + - ( instance_index - 1 ) * mmvar->num_axis + - i; + c = blend->normalizedcoords + i; + n = blend->normalized_stylecoords + + ( instance_index - 1 ) * mmvar->num_axis + + i; - for ( j = i; j < mmvar->num_axis; j++, n++, c++ ) - if ( *c != *n ) - have_diff = 1; - } - else - { - c = blend->normalizedcoords + i; - for ( j = i; j < mmvar->num_axis; j++, c++ ) - if ( *c != 0 ) - have_diff = 1; + for ( j = i; j < mmvar->num_axis; j++, n++, c++ ) + if ( *c != *n ) + have_diff = 1; + } + else + { + c = blend->normalizedcoords + i; + for ( j = i; j < mmvar->num_axis; j++, c++ ) + if ( *c != 0 ) + have_diff = 1; + } } /* return value -1 indicates `no change' */ @@ -2652,9 +2933,10 @@ } blend->num_axis = mmvar->num_axis; - FT_MEM_COPY( blend->normalizedcoords, - coords, - num_coords * sizeof ( FT_Fixed ) ); + if ( coords ) + FT_MEM_COPY( blend->normalizedcoords, + coords, + num_coords * sizeof ( FT_Fixed ) ); if ( set_design_coords ) ft_var_to_design( face, @@ -2672,7 +2954,6 @@ /* The cvt table has been loaded already; every time we change the */ /* blend we may need to reload and remodify the cvt table. */ FT_FREE( face->cvt ); - face->cvt = NULL; error = tt_face_load_cvt( face, face->root.stream ); break; @@ -2689,10 +2970,6 @@ } } - /* enforce recomputation of the PostScript name; */ - FT_FREE( face->postscript_name ); - face->postscript_name = NULL; - Exit: return error; } @@ -2724,26 +3001,15 @@ * An array of `num_coords', each between [-1,1]. * * @Return: - * FreeType error code. 0 means success. + * FreeType error code. 0 means success, -1 means success and unchanged + * axis values. */ FT_LOCAL_DEF( FT_Error ) - TT_Set_MM_Blend( TT_Face face, + TT_Set_MM_Blend( FT_Face face, /* TT_Face */ FT_UInt num_coords, FT_Fixed* coords ) { - FT_Error error; - - - error = tt_set_mm_blend( face, num_coords, coords, 1 ); - if ( error ) - return error; - - if ( num_coords ) - face->root.face_flags |= FT_FACE_FLAG_VARIATION; - else - face->root.face_flags &= ~FT_FACE_FLAG_VARIATION; - - return FT_Err_Ok; + return tt_set_mm_blend( (TT_Face)face, num_coords, coords, 1 ); } @@ -2771,31 +3037,34 @@ * An array of `num_coords', each between [-1,1]. * * @Return: - * FreeType error code. 0 means success. + * FreeType error code. 0 means success, -1 means success and unchanged + * axis values. */ FT_LOCAL_DEF( FT_Error ) - TT_Get_MM_Blend( TT_Face face, + TT_Get_MM_Blend( FT_Face face, /* TT_Face */ FT_UInt num_coords, FT_Fixed* coords ) { + TT_Face ttface = (TT_Face)face; + FT_Error error = FT_Err_Ok; GX_Blend blend; FT_UInt i, nc; - if ( !face->blend ) + if ( !ttface->blend ) { if ( FT_SET_ERROR( TT_Get_MM_Var( face, NULL ) ) ) return error; } - blend = face->blend; + blend = ttface->blend; if ( !blend->coords ) { /* select default instance coordinates */ /* if no instance is selected yet */ - if ( FT_SET_ERROR( tt_set_mm_blend( face, 0, NULL, 1 ) ) ) + if ( FT_SET_ERROR( tt_set_mm_blend( ttface, 0, NULL, 1 ) ) ) return error; } @@ -2808,7 +3077,7 @@ nc = blend->num_axis; } - if ( face->doblend ) + if ( ttface->doblend ) { for ( i = 0; i < nc; i++ ) coords[i] = blend->normalizedcoords[i]; @@ -2855,15 +3124,16 @@ * FreeType error code. 0 means success. */ FT_LOCAL_DEF( FT_Error ) - TT_Set_Var_Design( TT_Face face, + TT_Set_Var_Design( FT_Face face, /* TT_Face */ FT_UInt num_coords, FT_Fixed* coords ) { + TT_Face ttface = (TT_Face)face; FT_Error error = FT_Err_Ok; GX_Blend blend; FT_MM_Var* mmvar; FT_UInt i; - FT_Memory memory = face->root.memory; + FT_Memory memory = FT_FACE_MEMORY( face ); FT_Fixed* c; FT_Fixed* n; @@ -2872,13 +3142,13 @@ FT_Bool have_diff = 0; - if ( !face->blend ) + if ( !ttface->blend ) { if ( FT_SET_ERROR( TT_Get_MM_Var( face, NULL ) ) ) goto Exit; } - blend = face->blend; + blend = ttface->blend; mmvar = blend->mmvar; if ( num_coords > mmvar->num_axis ) @@ -2906,13 +3176,13 @@ } } - if ( FT_IS_NAMED_INSTANCE( FT_FACE( face ) ) ) + if ( FT_IS_NAMED_INSTANCE( face ) ) { FT_UInt instance_index; FT_Var_Named_Style* named_style; - instance_index = (FT_UInt)face->root.face_index >> 16; + instance_index = (FT_UInt)face->face_index >> 16; named_style = mmvar->namedstyle + instance_index - 1; n = named_style->coords + num_coords; @@ -2949,22 +3219,17 @@ if ( FT_NEW_ARRAY( normalized, mmvar->num_axis ) ) goto Exit; - if ( !face->blend->avar_loaded ) - ft_var_load_avar( face ); + if ( !ttface->blend->avar_loaded ) + ft_var_load_avar( ttface ); - FT_TRACE5(( "TT_Set_Var_Design:\n" - " normalized design coordinates:\n" )); - ft_var_to_normalized( face, num_coords, blend->coords, normalized ); + FT_TRACE5(( "TT_Set_Var_Design:\n" )); + FT_TRACE5(( " normalized design coordinates:\n" )); + ft_var_to_normalized( ttface, num_coords, blend->coords, normalized ); - error = tt_set_mm_blend( face, mmvar->num_axis, normalized, 0 ); + error = tt_set_mm_blend( ttface, mmvar->num_axis, normalized, 0 ); if ( error ) goto Exit; - if ( num_coords ) - face->root.face_flags |= FT_FACE_FLAG_VARIATION; - else - face->root.face_flags &= ~FT_FACE_FLAG_VARIATION; - Exit: FT_FREE( normalized ); return error; @@ -2997,28 +3262,29 @@ * FreeType error code. 0~means success. */ FT_LOCAL_DEF( FT_Error ) - TT_Get_Var_Design( TT_Face face, + TT_Get_Var_Design( FT_Face face, /* TT_Face */ FT_UInt num_coords, FT_Fixed* coords ) { - FT_Error error = FT_Err_Ok; + TT_Face ttface = (TT_Face)face; + FT_Error error = FT_Err_Ok; GX_Blend blend; FT_UInt i, nc; - if ( !face->blend ) + if ( !ttface->blend ) { if ( FT_SET_ERROR( TT_Get_MM_Var( face, NULL ) ) ) return error; } - blend = face->blend; + blend = ttface->blend; if ( !blend->coords ) { /* select default instance coordinates */ /* if no instance is selected yet */ - if ( FT_SET_ERROR( tt_set_mm_blend( face, 0, NULL, 1 ) ) ) + if ( FT_SET_ERROR( tt_set_mm_blend( ttface, 0, NULL, 1 ) ) ) return error; } @@ -3031,7 +3297,7 @@ nc = blend->num_axis; } - if ( face->doblend ) + if ( ttface->doblend ) { for ( i = 0; i < nc; i++ ) coords[i] = blend->coords[i]; @@ -3067,29 +3333,33 @@ * Value 0 indicates to not use an instance. * * @Return: - * FreeType error code. 0~means success. + * FreeType error code. 0~means success, -1 means success and unchanged + * axis values. */ FT_LOCAL_DEF( FT_Error ) - TT_Set_Named_Instance( TT_Face face, + TT_Set_Named_Instance( FT_Face face, /* TT_Face */ FT_UInt instance_index ) { + TT_Face ttface = (TT_Face)face; FT_Error error; GX_Blend blend; FT_MM_Var* mmvar; + FT_Memory memory = FT_FACE_MEMORY( face ); + FT_UInt num_instances; - if ( !face->blend ) + if ( !ttface->blend ) { if ( FT_SET_ERROR( TT_Get_MM_Var( face, NULL ) ) ) goto Exit; } - blend = face->blend; + blend = ttface->blend; mmvar = blend->mmvar; - num_instances = (FT_UInt)face->root.style_flags >> 16; + num_instances = (FT_UInt)face->style_flags >> 16; /* `instance_index' starts with value 1, thus `>' */ if ( instance_index > num_instances ) @@ -3100,8 +3370,7 @@ if ( instance_index > 0 ) { - FT_Memory memory = face->root.memory; - SFNT_Service sfnt = (SFNT_Service)face->sfnt; + SFNT_Service sfnt = (SFNT_Service)ttface->sfnt; FT_Var_Named_Style* named_style; FT_String* style_name; @@ -3109,40 +3378,89 @@ named_style = mmvar->namedstyle + instance_index - 1; - error = sfnt->get_name( face, + error = sfnt->get_name( ttface, (FT_UShort)named_style->strid, &style_name ); if ( error ) goto Exit; /* set (or replace) style name */ - FT_FREE( face->root.style_name ); - face->root.style_name = style_name; + FT_FREE( face->style_name ); + face->style_name = style_name; /* finally, select the named instance */ error = TT_Set_Var_Design( face, mmvar->num_axis, named_style->coords ); - if ( error ) - { - /* internal error code -1 means `no change' */ - if ( error == -1 ) - error = FT_Err_Ok; - goto Exit; - } } else + { + /* restore non-VF style name */ + FT_FREE( face->style_name ); + if ( FT_STRDUP( face->style_name, ttface->non_var_style_name ) ) + goto Exit; error = TT_Set_Var_Design( face, 0, NULL ); + } + + Exit: + return error; + } - face->root.face_index = ( instance_index << 16 ) | - ( face->root.face_index & 0xFFFFL ); - face->root.face_flags &= ~FT_FACE_FLAG_VARIATION; + + /************************************************************************** + * + * @Function: + * TT_Get_Default_Named_Instance + * + * @Description: + * Get the default named instance. + * + * @Input: + * face :: + * A handle to the source face. + * + * @Output: + * instance_index :: + * The default named instance index. + * + * @Return: + * FreeType error code. 0~means success. + */ + FT_LOCAL_DEF( FT_Error ) + TT_Get_Default_Named_Instance( FT_Face face, + FT_UInt *instance_index ) + { + TT_Face ttface = (TT_Face)face; + FT_Error error = FT_Err_Ok; + + + if ( !ttface->blend ) + { + if ( FT_SET_ERROR( TT_Get_MM_Var( face, NULL ) ) ) + goto Exit; + } + + *instance_index = ttface->var_default_named_instance; Exit: return error; } + /* This function triggers (lazy) recomputation of the `postscript_name` */ + /* field in `TT_Face`. */ + + FT_LOCAL_DEF( void ) + tt_construct_ps_name( FT_Face face ) + { + TT_Face ttface = (TT_Face)face; + FT_Memory memory = FT_FACE_MEMORY( face ); + + + FT_FREE( ttface->postscript_name ); + } + + /*************************************************************************/ /*************************************************************************/ /***** *****/ @@ -3152,6 +3470,8 @@ /*************************************************************************/ +#ifdef TT_CONFIG_OPTION_BYTECODE_INTERPRETER + static FT_Error tt_cvt_ready_iterator( FT_ListNode node, void* user ) @@ -3166,6 +3486,9 @@ return FT_Err_Ok; } +#endif /* TT_CONFIG_OPTION_BYTECODE_INTERPRETER */ + + /************************************************************************** * @@ -3194,6 +3517,8 @@ tt_face_vary_cvt( TT_Face face, FT_Stream stream ) { +#ifdef TT_CONFIG_OPTION_BYTECODE_INTERPRETER + FT_Error error; FT_Memory memory = stream->memory; @@ -3229,16 +3554,16 @@ if ( !blend ) { - FT_TRACE2(( "\n" - "tt_face_vary_cvt: no blend specified\n" )); + FT_TRACE2(( "\n" )); + FT_TRACE2(( "tt_face_vary_cvt: no blend specified\n" )); error = FT_Err_Ok; goto Exit; } if ( !face->cvt ) { - FT_TRACE2(( "\n" - "tt_face_vary_cvt: no `cvt ' table\n" )); + FT_TRACE2(( "\n" )); + FT_TRACE2(( "tt_face_vary_cvt: no `cvt ' table\n" )); error = FT_Err_Ok; goto Exit; } @@ -3388,6 +3713,7 @@ } else { + localpoints = NULL; points = sharedpoints; point_count = spoint_count; } @@ -3397,9 +3723,7 @@ point_count == 0 ? face->cvt_size : point_count ); - if ( !points || - !deltas || - ( localpoints == ALL_POINTS && point_count != face->cvt_size ) ) + if ( !points || !deltas ) ; /* failure, ignore it */ else if ( localpoints == ALL_POINTS ) @@ -3425,10 +3749,10 @@ { FT_TRACE7(( " %d: %f -> %f\n", j, - ( FT_fdot6ToFixed( face->cvt[j] ) + - old_cvt_delta ) / 65536.0, - ( FT_fdot6ToFixed( face->cvt[j] ) + - cvt_deltas[j] ) / 65536.0 )); + (double)( FT_fdot6ToFixed( face->cvt[j] ) + + old_cvt_delta ) / 65536, + (double)( FT_fdot6ToFixed( face->cvt[j] ) + + cvt_deltas[j] ) / 65536 )); count++; } #endif @@ -3467,10 +3791,10 @@ { FT_TRACE7(( " %d: %f -> %f\n", pindex, - ( FT_fdot6ToFixed( face->cvt[pindex] ) + - old_cvt_delta ) / 65536.0, - ( FT_fdot6ToFixed( face->cvt[pindex] ) + - cvt_deltas[pindex] ) / 65536.0 )); + (double)( FT_fdot6ToFixed( face->cvt[pindex] ) + + old_cvt_delta ) / 65536, + (double)( FT_fdot6ToFixed( face->cvt[pindex] ) + + cvt_deltas[pindex] ) / 65536 )); count++; } #endif @@ -3514,6 +3838,16 @@ NULL ); return error; + +#else /* !TT_CONFIG_OPTION_BYTECODE_INTERPRETER */ + + FT_UNUSED( face ); + FT_UNUSED( stream ); + + return FT_Err_Ok; + +#endif /* !TT_CONFIG_OPTION_BYTECODE_INTERPRETER */ + } @@ -3725,20 +4059,12 @@ * @Description: * Apply the appropriate deltas to the current glyph. * - * @Input: - * face :: - * A handle to the target face object. - * - * glyph_index :: - * The index of the glyph being modified. - * - * n_points :: - * The number of the points in the glyph, including - * phantom points. - * * @InOut: + * loader :: + * A handle to the loader object. + * * outline :: - * The outline to change. + * The outline to change, with appended phantom points. * * @Output: * unrounded :: @@ -3749,15 +4075,16 @@ * FreeType error code. 0 means success. */ FT_LOCAL_DEF( FT_Error ) - TT_Vary_Apply_Glyph_Deltas( TT_Face face, - FT_UInt glyph_index, + TT_Vary_Apply_Glyph_Deltas( TT_Loader loader, FT_Outline* outline, - FT_Vector* unrounded, - FT_UInt n_points ) + FT_Vector* unrounded ) { FT_Error error; - FT_Stream stream = face->root.stream; - FT_Memory memory = stream->memory; + TT_Face face = loader->face; + FT_Stream stream = face->root.stream; + FT_Memory memory = stream->memory; + FT_UInt glyph_index = loader->glyph_index; + FT_UInt n_points = (FT_UInt)outline->n_points + 4; FT_Vector* points_org = NULL; /* coordinates in 16.16 format */ FT_Vector* points_out = NULL; /* coordinates in 16.16 format */ @@ -3975,50 +4302,22 @@ FT_Fixed point_delta_y = FT_MulFix( deltas_y[j], apply ); - if ( j < n_points - 4 ) - { - point_deltas_x[j] = old_point_delta_x + point_delta_x; - point_deltas_y[j] = old_point_delta_y + point_delta_y; - } - else - { - /* To avoid double adjustment of advance width or height, */ - /* adjust phantom points only if there is no HVAR or VVAR */ - /* support, respectively. */ - if ( j == ( n_points - 4 ) && - !( face->variation_support & - TT_FACE_FLAG_VAR_LSB ) ) - point_deltas_x[j] = old_point_delta_x + point_delta_x; - - else if ( j == ( n_points - 3 ) && - !( face->variation_support & - TT_FACE_FLAG_VAR_HADVANCE ) ) - point_deltas_x[j] = old_point_delta_x + point_delta_x; - - else if ( j == ( n_points - 2 ) && - !( face->variation_support & - TT_FACE_FLAG_VAR_TSB ) ) - point_deltas_y[j] = old_point_delta_y + point_delta_y; - - else if ( j == ( n_points - 1 ) && - !( face->variation_support & - TT_FACE_FLAG_VAR_VADVANCE ) ) - point_deltas_y[j] = old_point_delta_y + point_delta_y; - } + point_deltas_x[j] = old_point_delta_x + point_delta_x; + point_deltas_y[j] = old_point_delta_y + point_delta_y; #ifdef FT_DEBUG_LEVEL_TRACE if ( point_delta_x || point_delta_y ) { FT_TRACE7(( " %d: (%f, %f) -> (%f, %f)\n", j, - ( FT_intToFixed( outline->points[j].x ) + - old_point_delta_x ) / 65536.0, - ( FT_intToFixed( outline->points[j].y ) + - old_point_delta_y ) / 65536.0, - ( FT_intToFixed( outline->points[j].x ) + - point_deltas_x[j] ) / 65536.0, - ( FT_intToFixed( outline->points[j].y ) + - point_deltas_y[j] ) / 65536.0 )); + (double)( FT_intToFixed( outline->points[j].x ) + + old_point_delta_x ) / 65536, + (double)( FT_intToFixed( outline->points[j].y ) + + old_point_delta_y ) / 65536, + (double)( FT_intToFixed( outline->points[j].x ) + + point_deltas_x[j] ) / 65536, + (double)( FT_intToFixed( outline->points[j].y ) + + point_deltas_y[j] ) / 65536 )); count++; } #endif @@ -4077,50 +4376,22 @@ FT_Pos point_delta_y = points_out[j].y - points_org[j].y; - if ( j < n_points - 4 ) - { - point_deltas_x[j] = old_point_delta_x + point_delta_x; - point_deltas_y[j] = old_point_delta_y + point_delta_y; - } - else - { - /* To avoid double adjustment of advance width or height, */ - /* adjust phantom points only if there is no HVAR or VVAR */ - /* support, respectively. */ - if ( j == ( n_points - 4 ) && - !( face->variation_support & - TT_FACE_FLAG_VAR_LSB ) ) - point_deltas_x[j] = old_point_delta_x + point_delta_x; - - else if ( j == ( n_points - 3 ) && - !( face->variation_support & - TT_FACE_FLAG_VAR_HADVANCE ) ) - point_deltas_x[j] = old_point_delta_x + point_delta_x; - - else if ( j == ( n_points - 2 ) && - !( face->variation_support & - TT_FACE_FLAG_VAR_TSB ) ) - point_deltas_y[j] = old_point_delta_y + point_delta_y; - - else if ( j == ( n_points - 1 ) && - !( face->variation_support & - TT_FACE_FLAG_VAR_VADVANCE ) ) - point_deltas_y[j] = old_point_delta_y + point_delta_y; - } + point_deltas_x[j] = old_point_delta_x + point_delta_x; + point_deltas_y[j] = old_point_delta_y + point_delta_y; #ifdef FT_DEBUG_LEVEL_TRACE if ( point_delta_x || point_delta_y ) { FT_TRACE7(( " %d: (%f, %f) -> (%f, %f)\n", j, - ( FT_intToFixed( outline->points[j].x ) + - old_point_delta_x ) / 65536.0, - ( FT_intToFixed( outline->points[j].y ) + - old_point_delta_y ) / 65536.0, - ( FT_intToFixed( outline->points[j].x ) + - point_deltas_x[j] ) / 65536.0, - ( FT_intToFixed( outline->points[j].y ) + - point_deltas_y[j] ) / 65536.0 )); + (double)( FT_intToFixed( outline->points[j].x ) + + old_point_delta_x ) / 65536, + (double)( FT_intToFixed( outline->points[j].y ) + + old_point_delta_y ) / 65536, + (double)( FT_intToFixed( outline->points[j].x ) + + point_deltas_x[j] ) / 65536, + (double)( FT_intToFixed( outline->points[j].y ) + + point_deltas_y[j] ) / 65536 )); count++; } #endif @@ -4144,6 +4415,24 @@ FT_TRACE5(( "\n" )); + /* To avoid double adjustment of advance width or height, */ + /* do not move phantom points if there is HVAR or VVAR */ + /* support, respectively. */ + if ( face->variation_support & TT_FACE_FLAG_VAR_HADVANCE ) + { + point_deltas_x[n_points - 4] = 0; + point_deltas_y[n_points - 4] = 0; + point_deltas_x[n_points - 3] = 0; + point_deltas_y[n_points - 3] = 0; + } + if ( face->variation_support & TT_FACE_FLAG_VAR_VADVANCE ) + { + point_deltas_x[n_points - 2] = 0; + point_deltas_y[n_points - 2] = 0; + point_deltas_x[n_points - 1] = 0; + point_deltas_y[n_points - 1] = 0; + } + for ( i = 0; i < n_points; i++ ) { unrounded[i].x += FT_fixedToFdot6( point_deltas_x[i] ); @@ -4153,6 +4442,24 @@ outline->points[i].y += FT_fixedToInt( point_deltas_y[i] ); } + /* To avoid double adjustment of advance width or height, */ + /* adjust phantom points only if there is no HVAR or VVAR */ + /* support, respectively. */ + if ( !( face->variation_support & TT_FACE_FLAG_VAR_HADVANCE ) ) + { + loader->pp1 = outline->points[n_points - 4]; + loader->pp2 = outline->points[n_points - 3]; + loader->linear = FT_PIX_ROUND( unrounded[n_points - 3].x - + unrounded[n_points - 4].x ) / 64; + } + if ( !( face->variation_support & TT_FACE_FLAG_VAR_VADVANCE ) ) + { + loader->pp3 = outline->points[n_points - 2]; + loader->pp4 = outline->points[n_points - 1]; + loader->vadvance = FT_PIX_ROUND( unrounded[n_points - 1].y - + unrounded[n_points - 2].y ) / 64; + } + Fail3: FT_FREE( point_deltas_x ); FT_FREE( point_deltas_y ); @@ -4186,22 +4493,25 @@ * the MM machinery in case it isn't loaded yet. */ FT_LOCAL_DEF( FT_Error ) - tt_get_var_blend( TT_Face face, + tt_get_var_blend( FT_Face face, /* TT_Face */ FT_UInt *num_coords, FT_Fixed* *coords, FT_Fixed* *normalizedcoords, FT_MM_Var* *mm_var ) { - if ( face->blend ) + TT_Face ttface = (TT_Face)face; + + + if ( ttface->blend ) { if ( num_coords ) - *num_coords = face->blend->num_axis; + *num_coords = ttface->blend->num_axis; if ( coords ) - *coords = face->blend->coords; + *coords = ttface->blend->coords; if ( normalizedcoords ) - *normalizedcoords = face->blend->normalizedcoords; + *normalizedcoords = ttface->blend->normalizedcoords; if ( mm_var ) - *mm_var = face->blend->mmvar; + *mm_var = ttface->blend->mmvar; } else { @@ -4217,8 +4527,8 @@ } - static void - ft_var_done_item_variation_store( TT_Face face, + FT_LOCAL_DEF( void ) + tt_var_done_item_variation_store( FT_Face face, GX_ItemVarStore itemStore ) { FT_Memory memory = FT_FACE_MEMORY( face ); @@ -4246,6 +4556,18 @@ } + FT_LOCAL_DEF( void ) + tt_var_done_delta_set_index_map( FT_Face face, + GX_DeltaSetIdxMap deltaSetIdxMap ) + { + FT_Memory memory = FT_FACE_MEMORY( face ); + + + FT_FREE( deltaSetIdxMap->innerIndex ); + FT_FREE( deltaSetIdxMap->outerIndex ); + } + + /************************************************************************** * * @Function: @@ -4255,10 +4577,11 @@ * Free the blend internal data structure. */ FT_LOCAL_DEF( void ) - tt_done_blend( TT_Face face ) + tt_done_blend( FT_Face face ) { + TT_Face ttface = (TT_Face)face; FT_Memory memory = FT_FACE_MEMORY( face ); - GX_Blend blend = face->blend; + GX_Blend blend = ttface->blend; if ( blend ) @@ -4274,36 +4597,47 @@ FT_FREE( blend->normalized_stylecoords ); FT_FREE( blend->mmvar ); - if ( blend->avar_segment ) + if ( blend->avar_table ) { - for ( i = 0; i < num_axes; i++ ) - FT_FREE( blend->avar_segment[i].correspondence ); - FT_FREE( blend->avar_segment ); + if ( blend->avar_table->avar_segment ) + { + for ( i = 0; i < num_axes; i++ ) + FT_FREE( blend->avar_table->avar_segment[i].correspondence ); + FT_FREE( blend->avar_table->avar_segment ); + } + + tt_var_done_item_variation_store( face, + &blend->avar_table->itemStore ); + + tt_var_done_delta_set_index_map( face, + &blend->avar_table->axisMap ); + + FT_FREE( blend->avar_table ); } if ( blend->hvar_table ) { - ft_var_done_item_variation_store( face, + tt_var_done_item_variation_store( face, &blend->hvar_table->itemStore ); - FT_FREE( blend->hvar_table->widthMap.innerIndex ); - FT_FREE( blend->hvar_table->widthMap.outerIndex ); + tt_var_done_delta_set_index_map( face, + &blend->hvar_table->widthMap ); FT_FREE( blend->hvar_table ); } if ( blend->vvar_table ) { - ft_var_done_item_variation_store( face, + tt_var_done_item_variation_store( face, &blend->vvar_table->itemStore ); - FT_FREE( blend->vvar_table->widthMap.innerIndex ); - FT_FREE( blend->vvar_table->widthMap.outerIndex ); + tt_var_done_delta_set_index_map( face, + &blend->vvar_table->widthMap ); FT_FREE( blend->vvar_table ); } if ( blend->mvar_table ) { - ft_var_done_item_variation_store( face, + tt_var_done_item_variation_store( face, &blend->mvar_table->itemStore ); FT_FREE( blend->mvar_table->values ); @@ -4319,7 +4653,7 @@ #else /* !TT_CONFIG_OPTION_GX_VAR_SUPPORT */ /* ANSI C doesn't like empty source files */ - typedef int _tt_gxvar_dummy; + typedef int tt_gxvar_dummy_; #endif /* !TT_CONFIG_OPTION_GX_VAR_SUPPORT */ diff --git a/src/font/freetype-2.10.2/src/truetype/ttgxvar.h b/3rdparty/freetype-2.13.2/src/truetype/ttgxvar.h similarity index 82% rename from src/font/freetype-2.10.2/src/truetype/ttgxvar.h rename to 3rdparty/freetype-2.13.2/src/truetype/ttgxvar.h index 11664e997..e3da6d170 100644 --- a/src/font/freetype-2.10.2/src/truetype/ttgxvar.h +++ b/3rdparty/freetype-2.13.2/src/truetype/ttgxvar.h @@ -4,7 +4,7 @@ * * TrueType GX Font Variation loader (specification) * - * Copyright (C) 2004-2020 by + * Copyright (C) 2004-2023 by * David Turner, Robert Wilhelm, Werner Lemberg and George Williams. * * This file is part of the FreeType project, and may only be used, @@ -20,7 +20,7 @@ #define TTGXVAR_H_ -#include +#include #include "ttobjs.h" @@ -63,55 +63,21 @@ FT_BEGIN_HEADER } GX_AVarSegmentRec, *GX_AVarSegment; - typedef struct GX_ItemVarDataRec_ - { - FT_UInt itemCount; /* number of delta sets per item */ - FT_UInt regionIdxCount; /* number of region indices in this data */ - FT_UInt* regionIndices; /* array of `regionCount' indices; */ - /* these index `varRegionList' */ - FT_Short* deltaSet; /* array of `itemCount' deltas */ - /* use `innerIndex' for this array */ - - } GX_ItemVarDataRec, *GX_ItemVarData; - - - /* contribution of one axis to a region */ - typedef struct GX_AxisCoordsRec_ - { - FT_Fixed startCoord; - FT_Fixed peakCoord; /* zero means no effect (factor = 1) */ - FT_Fixed endCoord; - - } GX_AxisCoordsRec, *GX_AxisCoords; - - - typedef struct GX_VarRegionRec_ - { - GX_AxisCoords axisList; /* array of axisCount records */ - - } GX_VarRegionRec, *GX_VarRegion; - - - /* item variation store */ - typedef struct GX_ItemVarStoreRec_ - { - FT_UInt dataCount; - GX_ItemVarData varData; /* array of dataCount records; */ - /* use `outerIndex' for this array */ - FT_UShort axisCount; - FT_UInt regionCount; /* total number of regions defined */ - GX_VarRegion varRegionList; - - } GX_ItemVarStoreRec, *GX_ItemVarStore; - - - typedef struct GX_DeltaSetIdxMapRec_ + /************************************************************************** + * + * @Struct: + * GX_AVarTableRec + * + * @Description: + * Data from the `avar' table. + */ + typedef struct GX_AVarTableRec_ { - FT_UInt mapCount; - FT_UInt* outerIndex; /* indices to item var data */ - FT_UInt* innerIndex; /* indices to delta set */ + GX_AVarSegment avar_segment; /* avar_segment[num_axis] */ + GX_ItemVarStoreRec itemStore; /* Item Variation Store */ + GX_DeltaSetIdxMapRec axisMap; /* Axis Mapping */ - } GX_DeltaSetIdxMapRec, *GX_DeltaSetIdxMap; + } GX_AVarTableRec, *GX_AVarTable; /************************************************************************** @@ -246,7 +212,7 @@ FT_BEGIN_HEADER * A Boolean; if set, FreeType tried to load (and parse) the `avar' * table. * - * avar_segment :: + * avar_table :: * Data from the `avar' table. * * hvar_loaded :: @@ -311,7 +277,7 @@ FT_BEGIN_HEADER /* normalized_stylecoords[num_namedstyles][num_axis] */ FT_Bool avar_loaded; - GX_AVarSegment avar_segment; /* avar_segment[num_axis] */ + GX_AVarTable avar_table; FT_Bool hvar_loaded; FT_Bool hvar_checked; @@ -377,70 +343,103 @@ FT_BEGIN_HEADER #define TTAG_wdth FT_MAKE_TAG( 'w', 'd', 't', 'h' ) #define TTAG_opsz FT_MAKE_TAG( 'o', 'p', 's', 'z' ) #define TTAG_slnt FT_MAKE_TAG( 's', 'l', 'n', 't' ) +#define TTAG_ital FT_MAKE_TAG( 'i', 't', 'a', 'l' ) FT_LOCAL( FT_Error ) - TT_Set_MM_Blend( TT_Face face, + TT_Set_MM_Blend( FT_Face face, FT_UInt num_coords, FT_Fixed* coords ); FT_LOCAL( FT_Error ) - TT_Get_MM_Blend( TT_Face face, + TT_Get_MM_Blend( FT_Face face, FT_UInt num_coords, FT_Fixed* coords ); FT_LOCAL( FT_Error ) - TT_Set_Var_Design( TT_Face face, + TT_Set_Var_Design( FT_Face face, FT_UInt num_coords, FT_Fixed* coords ); FT_LOCAL( FT_Error ) - TT_Get_MM_Var( TT_Face face, + TT_Get_MM_Var( FT_Face face, FT_MM_Var* *master ); FT_LOCAL( FT_Error ) - TT_Get_Var_Design( TT_Face face, + TT_Get_Var_Design( FT_Face face, FT_UInt num_coords, FT_Fixed* coords ); FT_LOCAL( FT_Error ) - TT_Set_Named_Instance( TT_Face face, + TT_Set_Named_Instance( FT_Face face, FT_UInt instance_index ); + FT_LOCAL( FT_Error ) + TT_Get_Default_Named_Instance( FT_Face face, + FT_UInt *instance_index ); + + FT_LOCAL( void ) + tt_construct_ps_name( FT_Face face ); + FT_LOCAL( FT_Error ) tt_face_vary_cvt( TT_Face face, FT_Stream stream ); FT_LOCAL( FT_Error ) - TT_Vary_Apply_Glyph_Deltas( TT_Face face, - FT_UInt glyph_index, + TT_Vary_Apply_Glyph_Deltas( TT_Loader loader, FT_Outline* outline, - FT_Vector* unrounded, - FT_UInt n_points ); + FT_Vector* unrounded ); FT_LOCAL( FT_Error ) - tt_hadvance_adjust( TT_Face face, + tt_hadvance_adjust( FT_Face face, FT_UInt gindex, FT_Int *adelta ); FT_LOCAL( FT_Error ) - tt_vadvance_adjust( TT_Face face, + tt_vadvance_adjust( FT_Face face, FT_UInt gindex, FT_Int *adelta ); FT_LOCAL( void ) - tt_apply_mvar( TT_Face face ); + tt_apply_mvar( FT_Face face ); + + FT_LOCAL( FT_Error ) + tt_var_load_item_variation_store( FT_Face face, + FT_ULong offset, + GX_ItemVarStore itemStore ); + + FT_LOCAL( FT_Error ) + tt_var_load_delta_set_index_mapping( FT_Face face, + FT_ULong offset, + GX_DeltaSetIdxMap map, + GX_ItemVarStore itemStore, + FT_ULong table_len ); + + FT_LOCAL( FT_ItemVarDelta ) + tt_var_get_item_delta( FT_Face face, + GX_ItemVarStore itemStore, + FT_UInt outerIndex, + FT_UInt innerIndex ); + + FT_LOCAL( void ) + tt_var_done_item_variation_store( FT_Face face, + GX_ItemVarStore itemStore ); + + FT_LOCAL( void ) + tt_var_done_delta_set_index_map( FT_Face face, + GX_DeltaSetIdxMap deltaSetIdxMap ); + FT_LOCAL( FT_Error ) - tt_get_var_blend( TT_Face face, + tt_get_var_blend( FT_Face face, FT_UInt *num_coords, FT_Fixed* *coords, FT_Fixed* *normalizedcoords, FT_MM_Var* *mm_var ); FT_LOCAL( void ) - tt_done_blend( TT_Face face ); + tt_done_blend( FT_Face face ); #endif /* TT_CONFIG_OPTION_GX_VAR_SUPPORT */ diff --git a/src/font/freetype-2.10.2/src/truetype/ttinterp.c b/3rdparty/freetype-2.13.2/src/truetype/ttinterp.c similarity index 82% rename from src/font/freetype-2.10.2/src/truetype/ttinterp.c rename to 3rdparty/freetype-2.13.2/src/truetype/ttinterp.c index 321504097..79df4555d 100644 --- a/src/font/freetype-2.10.2/src/truetype/ttinterp.c +++ b/3rdparty/freetype-2.13.2/src/truetype/ttinterp.c @@ -4,7 +4,7 @@ * * TrueType bytecode interpreter (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,17 +20,15 @@ /* issues; many thanks! */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_CALC_H -#include FT_TRIGONOMETRY_H -#include FT_SYSTEM_H -#include FT_DRIVER_H -#include FT_MULTIPLE_MASTERS_H +#include +#include +#include +#include +#include +#include #include "ttinterp.h" #include "tterrors.h" -#include "ttsubpix.h" #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT #include "ttgxvar.h" #endif @@ -53,12 +51,6 @@ ( ((TT_Driver)FT_FACE_DRIVER( exc->face ))->interpreter_version == \ TT_INTERPRETER_VERSION_35 ) -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY -#define SUBPIXEL_HINTING_INFINALITY \ - ( ((TT_Driver)FT_FACE_DRIVER( exc->face ))->interpreter_version == \ - TT_INTERPRETER_VERSION_38 ) -#endif - #ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL #define SUBPIXEL_HINTING_MINIMAL \ ( ((TT_Driver)FT_FACE_DRIVER( exc->face ))->interpreter_version == \ @@ -252,6 +244,14 @@ FT_FREE( exec->stack ); exec->stackSize = 0; + /* free glyf cvt working area */ + FT_FREE( exec->glyfCvt ); + exec->glyfCvtSize = 0; + + /* free glyf storage working area */ + FT_FREE( exec->glyfStorage ); + exec->glyfStoreSize = 0; + /* free call stack */ FT_FREE( exec->callStack ); exec->callSize = 0; @@ -268,115 +268,6 @@ } - /************************************************************************** - * - * @Function: - * Init_Context - * - * @Description: - * Initializes a context object. - * - * @Input: - * memory :: - * A handle to the parent memory object. - * - * @InOut: - * exec :: - * A handle to the target execution context. - * - * @Return: - * FreeType error code. 0 means success. - */ - static FT_Error - Init_Context( TT_ExecContext exec, - FT_Memory memory ) - { - FT_Error error; - - - FT_TRACE1(( "Init_Context: new object at 0x%08p\n", exec )); - - exec->memory = memory; - exec->callSize = 32; - - if ( FT_NEW_ARRAY( exec->callStack, exec->callSize ) ) - goto Fail_Memory; - - /* all values in the context are set to 0 already, but this is */ - /* here as a remainder */ - exec->maxPoints = 0; - exec->maxContours = 0; - - exec->stackSize = 0; - exec->glyphSize = 0; - - exec->stack = NULL; - exec->glyphIns = NULL; - - exec->face = NULL; - exec->size = NULL; - - return FT_Err_Ok; - - Fail_Memory: - FT_ERROR(( "Init_Context: not enough memory for %p\n", exec )); - TT_Done_Context( exec ); - - return error; - } - - - /************************************************************************** - * - * @Function: - * Update_Max - * - * @Description: - * Checks the size of a buffer and reallocates it if necessary. - * - * @Input: - * memory :: - * A handle to the parent memory object. - * - * multiplier :: - * The size in bytes of each element in the buffer. - * - * new_max :: - * The new capacity (size) of the buffer. - * - * @InOut: - * size :: - * The address of the buffer's current size expressed - * in elements. - * - * buff :: - * The address of the buffer base pointer. - * - * @Return: - * FreeType error code. 0 means success. - */ - FT_LOCAL_DEF( FT_Error ) - Update_Max( FT_Memory memory, - FT_ULong* size, - FT_ULong multiplier, - void* _pbuff, - FT_ULong new_max ) - { - FT_Error error; - void** pbuff = (void**)_pbuff; - - - if ( *size < new_max ) - { - if ( FT_REALLOC( *pbuff, *size * multiplier, new_max * multiplier ) ) - return error; - *size = new_max; - } - - return FT_Err_Ok; - } - - /************************************************************************** * * @Function: @@ -401,6 +292,8 @@ * * @Note: * Only the glyph loader and debugger should call this function. + * + * Note that not all members of `TT_ExecContext` get initialized. */ FT_LOCAL_DEF( FT_Error ) TT_Load_Context( TT_ExecContext exec, @@ -408,9 +301,9 @@ TT_Size size ) { FT_Int i; - FT_ULong tmp; TT_MaxProfile* maxp; FT_Error error; + FT_Memory memory = exec->memory; exec->face = face; @@ -455,25 +348,15 @@ /* XXX: We reserve a little more elements on the stack to deal safely */ /* with broken fonts like arialbs, courbs, timesbs, etc. */ - tmp = (FT_ULong)exec->stackSize; - error = Update_Max( exec->memory, - &tmp, - sizeof ( FT_F26Dot6 ), - (void*)&exec->stack, - maxp->maxStackElements + 32 ); - exec->stackSize = (FT_Long)tmp; - if ( error ) + if ( FT_QRENEW_ARRAY( exec->stack, + exec->stackSize, + maxp->maxStackElements + 32 ) ) return error; + exec->stackSize = maxp->maxStackElements + 32; - tmp = exec->glyphSize; - error = Update_Max( exec->memory, - &tmp, - sizeof ( FT_Byte ), - (void*)&exec->glyphIns, - maxp->maxSizeOfInstructions ); - exec->glyphSize = (FT_UShort)tmp; - if ( error ) - return error; + /* free previous glyph code range */ + FT_FREE( exec->glyphIns ); + exec->glyphSize = 0; exec->pts.n_points = 0; exec->pts.n_contours = 0; @@ -610,19 +493,19 @@ memory = driver->root.root.memory; - /* allocate object */ + /* allocate object and zero everything inside */ if ( FT_NEW( exec ) ) goto Fail; - /* initialize it; in case of error this deallocates `exec' too */ - error = Init_Context( exec, memory ); - if ( error ) - goto Fail; + /* create callStack here, other allocations delayed */ + exec->memory = memory; + exec->callSize = 32; - return exec; + if ( FT_QNEW_ARRAY( exec->callStack, exec->callSize ) ) + FT_FREE( exec ); Fail: - return NULL; + return exec; } @@ -1573,11 +1456,37 @@ } + static void + Modify_CVT_Check( TT_ExecContext exc ) + { + if ( exc->iniRange == tt_coderange_glyph && + exc->cvt != exc->glyfCvt ) + { + FT_Memory memory = exc->memory; + FT_Error error; + + + FT_MEM_QRENEW_ARRAY( exc->glyfCvt, exc->glyfCvtSize, exc->cvtSize ); + exc->error = error; + if ( error ) + return; + + exc->glyfCvtSize = exc->cvtSize; + FT_ARRAY_COPY( exc->glyfCvt, exc->cvt, exc->glyfCvtSize ); + exc->cvt = exc->glyfCvt; + } + } + + FT_CALLBACK_DEF( void ) Write_CVT( TT_ExecContext exc, FT_ULong idx, FT_F26Dot6 value ) { + Modify_CVT_Check( exc ); + if ( exc->error ) + return; + exc->cvt[idx] = value; } @@ -1587,6 +1496,10 @@ FT_ULong idx, FT_F26Dot6 value ) { + Modify_CVT_Check( exc ); + if ( exc->error ) + return; + exc->cvt[idx] = FT_DivFix( value, Current_Ratio( exc ) ); } @@ -1596,6 +1509,10 @@ FT_ULong idx, FT_F26Dot6 value ) { + Modify_CVT_Check( exc ); + if ( exc->error ) + return; + exc->cvt[idx] = ADD_LONG( exc->cvt[idx], value ); } @@ -1605,6 +1522,10 @@ FT_ULong idx, FT_F26Dot6 value ) { + Modify_CVT_Check( exc ); + if ( exc->error ) + return; + exc->cvt[idx] = ADD_LONG( exc->cvt[idx], FT_DivFix( value, Current_Ratio( exc ) ) ); } @@ -1757,17 +1678,6 @@ if ( v != 0 ) { -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY && - ( !exc->ignore_x_mode || - ( exc->sph_tweak_flags & SPH_TWEAK_ALLOW_X_DMOVE ) ) ) - zone->cur[point].x = ADD_LONG( zone->cur[point].x, - FT_MulDiv( distance, - v, - exc->F_dot_P ) ); - else -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - #ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL /* Exception to the post-IUP curfew: Allow the x component of */ /* diagonal moves, but only post-IUP. DejaVu tries to adjust */ @@ -1873,12 +1783,6 @@ FT_UShort point, FT_F26Dot6 distance ) { -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY && !exc->ignore_x_mode ) - zone->cur[point].x = ADD_LONG( zone->cur[point].x, distance ); - else -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - #ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL if ( SUBPIXEL_HINTING_MINIMAL && !exc->backward_compatibility ) zone->cur[point].x = ADD_LONG( zone->cur[point].x, distance ); @@ -1956,8 +1860,8 @@ * distance :: * The distance (not) to round. * - * compensation :: - * The engine compensation. + * color :: + * The engine compensation color. * * @Return: * The compensated distance. @@ -1965,12 +1869,11 @@ static FT_F26Dot6 Round_None( TT_ExecContext exc, FT_F26Dot6 distance, - FT_F26Dot6 compensation ) + FT_Int color ) { + FT_F26Dot6 compensation = exc->tt_metrics.compensations[color]; FT_F26Dot6 val; - FT_UNUSED( exc ); - if ( distance >= 0 ) { @@ -2000,8 +1903,8 @@ * distance :: * The distance to round. * - * compensation :: - * The engine compensation. + * color :: + * The engine compensation color. * * @Return: * Rounded distance. @@ -2009,12 +1912,11 @@ static FT_F26Dot6 Round_To_Grid( TT_ExecContext exc, FT_F26Dot6 distance, - FT_F26Dot6 compensation ) + FT_Int color ) { + FT_F26Dot6 compensation = exc->tt_metrics.compensations[color]; FT_F26Dot6 val; - FT_UNUSED( exc ); - if ( distance >= 0 ) { @@ -2046,8 +1948,8 @@ * distance :: * The distance to round. * - * compensation :: - * The engine compensation. + * color :: + * The engine compensation color. * * @Return: * Rounded distance. @@ -2055,12 +1957,11 @@ static FT_F26Dot6 Round_To_Half_Grid( TT_ExecContext exc, FT_F26Dot6 distance, - FT_F26Dot6 compensation ) + FT_Int color ) { + FT_F26Dot6 compensation = exc->tt_metrics.compensations[color]; FT_F26Dot6 val; - FT_UNUSED( exc ); - if ( distance >= 0 ) { @@ -2094,8 +1995,8 @@ * distance :: * The distance to round. * - * compensation :: - * The engine compensation. + * color :: + * The engine compensation color. * * @Return: * Rounded distance. @@ -2103,12 +2004,11 @@ static FT_F26Dot6 Round_Down_To_Grid( TT_ExecContext exc, FT_F26Dot6 distance, - FT_F26Dot6 compensation ) + FT_Int color ) { + FT_F26Dot6 compensation = exc->tt_metrics.compensations[color]; FT_F26Dot6 val; - FT_UNUSED( exc ); - if ( distance >= 0 ) { @@ -2139,8 +2039,8 @@ * distance :: * The distance to round. * - * compensation :: - * The engine compensation. + * color :: + * The engine compensation color. * * @Return: * Rounded distance. @@ -2148,12 +2048,11 @@ static FT_F26Dot6 Round_Up_To_Grid( TT_ExecContext exc, FT_F26Dot6 distance, - FT_F26Dot6 compensation ) + FT_Int color ) { + FT_F26Dot6 compensation = exc->tt_metrics.compensations[color]; FT_F26Dot6 val; - FT_UNUSED( exc ); - if ( distance >= 0 ) { @@ -2185,8 +2084,8 @@ * distance :: * The distance to round. * - * compensation :: - * The engine compensation. + * color :: + * The engine compensation color. * * @Return: * Rounded distance. @@ -2194,12 +2093,11 @@ static FT_F26Dot6 Round_To_Double_Grid( TT_ExecContext exc, FT_F26Dot6 distance, - FT_F26Dot6 compensation ) + FT_Int color ) { + FT_F26Dot6 compensation = exc->tt_metrics.compensations[color]; FT_F26Dot6 val; - FT_UNUSED( exc ); - if ( distance >= 0 ) { @@ -2231,8 +2129,8 @@ * distance :: * The distance to round. * - * compensation :: - * The engine compensation. + * color :: + * The engine compensation color. * * @Return: * Rounded distance. @@ -2246,8 +2144,9 @@ static FT_F26Dot6 Round_Super( TT_ExecContext exc, FT_F26Dot6 distance, - FT_F26Dot6 compensation ) + FT_Int color ) { + FT_F26Dot6 compensation = exc->tt_metrics.compensations[color]; FT_F26Dot6 val; @@ -2286,8 +2185,8 @@ * distance :: * The distance to round. * - * compensation :: - * The engine compensation. + * color :: + * The engine compensation color. * * @Return: * Rounded distance. @@ -2299,8 +2198,9 @@ static FT_F26Dot6 Round_Super_45( TT_ExecContext exc, FT_F26Dot6 distance, - FT_F26Dot6 compensation ) + FT_Int color ) { + FT_F26Dot6 compensation = exc->tt_metrics.compensations[color]; FT_F26Dot6 val; @@ -2899,7 +2799,7 @@ Ins_ODD( TT_ExecContext exc, FT_Long* args ) { - args[0] = ( ( exc->func_round( exc, args[0], 0 ) & 127 ) == 64 ); + args[0] = ( ( exc->func_round( exc, args[0], 3 ) & 127 ) == 64 ); } @@ -2913,7 +2813,7 @@ Ins_EVEN( TT_ExecContext exc, FT_Long* args ) { - args[0] = ( ( exc->func_round( exc, args[0], 0 ) & 127 ) == 0 ); + args[0] = ( ( exc->func_round( exc, args[0], 3 ) & 127 ) == 0 ); } @@ -3086,28 +2986,7 @@ args[0] = 0; } else - { -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - /* subpixel hinting - avoid Typeman Dstroke and */ - /* IStroke and Vacuform rounds */ - if ( SUBPIXEL_HINTING_INFINALITY && - exc->ignore_x_mode && - ( ( I == 24 && - ( exc->face->sph_found_func_flags & - ( SPH_FDEF_SPACING_1 | - SPH_FDEF_SPACING_2 ) ) ) || - ( I == 22 && - ( exc->sph_in_func_flags & - SPH_FDEF_TYPEMAN_STROKES ) ) || - ( I == 8 && - ( exc->face->sph_found_func_flags & - SPH_FDEF_VACUFORM_ROUND_1 ) && - exc->iup_called ) ) ) - args[0] = 0; - else -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - args[0] = exc->storage[I]; - } + args[0] = exc->storage[I]; } @@ -3130,7 +3009,28 @@ ARRAY_BOUND_ERROR; } else + { + if ( exc->iniRange == tt_coderange_glyph && + exc->storage != exc->glyfStorage ) + { + FT_Memory memory = exc->memory; + FT_Error error; + + + FT_MEM_QRENEW_ARRAY( exc->glyfStorage, + exc->glyfStoreSize, + exc->storeSize ); + exc->error = error; + if ( error ) + return; + + exc->glyfStoreSize = exc->storeSize; + FT_ARRAY_COPY( exc->glyfStorage, exc->storage, exc->glyfStoreSize ); + exc->storage = exc->glyfStorage; + } + exc->storage[I] = args[1]; + } } @@ -3243,10 +3143,7 @@ Ins_ROUND( TT_ExecContext exc, FT_Long* args ) { - args[0] = exc->func_round( - exc, - args[0], - exc->tt_metrics.compensations[exc->opcode - 0x68] ); + args[0] = exc->func_round( exc, args[0], exc->opcode & 3 ); } @@ -3260,10 +3157,7 @@ Ins_NROUND( TT_ExecContext exc, FT_Long* args ) { - args[0] = Round_None( - exc, - args[0], - exc->tt_metrics.compensations[exc->opcode - 0x6C] ); + args[0] = Round_None( exc, args[0], exc->opcode & 3 ); } @@ -3536,7 +3430,7 @@ return; } - exc->IP += args[0]; + exc->IP = ADD_LONG( exc->IP, args[0] ); if ( exc->IP < 0 || ( exc->callTop > 0 && exc->IP > exc->callStack[exc->callTop - 1].Def->end ) ) @@ -3606,109 +3500,9 @@ TT_DefRecord* rec; TT_DefRecord* limit; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - /* arguments to opcodes are skipped by `SKIP_Code' */ - FT_Byte opcode_pattern[9][12] = { - /* #0 inline delta function 1 */ - { - 0x4B, /* PPEM */ - 0x53, /* GTEQ */ - 0x23, /* SWAP */ - 0x4B, /* PPEM */ - 0x51, /* LTEQ */ - 0x5A, /* AND */ - 0x58, /* IF */ - 0x38, /* SHPIX */ - 0x1B, /* ELSE */ - 0x21, /* POP */ - 0x21, /* POP */ - 0x59 /* EIF */ - }, - /* #1 inline delta function 2 */ - { - 0x4B, /* PPEM */ - 0x54, /* EQ */ - 0x58, /* IF */ - 0x38, /* SHPIX */ - 0x1B, /* ELSE */ - 0x21, /* POP */ - 0x21, /* POP */ - 0x59 /* EIF */ - }, - /* #2 diagonal stroke function */ - { - 0x20, /* DUP */ - 0x20, /* DUP */ - 0xB0, /* PUSHB_1 */ - /* 1 */ - 0x60, /* ADD */ - 0x46, /* GC_cur */ - 0xB0, /* PUSHB_1 */ - /* 64 */ - 0x23, /* SWAP */ - 0x42 /* WS */ - }, - /* #3 VacuFormRound function */ - { - 0x45, /* RCVT */ - 0x23, /* SWAP */ - 0x46, /* GC_cur */ - 0x60, /* ADD */ - 0x20, /* DUP */ - 0xB0 /* PUSHB_1 */ - /* 38 */ - }, - /* #4 TTFautohint bytecode (old) */ - { - 0x20, /* DUP */ - 0x64, /* ABS */ - 0xB0, /* PUSHB_1 */ - /* 32 */ - 0x60, /* ADD */ - 0x66, /* FLOOR */ - 0x23, /* SWAP */ - 0xB0 /* PUSHB_1 */ - }, - /* #5 spacing function 1 */ - { - 0x01, /* SVTCA_x */ - 0xB0, /* PUSHB_1 */ - /* 24 */ - 0x43, /* RS */ - 0x58 /* IF */ - }, - /* #6 spacing function 2 */ - { - 0x01, /* SVTCA_x */ - 0x18, /* RTG */ - 0xB0, /* PUSHB_1 */ - /* 24 */ - 0x43, /* RS */ - 0x58 /* IF */ - }, - /* #7 TypeMan Talk DiagEndCtrl function */ - { - 0x01, /* SVTCA_x */ - 0x20, /* DUP */ - 0xB0, /* PUSHB_1 */ - /* 3 */ - 0x25, /* CINDEX */ - }, - /* #8 TypeMan Talk Align */ - { - 0x06, /* SPVTL */ - 0x7D, /* RDTG */ - }, - }; - FT_UShort opcode_patterns = 9; - FT_UShort opcode_pointer[9] = { 0, 0, 0, 0, 0, 0, 0, 0, 0 }; - FT_UShort opcode_size[9] = { 12, 8, 8, 6, 7, 4, 5, 4, 2 }; - FT_UShort i; -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - /* FDEF is only allowed in `prep' or `fpgm' */ - if ( exc->curRange == tt_coderange_glyph ) + if ( exc->iniRange == tt_coderange_glyph ) { exc->error = FT_THROW( DEF_In_Glyf_Bytecode ); return; @@ -3750,136 +3544,15 @@ rec->opc = (FT_UInt16)n; rec->start = exc->IP + 1; rec->active = TRUE; - rec->inline_delta = FALSE; - rec->sph_fdef_flags = 0x0000; if ( n > exc->maxFunc ) exc->maxFunc = (FT_UInt16)n; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - /* We don't know for sure these are typeman functions, */ - /* however they are only active when RS 22 is called */ - if ( n >= 64 && n <= 66 ) - rec->sph_fdef_flags |= SPH_FDEF_TYPEMAN_STROKES; -#endif - /* Now skip the whole function definition. */ /* We don't allow nested IDEFS & FDEFs. */ while ( SkipCode( exc ) == SUCCESS ) { - -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - - if ( SUBPIXEL_HINTING_INFINALITY ) - { - for ( i = 0; i < opcode_patterns; i++ ) - { - if ( opcode_pointer[i] < opcode_size[i] && - exc->opcode == opcode_pattern[i][opcode_pointer[i]] ) - { - opcode_pointer[i] += 1; - - if ( opcode_pointer[i] == opcode_size[i] ) - { - FT_TRACE6(( "sph: Function %d, opcode ptrn: %d, %s %s\n", - i, n, - exc->face->root.family_name, - exc->face->root.style_name )); - - switch ( i ) - { - case 0: - rec->sph_fdef_flags |= SPH_FDEF_INLINE_DELTA_1; - exc->face->sph_found_func_flags |= SPH_FDEF_INLINE_DELTA_1; - break; - - case 1: - rec->sph_fdef_flags |= SPH_FDEF_INLINE_DELTA_2; - exc->face->sph_found_func_flags |= SPH_FDEF_INLINE_DELTA_2; - break; - - case 2: - switch ( n ) - { - /* needs to be implemented still */ - case 58: - rec->sph_fdef_flags |= SPH_FDEF_DIAGONAL_STROKE; - exc->face->sph_found_func_flags |= SPH_FDEF_DIAGONAL_STROKE; - } - break; - - case 3: - switch ( n ) - { - case 0: - rec->sph_fdef_flags |= SPH_FDEF_VACUFORM_ROUND_1; - exc->face->sph_found_func_flags |= SPH_FDEF_VACUFORM_ROUND_1; - } - break; - - case 4: - /* probably not necessary to detect anymore */ - rec->sph_fdef_flags |= SPH_FDEF_TTFAUTOHINT_1; - exc->face->sph_found_func_flags |= SPH_FDEF_TTFAUTOHINT_1; - break; - - case 5: - switch ( n ) - { - case 0: - case 1: - case 2: - case 4: - case 7: - case 8: - rec->sph_fdef_flags |= SPH_FDEF_SPACING_1; - exc->face->sph_found_func_flags |= SPH_FDEF_SPACING_1; - } - break; - - case 6: - switch ( n ) - { - case 0: - case 1: - case 2: - case 4: - case 7: - case 8: - rec->sph_fdef_flags |= SPH_FDEF_SPACING_2; - exc->face->sph_found_func_flags |= SPH_FDEF_SPACING_2; - } - break; - - case 7: - rec->sph_fdef_flags |= SPH_FDEF_TYPEMAN_DIAGENDCTRL; - exc->face->sph_found_func_flags |= SPH_FDEF_TYPEMAN_DIAGENDCTRL; - break; - - case 8: -#if 0 - rec->sph_fdef_flags |= SPH_FDEF_TYPEMAN_DIAGENDCTRL; - exc->face->sph_found_func_flags |= SPH_FDEF_TYPEMAN_DIAGENDCTRL; -#endif - break; - } - opcode_pointer[i] = 0; - } - } - - else - opcode_pointer[i] = 0; - } - - /* Set sph_compatibility_mode only when deltas are detected */ - exc->face->sph_compatibility_mode = - ( ( exc->face->sph_found_func_flags & SPH_FDEF_INLINE_DELTA_1 ) | - ( exc->face->sph_found_func_flags & SPH_FDEF_INLINE_DELTA_2 ) ); - } - -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - switch ( exc->opcode ) { case 0x89: /* IDEF */ @@ -3907,10 +3580,6 @@ TT_CallRec* pRec; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - exc->sph_in_func_flags = 0x0000; -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - if ( exc->callTop <= 0 ) /* We encountered an ENDF without a call */ { exc->error = FT_THROW( ENDF_In_Exec_Stream ); @@ -3998,17 +3667,6 @@ if ( !def->active ) goto Fail; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY && - exc->ignore_x_mode && - ( ( exc->iup_called && - ( exc->sph_tweak_flags & SPH_TWEAK_NO_CALL_AFTER_IUP ) ) || - ( def->sph_fdef_flags & SPH_FDEF_VACUFORM_ROUND_1 ) ) ) - goto Fail; - else - exc->sph_in_func_flags = def->sph_fdef_flags; -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - /* check the call stack */ if ( exc->callTop >= exc->callSize ) { @@ -4086,15 +3744,6 @@ if ( !def->active ) goto Fail; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY && - exc->ignore_x_mode && - ( def->sph_fdef_flags & SPH_FDEF_VACUFORM_ROUND_1 ) ) - goto Fail; - else - exc->sph_in_func_flags = def->sph_fdef_flags; -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - /* check stack */ if ( exc->callTop >= exc->callSize ) { @@ -4144,7 +3793,7 @@ /* we enable IDEF only in `prep' or `fpgm' */ - if ( exc->curRange == tt_coderange_glyph ) + if ( exc->iniRange == tt_coderange_glyph ) { exc->error = FT_THROW( DEF_In_Glyf_Bytecode ); return; @@ -4373,7 +4022,7 @@ if ( ( opcode & 1 ) != 0 ) { - C = B; /* counter clockwise rotation */ + C = B; /* counter-clockwise rotation */ B = A; A = NEG_LONG( C ); } @@ -5000,14 +4649,6 @@ } } -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - /* Disable Type 2 Vacuform Rounds - e.g. Arial Narrow */ - if ( SUBPIXEL_HINTING_INFINALITY && - exc->ignore_x_mode && - FT_ABS( D ) == 64 ) - D += 1; -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - args[0] = D; } @@ -5061,7 +4702,7 @@ if ( ( opcode & 1 ) != 0 ) { - C = B; /* counter clockwise rotation */ + C = B; /* counter-clockwise rotation */ B = A; A = NEG_LONG( C ); } @@ -5085,7 +4726,7 @@ if ( ( opcode & 1 ) != 0 ) { - C = B; /* counter clockwise rotation */ + C = B; /* counter-clockwise rotation */ B = A; A = NEG_LONG( C ); } @@ -5259,18 +4900,16 @@ } } - exc->GS.instruct_control &= ~(FT_Byte)Kf; - exc->GS.instruct_control |= (FT_Byte)L; - - if ( K == 3 ) + /* INSTCTRL should only be used in the CVT program */ + if ( exc->iniRange == tt_coderange_cvt ) { -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - /* INSTCTRL modifying flag 3 also has an effect */ - /* outside of the CVT program */ - if ( SUBPIXEL_HINTING_INFINALITY ) - exc->ignore_x_mode = FT_BOOL( L == 4 ); -#endif + exc->GS.instruct_control &= ~(FT_Byte)Kf; + exc->GS.instruct_control |= (FT_Byte)L; + } + /* except to change the subpixel flags temporarily */ + else if ( exc->iniRange == tt_coderange_glyph && K == 3 ) + { #ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL /* Native ClearType fonts sign a waiver that turns off all backward */ /* compatibility hacks and lets them program points to the grid like */ @@ -5279,6 +4918,8 @@ exc->backward_compatibility = !FT_BOOL( L == 4 ); #endif } + else if ( exc->pedantic_hinting ) + exc->error = FT_THROW( Invalid_Reference ); } @@ -5600,12 +5241,6 @@ } } else -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - /* doesn't follow Cleartype spec but produces better result */ - if ( SUBPIXEL_HINTING_INFINALITY && exc->ignore_x_mode ) - Move_Zp2_Point( exc, point, 0, dy, TRUE ); - else -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ Move_Zp2_Point( exc, point, dx, dy, TRUE ); exc->GS.loop--; @@ -5733,9 +5368,6 @@ { FT_F26Dot6 dx, dy; FT_UShort point; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - FT_Int B1, B2; -#endif #ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL FT_Bool in_twilight = FT_BOOL( exc->GS.gep0 == 0 || exc->GS.gep1 == 0 || @@ -5769,87 +5401,6 @@ } } else -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY ) - { - /* If not using ignore_x_mode rendering, allow ZP2 move. */ - /* If inline deltas aren't allowed, skip ZP2 move. */ - /* If using ignore_x_mode rendering, allow ZP2 point move if: */ - /* - freedom vector is y and sph_compatibility_mode is off */ - /* - the glyph is composite and the move is in the Y direction */ - /* - the glyph is specifically set to allow SHPIX moves */ - /* - the move is on a previously Y-touched point */ - - if ( exc->ignore_x_mode ) - { - /* save point for later comparison */ - if ( exc->GS.freeVector.y != 0 ) - B1 = exc->zp2.cur[point].y; - else - B1 = exc->zp2.cur[point].x; - - if ( !exc->face->sph_compatibility_mode && - exc->GS.freeVector.y != 0 ) - { - Move_Zp2_Point( exc, point, dx, dy, TRUE ); - - /* save new point */ - if ( exc->GS.freeVector.y != 0 ) - { - B2 = exc->zp2.cur[point].y; - - /* reverse any disallowed moves */ - if ( ( exc->sph_tweak_flags & SPH_TWEAK_SKIP_NONPIXEL_Y_MOVES ) && - ( B1 & 63 ) != 0 && - ( B2 & 63 ) != 0 && - B1 != B2 ) - Move_Zp2_Point( exc, - point, - NEG_LONG( dx ), - NEG_LONG( dy ), - TRUE ); - } - } - else if ( exc->face->sph_compatibility_mode ) - { - if ( exc->sph_tweak_flags & SPH_TWEAK_ROUND_NONPIXEL_Y_MOVES ) - { - dx = FT_PIX_ROUND( B1 + dx ) - B1; - dy = FT_PIX_ROUND( B1 + dy ) - B1; - } - - /* skip post-iup deltas */ - if ( exc->iup_called && - ( ( exc->sph_in_func_flags & SPH_FDEF_INLINE_DELTA_1 ) || - ( exc->sph_in_func_flags & SPH_FDEF_INLINE_DELTA_2 ) ) ) - goto Skip; - - if ( !( exc->sph_tweak_flags & SPH_TWEAK_ALWAYS_SKIP_DELTAP ) && - ( ( exc->is_composite && exc->GS.freeVector.y != 0 ) || - ( exc->zp2.tags[point] & FT_CURVE_TAG_TOUCH_Y ) || - ( exc->sph_tweak_flags & SPH_TWEAK_DO_SHPIX ) ) ) - Move_Zp2_Point( exc, point, 0, dy, TRUE ); - - /* save new point */ - if ( exc->GS.freeVector.y != 0 ) - { - B2 = exc->zp2.cur[point].y; - - /* reverse any disallowed moves */ - if ( ( B1 & 63 ) == 0 && - ( B2 & 63 ) != 0 && - B1 != B2 ) - Move_Zp2_Point( exc, point, 0, NEG_LONG( dy ), TRUE ); - } - } - else if ( exc->sph_in_func_flags & SPH_FDEF_TYPEMAN_DIAGENDCTRL ) - Move_Zp2_Point( exc, point, dx, dy, TRUE ); - } - else - Move_Zp2_Point( exc, point, dx, dy, TRUE ); - } - else -#endif #ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL if ( SUBPIXEL_HINTING_MINIMAL && exc->backward_compatibility ) @@ -5869,9 +5420,6 @@ #endif Move_Zp2_Point( exc, point, dx, dy, TRUE ); -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - Skip: -#endif exc->GS.loop--; } @@ -5893,22 +5441,8 @@ { FT_UShort point = 0; FT_F26Dot6 distance; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - FT_F26Dot6 control_value_cutin = 0; - FT_F26Dot6 delta; - if ( SUBPIXEL_HINTING_INFINALITY ) - { - control_value_cutin = exc->GS.control_value_cutin; - - if ( exc->ignore_x_mode && - exc->GS.freeVector.x != 0 && - !( exc->sph_tweak_flags & SPH_TWEAK_NORMAL_ROUND ) ) - control_value_cutin = 0; - } -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - point = (FT_UShort)args[0]; if ( BOUNDS( point, exc->zp1.n_points ) || @@ -5930,19 +5464,6 @@ distance = PROJECT( exc->zp1.cur + point, exc->zp0.cur + exc->GS.rp0 ); -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - delta = SUB_LONG( distance, args[1] ); - if ( delta < 0 ) - delta = NEG_LONG( delta ); - - /* subpixel hinting - make MSIRP respect CVT cut-in; */ - if ( SUBPIXEL_HINTING_INFINALITY && - exc->ignore_x_mode && - exc->GS.freeVector.x != 0 && - delta >= control_value_cutin ) - distance = args[1]; -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - exc->func_move( exc, &exc->zp1, point, @@ -5983,22 +5504,7 @@ if ( ( exc->opcode & 1 ) != 0 ) { cur_dist = FAST_PROJECT( &exc->zp0.cur[point] ); -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY && - exc->ignore_x_mode && - exc->GS.freeVector.x != 0 ) - distance = SUB_LONG( - Round_None( exc, - cur_dist, - exc->tt_metrics.compensations[0] ), - cur_dist ); - else -#endif - distance = SUB_LONG( - exc->func_round( exc, - cur_dist, - exc->tt_metrics.compensations[0] ), - cur_dist ); + distance = SUB_LONG( exc->func_round( exc, cur_dist, 3 ), cur_dist ); } else distance = 0; @@ -6024,21 +5530,10 @@ FT_UShort point; FT_F26Dot6 distance; FT_F26Dot6 org_dist; - FT_F26Dot6 control_value_cutin; - - control_value_cutin = exc->GS.control_value_cutin; - cvtEntry = (FT_ULong)args[1]; - point = (FT_UShort)args[0]; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY && - exc->ignore_x_mode && - exc->GS.freeVector.x != 0 && - exc->GS.freeVector.y == 0 && - !( exc->sph_tweak_flags & SPH_TWEAK_NORMAL_ROUND ) ) - control_value_cutin = 0; -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ + cvtEntry = (FT_ULong)args[1]; + point = (FT_UShort)args[0]; if ( BOUNDS( point, exc->zp0.n_points ) || BOUNDSL( cvtEntry, exc->cvtSize ) ) @@ -6072,32 +5567,18 @@ if ( exc->GS.gep0 == 0 ) /* If in twilight zone */ { -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - /* Only adjust if not in sph_compatibility_mode or ignore_x_mode. */ - /* Determined via experimentation and may be incorrect... */ - if ( !( SUBPIXEL_HINTING_INFINALITY && - ( exc->ignore_x_mode && - exc->face->sph_compatibility_mode ) ) ) -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - exc->zp0.org[point].x = TT_MulFix14( distance, + exc->zp0.org[point].x = TT_MulFix14( distance, exc->GS.freeVector.x ); exc->zp0.org[point].y = TT_MulFix14( distance, - exc->GS.freeVector.y ), + exc->GS.freeVector.y ); exc->zp0.cur[point] = exc->zp0.org[point]; } -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY && - exc->ignore_x_mode && - ( exc->sph_tweak_flags & SPH_TWEAK_MIAP_HACK ) && - distance > 0 && - exc->GS.freeVector.y != 0 ) - distance = 0; -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ org_dist = FAST_PROJECT( &exc->zp0.cur[point] ); if ( ( exc->opcode & 1 ) != 0 ) /* rounding and control cut-in flag */ { + FT_F26Dot6 control_value_cutin = exc->GS.control_value_cutin; FT_F26Dot6 delta; @@ -6108,18 +5589,7 @@ if ( delta > control_value_cutin ) distance = org_dist; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY && - exc->ignore_x_mode && - exc->GS.freeVector.x != 0 ) - distance = Round_None( exc, - distance, - exc->tt_metrics.compensations[0] ); - else -#endif - distance = exc->func_round( exc, - distance, - exc->tt_metrics.compensations[0] ); + distance = exc->func_round( exc, distance, 3 ); } exc->func_move( exc, &exc->zp0, point, SUB_LONG( distance, org_dist ) ); @@ -6141,18 +5611,8 @@ FT_Long* args ) { FT_UShort point = 0; - FT_F26Dot6 org_dist, distance, minimum_distance; - + FT_F26Dot6 org_dist, distance; - minimum_distance = exc->GS.minimum_distance; - -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY && - exc->ignore_x_mode && - exc->GS.freeVector.x != 0 && - !( exc->sph_tweak_flags & SPH_TWEAK_NORMAL_ROUND ) ) - minimum_distance = 0; -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ point = (FT_UShort)args[0]; @@ -6222,31 +5682,18 @@ if ( ( exc->opcode & 4 ) != 0 ) { -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY && - exc->ignore_x_mode && - exc->GS.freeVector.x != 0 ) - distance = Round_None( - exc, - org_dist, - exc->tt_metrics.compensations[exc->opcode & 3] ); - else -#endif - distance = exc->func_round( - exc, - org_dist, - exc->tt_metrics.compensations[exc->opcode & 3] ); + distance = exc->func_round( exc, org_dist, exc->opcode & 3 ); } else - distance = Round_None( - exc, - org_dist, - exc->tt_metrics.compensations[exc->opcode & 3] ); + distance = Round_None( exc, org_dist, exc->opcode & 3 ); /* minimum distance flag */ if ( ( exc->opcode & 8 ) != 0 ) { + FT_F26Dot6 minimum_distance = exc->GS.minimum_distance; + + if ( org_dist >= 0 ) { if ( distance < minimum_distance ) @@ -6290,30 +5737,13 @@ FT_F26Dot6 cvt_dist, distance, cur_dist, - org_dist, - control_value_cutin, - minimum_distance; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - FT_Int B1 = 0; /* pacify compiler */ - FT_Int B2 = 0; - FT_Bool reverse_move = FALSE; -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ + org_dist; FT_F26Dot6 delta; - minimum_distance = exc->GS.minimum_distance; - control_value_cutin = exc->GS.control_value_cutin; - point = (FT_UShort)args[0]; - cvtEntry = (FT_ULong)( ADD_LONG( args[1], 1 ) ); - -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY && - exc->ignore_x_mode && - exc->GS.freeVector.x != 0 && - !( exc->sph_tweak_flags & SPH_TWEAK_NORMAL_ROUND ) ) - control_value_cutin = minimum_distance = 0; -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ + point = (FT_UShort)args[0]; + cvtEntry = (FT_ULong)( ADD_LONG( args[1], 1 ) ); /* XXX: UNDOCUMENTED! cvt[-1] = 0 always */ @@ -6371,19 +5801,6 @@ cvt_dist = NEG_LONG( cvt_dist ); } -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY && - exc->ignore_x_mode && - exc->GS.freeVector.y != 0 && - ( exc->sph_tweak_flags & SPH_TWEAK_TIMES_NEW_ROMAN_HACK ) ) - { - if ( cur_dist < -64 ) - cvt_dist -= 16; - else if ( cur_dist > 64 && cur_dist < 84 ) - cvt_dist += 32; - } -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - /* control value cut-in and round */ if ( ( exc->opcode & 4 ) != 0 ) @@ -6393,6 +5810,9 @@ if ( exc->GS.gep0 == exc->GS.gep1 ) { + FT_F26Dot6 control_value_cutin = exc->GS.control_value_cutin; + + /* XXX: According to Greg Hitchcock, the following wording is */ /* the right one: */ /* */ @@ -6413,39 +5833,18 @@ cvt_dist = org_dist; } - distance = exc->func_round( - exc, - cvt_dist, - exc->tt_metrics.compensations[exc->opcode & 3] ); + distance = exc->func_round( exc, cvt_dist, exc->opcode & 3 ); } else - { - -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - /* do cvt cut-in always in MIRP for sph */ - if ( SUBPIXEL_HINTING_INFINALITY && - exc->ignore_x_mode && - exc->GS.gep0 == exc->GS.gep1 ) - { - delta = SUB_LONG( cvt_dist, org_dist ); - if ( delta < 0 ) - delta = NEG_LONG( delta ); - - if ( delta > control_value_cutin ) - cvt_dist = org_dist; - } -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - - distance = Round_None( - exc, - cvt_dist, - exc->tt_metrics.compensations[exc->opcode & 3] ); - } + distance = Round_None( exc, cvt_dist, exc->opcode & 3 ); /* minimum distance test */ if ( ( exc->opcode & 8 ) != 0 ) { + FT_F26Dot6 minimum_distance = exc->GS.minimum_distance; + + if ( org_dist >= 0 ) { if ( distance < minimum_distance ) @@ -6458,61 +5857,11 @@ } } -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY ) - { - B1 = exc->zp1.cur[point].y; - - /* Round moves if necessary */ - if ( exc->ignore_x_mode && - exc->GS.freeVector.y != 0 && - ( exc->sph_tweak_flags & SPH_TWEAK_ROUND_NONPIXEL_Y_MOVES ) ) - distance = FT_PIX_ROUND( B1 + distance - cur_dist ) - B1 + cur_dist; - - if ( exc->ignore_x_mode && - exc->GS.freeVector.y != 0 && - ( exc->opcode & 16 ) == 0 && - ( exc->opcode & 8 ) == 0 && - ( exc->sph_tweak_flags & SPH_TWEAK_COURIER_NEW_2_HACK ) ) - distance += 64; - } -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - exc->func_move( exc, &exc->zp1, point, SUB_LONG( distance, cur_dist ) ); -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY ) - { - B2 = exc->zp1.cur[point].y; - - /* Reverse move if necessary */ - if ( exc->ignore_x_mode ) - { - if ( exc->face->sph_compatibility_mode && - exc->GS.freeVector.y != 0 && - ( B1 & 63 ) == 0 && - ( B2 & 63 ) != 0 ) - reverse_move = TRUE; - - if ( ( exc->sph_tweak_flags & SPH_TWEAK_SKIP_NONPIXEL_Y_MOVES ) && - exc->GS.freeVector.y != 0 && - ( B2 & 63 ) != 0 && - ( B1 & 63 ) != 0 ) - reverse_move = TRUE; - } - - if ( reverse_move ) - exc->func_move( exc, - &exc->zp1, - point, - SUB_LONG( cur_dist, distance ) ); - } - -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - Fail: exc->GS.rp1 = exc->GS.rp0; @@ -6536,17 +5885,6 @@ FT_F26Dot6 distance; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY && - exc->ignore_x_mode && - exc->iup_called && - ( exc->sph_tweak_flags & SPH_TWEAK_NO_ALIGNRP_AFTER_IUP ) ) - { - exc->error = FT_THROW( Invalid_Reference ); - goto Fail; - } -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - if ( exc->top < exc->GS.loop || BOUNDS( exc->GS.rp0, exc->zp0.n_points ) ) { @@ -6921,7 +6259,7 @@ static void - _iup_worker_shift( IUP_Worker worker, + iup_worker_shift_( IUP_Worker worker, FT_UInt p1, FT_UInt p2, FT_UInt p ) @@ -6943,7 +6281,7 @@ static void - _iup_worker_interpolate( IUP_Worker worker, + iup_worker_interpolate_( IUP_Worker worker, FT_UInt p1, FT_UInt p2, FT_UInt ref1, @@ -7105,16 +6443,6 @@ contour = 0; point = 0; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY && - exc->ignore_x_mode ) - { - exc->iup_called = TRUE; - if ( exc->sph_tweak_flags & SPH_TWEAK_SKIP_IUP ) - return; - } -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - do { end_point = exc->pts.contours[contour] - exc->pts.first_point; @@ -7137,7 +6465,7 @@ { if ( ( exc->pts.tags[point] & mask ) != 0 ) { - _iup_worker_interpolate( &V, + iup_worker_interpolate_( &V, cur_touched + 1, point - 1, cur_touched, @@ -7149,17 +6477,17 @@ } if ( cur_touched == first_touched ) - _iup_worker_shift( &V, first_point, end_point, cur_touched ); + iup_worker_shift_( &V, first_point, end_point, cur_touched ); else { - _iup_worker_interpolate( &V, + iup_worker_interpolate_( &V, (FT_UShort)( cur_touched + 1 ), end_point, cur_touched, first_touched ); if ( first_touched > 0 ) - _iup_worker_interpolate( &V, + iup_worker_interpolate_( &V, first_point, first_touched - 1, cur_touched, @@ -7185,16 +6513,7 @@ FT_UShort A; FT_ULong C, P; FT_Long B; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - FT_UShort B1, B2; - - if ( SUBPIXEL_HINTING_INFINALITY && - exc->ignore_x_mode && - exc->iup_called && - ( exc->sph_tweak_flags & SPH_TWEAK_NO_DELTAP_AFTER_IUP ) ) - goto Fail; -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ P = (FT_ULong)exc->func_cur_ppem( exc ); nump = (FT_ULong)args[0]; /* some points theoretically may occur more @@ -7248,84 +6567,21 @@ B++; B *= 1L << ( 6 - exc->GS.delta_shift ); -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - if ( SUBPIXEL_HINTING_INFINALITY ) +#ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL + /* See `ttinterp.h' for details on backward compatibility */ + /* mode. */ + if ( SUBPIXEL_HINTING_MINIMAL && + exc->backward_compatibility ) { - /* - * Allow delta move if - * - * - not using ignore_x_mode rendering, - * - glyph is specifically set to allow it, or - * - glyph is composite and freedom vector is not in subpixel - * direction. - */ - if ( !exc->ignore_x_mode || - ( exc->sph_tweak_flags & SPH_TWEAK_ALWAYS_DO_DELTAP ) || - ( exc->is_composite && exc->GS.freeVector.y != 0 ) ) + if ( !( exc->iupx_called && exc->iupy_called ) && + ( ( exc->is_composite && exc->GS.freeVector.y != 0 ) || + ( exc->zp0.tags[A] & FT_CURVE_TAG_TOUCH_Y ) ) ) exc->func_move( exc, &exc->zp0, A, B ); - - /* Otherwise, apply subpixel hinting and compatibility mode */ - /* rules, always skipping deltas in subpixel direction. */ - else if ( exc->ignore_x_mode && exc->GS.freeVector.y != 0 ) - { - /* save the y value of the point now; compare after move */ - B1 = (FT_UShort)exc->zp0.cur[A].y; - - /* Standard subpixel hinting: Allow y move for y-touched */ - /* points. This messes up DejaVu ... */ - if ( !exc->face->sph_compatibility_mode && - ( exc->zp0.tags[A] & FT_CURVE_TAG_TOUCH_Y ) ) - exc->func_move( exc, &exc->zp0, A, B ); - - /* compatibility mode */ - else if ( exc->face->sph_compatibility_mode && - !( exc->sph_tweak_flags & SPH_TWEAK_ALWAYS_SKIP_DELTAP ) ) - { - if ( exc->sph_tweak_flags & SPH_TWEAK_ROUND_NONPIXEL_Y_MOVES ) - B = FT_PIX_ROUND( B1 + B ) - B1; - - /* Allow delta move if using sph_compatibility_mode, */ - /* IUP has not been called, and point is touched on Y. */ - if ( !exc->iup_called && - ( exc->zp0.tags[A] & FT_CURVE_TAG_TOUCH_Y ) ) - exc->func_move( exc, &exc->zp0, A, B ); - } - - B2 = (FT_UShort)exc->zp0.cur[A].y; - - /* Reverse this move if it results in a disallowed move */ - if ( exc->GS.freeVector.y != 0 && - ( ( exc->face->sph_compatibility_mode && - ( B1 & 63 ) == 0 && - ( B2 & 63 ) != 0 ) || - ( ( exc->sph_tweak_flags & - SPH_TWEAK_SKIP_NONPIXEL_Y_MOVES_DELTAP ) && - ( B1 & 63 ) != 0 && - ( B2 & 63 ) != 0 ) ) ) - exc->func_move( exc, &exc->zp0, A, NEG_LONG( B ) ); - } } else -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - - { - -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL - /* See `ttinterp.h' for details on backward compatibility */ - /* mode. */ - if ( SUBPIXEL_HINTING_MINIMAL && - exc->backward_compatibility ) - { - if ( !( exc->iupx_called && exc->iupy_called ) && - ( ( exc->is_composite && exc->GS.freeVector.y != 0 ) || - ( exc->zp0.tags[A] & FT_CURVE_TAG_TOUCH_Y ) ) ) - exc->func_move( exc, &exc->zp0, A, B ); - } - else #endif - exc->func_move( exc, &exc->zp0, A, B ); - } + exc->func_move( exc, &exc->zp0, A, B ); } } else @@ -7428,14 +6684,6 @@ * GETINFO[]: GET INFOrmation * Opcode range: 0x88 * Stack: uint32 --> uint32 - * - * XXX: UNDOCUMENTED: Selector bits higher than 9 are currently (May - * 2015) not documented in the OpenType specification. - * - * Selector bit 11 is incorrectly described as bit 8, while the - * real meaning of bit 8 (vertical LCD subpixels) stays - * undocumented. The same mistake can be found in Greg Hitchcock's - * whitepaper. */ static void Ins_GETINFO( TT_ExecContext exc, @@ -7447,31 +6695,8 @@ K = 0; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - /********************************* - * RASTERIZER VERSION - * Selector Bit: 0 - * Return Bit(s): 0-7 - */ - if ( SUBPIXEL_HINTING_INFINALITY && - ( args[0] & 1 ) != 0 && - exc->subpixel_hinting ) - { - if ( exc->ignore_x_mode ) - { - /* if in ClearType backward compatibility mode, */ - /* we sometimes change the TrueType version dynamically */ - K = exc->rasterizer_version; - FT_TRACE6(( "Setting rasterizer version %d\n", - exc->rasterizer_version )); - } - else - K = TT_INTERPRETER_VERSION_38; - } - else -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - if ( ( args[0] & 1 ) != 0 ) - K = driver->interpreter_version; + if ( ( args[0] & 1 ) != 0 ) + K = driver->interpreter_version; /********************************* * GLYPH ROTATED @@ -7494,8 +6719,6 @@ * VARIATION GLYPH * Selector Bit: 3 * Return Bit(s): 10 - * - * XXX: UNDOCUMENTED! */ if ( (args[0] & 8 ) != 0 && exc->face->blend ) K |= 1 << 10; @@ -7570,89 +6793,6 @@ } #endif -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - - if ( SUBPIXEL_HINTING_INFINALITY && - exc->rasterizer_version >= TT_INTERPRETER_VERSION_35 ) - { - - if ( exc->rasterizer_version >= 37 ) - { - /********************************* - * HINTING FOR SUBPIXEL - * Selector Bit: 6 - * Return Bit(s): 13 - */ - if ( ( args[0] & 64 ) != 0 && exc->subpixel_hinting ) - K |= 1 << 13; - - /********************************* - * COMPATIBLE WIDTHS ENABLED - * Selector Bit: 7 - * Return Bit(s): 14 - * - * Functionality still needs to be added - */ - if ( ( args[0] & 128 ) != 0 && exc->compatible_widths ) - K |= 1 << 14; - - /********************************* - * VERTICAL LCD SUBPIXELS? - * Selector Bit: 8 - * Return Bit(s): 15 - * - * Functionality still needs to be added - */ - if ( ( args[0] & 256 ) != 0 && exc->vertical_lcd ) - K |= 1 << 15; - - /********************************* - * HINTING FOR BGR? - * Selector Bit: 9 - * Return Bit(s): 16 - * - * Functionality still needs to be added - */ - if ( ( args[0] & 512 ) != 0 && exc->bgr ) - K |= 1 << 16; - - if ( exc->rasterizer_version >= 38 ) - { - /********************************* - * SUBPIXEL POSITIONED? - * Selector Bit: 10 - * Return Bit(s): 17 - * - * Functionality still needs to be added - */ - if ( ( args[0] & 1024 ) != 0 && exc->subpixel_positioned ) - K |= 1 << 17; - - /********************************* - * SYMMETRICAL SMOOTHING - * Selector Bit: 11 - * Return Bit(s): 18 - * - * Functionality still needs to be added - */ - if ( ( args[0] & 2048 ) != 0 && exc->symmetrical_smoothing ) - K |= 1 << 18; - - /********************************* - * GRAY CLEARTYPE - * Selector Bit: 12 - * Return Bit(s): 19 - * - * Functionality still needs to be added - */ - if ( ( args[0] & 4096 ) != 0 && exc->gray_cleartype ) - K |= 1 << 19; - } - } - } - -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - args[0] = K; } @@ -7787,54 +6927,14 @@ /* documentation is in ttinterp.h */ FT_EXPORT_DEF( FT_Error ) - TT_RunIns( TT_ExecContext exc ) + TT_RunIns( void* exec ) { + TT_ExecContext exc = (TT_ExecContext)exec; + FT_ULong ins_counter = 0; /* executed instructions counter */ FT_ULong num_twilight_points; FT_UShort i; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - FT_Byte opcode_pattern[1][2] = { - /* #8 TypeMan Talk Align */ - { - 0x06, /* SPVTL */ - 0x7D, /* RDTG */ - }, - }; - FT_UShort opcode_patterns = 1; - FT_UShort opcode_pointer[1] = { 0 }; - FT_UShort opcode_size[1] = { 1 }; -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - - -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - exc->iup_called = FALSE; -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL - /* - * Toggle backward compatibility according to what font wants, except - * when - * - * 1) we have a `tricky' font that heavily relies on the interpreter to - * render glyphs correctly, for example DFKai-SB, or - * 2) FT_RENDER_MODE_MONO (i.e, monochome rendering) is requested. - * - * In those cases, backward compatibility needs to be turned off to get - * correct rendering. The rendering is then completely up to the - * font's programming. - * - */ - if ( SUBPIXEL_HINTING_MINIMAL && - exc->subpixel_hinting_lean && - !FT_IS_TRICKY( &exc->face->root ) ) - exc->backward_compatibility = !( exc->GS.instruct_control & 4 ); - else - exc->backward_compatibility = FALSE; - - exc->iupx_called = FALSE; - exc->iupy_called = FALSE; -#endif /* We restrict the number of twilight points to a reasonable, */ /* heuristic value to avoid slow execution of malformed bytecode. */ @@ -7845,8 +6945,8 @@ if ( num_twilight_points > 0xFFFFU ) num_twilight_points = 0xFFFFU; - FT_TRACE5(( "TT_RunIns: Resetting number of twilight points\n" - " from %d to the more reasonable value %d\n", + FT_TRACE5(( "TT_RunIns: Resetting number of twilight points\n" )); + FT_TRACE5(( " from %d to the more reasonable value %ld\n", exc->twilight.n_points, num_twilight_points )); exc->twilight.n_points = (FT_UShort)num_twilight_points; @@ -7881,11 +6981,11 @@ exc->loopcall_counter_max = 100 * (FT_ULong)exc->face->root.num_glyphs; FT_TRACE5(( "TT_RunIns: Limiting total number of loops in LOOPCALL" - " to %d\n", exc->loopcall_counter_max )); + " to %ld\n", exc->loopcall_counter_max )); exc->neg_jump_counter_max = exc->loopcall_counter_max; FT_TRACE5(( "TT_RunIns: Limiting total number of backward jumps" - " to %d\n", exc->neg_jump_counter_max )); + " to %ld\n", exc->neg_jump_counter_max )); /* set PPEM and CVT functions */ exc->tt_metrics.ratio = 0; @@ -7906,14 +7006,23 @@ exc->func_move_cvt = Move_CVT; } + exc->iniRange = exc->curRange; + Compute_Funcs( exc ); Compute_Round( exc, (FT_Byte)exc->GS.round_state ); + /* These flags cancel execution of some opcodes after IUP is called */ +#ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL + exc->iupx_called = FALSE; + exc->iupy_called = FALSE; +#endif + do { exc->opcode = exc->code[exc->IP]; #ifdef FT_DEBUG_LEVEL_TRACE + if ( ft_trace_levels[trace_ttinterp] >= 6 ) { FT_Long cnt = FT_MIN( 8, exc->top ); FT_Long n; @@ -7922,14 +7031,14 @@ /* if tracing level is 7, show current code position */ /* and the first few stack elements also */ FT_TRACE6(( " " )); - FT_TRACE7(( "%06d ", exc->IP )); + FT_TRACE7(( "%06ld ", exc->IP )); FT_TRACE6(( "%s", opcode_name[exc->opcode] + 2 )); FT_TRACE7(( "%*s", *opcode_name[exc->opcode] == 'A' ? 2 : 12 - ( *opcode_name[exc->opcode] - '0' ), "#" )); for ( n = 1; n <= cnt; n++ ) - FT_TRACE7(( " %d", exc->stack[exc->top - n] )); + FT_TRACE7(( " %ld", exc->stack[exc->top - n] )); FT_TRACE6(( "\n" )); } #endif /* FT_DEBUG_LEVEL_TRACE */ @@ -7971,7 +7080,7 @@ /* a variable number of arguments */ /* it is the job of the application to `activate' GX handling, */ - /* this is, calling any of the GX API functions on the current */ + /* that is, calling any of the GX API functions on the current */ /* font to select a variation instance */ if ( exc->face->blend ) exc->new_top = exc->args + exc->face->blend->num_axis; @@ -7992,39 +7101,6 @@ exc->step_ins = TRUE; exc->error = FT_Err_Ok; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - - if ( SUBPIXEL_HINTING_INFINALITY ) - { - for ( i = 0; i < opcode_patterns; i++ ) - { - if ( opcode_pointer[i] < opcode_size[i] && - exc->opcode == opcode_pattern[i][opcode_pointer[i]] ) - { - opcode_pointer[i] += 1; - - if ( opcode_pointer[i] == opcode_size[i] ) - { - FT_TRACE6(( "sph: opcode ptrn: %d, %s %s\n", - i, - exc->face->root.family_name, - exc->face->root.style_name )); - - switch ( i ) - { - case 0: - break; - } - opcode_pointer[i] = 0; - } - } - else - opcode_pointer[i] = 0; - } - } - -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - { FT_Long* args = exc->stack + exc->args; FT_Byte opcode = exc->opcode; @@ -8531,7 +7607,7 @@ #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT case 0x91: /* it is the job of the application to `activate' GX handling, */ - /* this is, calling any of the GX API functions on the current */ + /* that is, calling any of the GX API functions on the current */ /* font to select a variation instance */ if ( exc->face->blend ) Ins_GETVARIATION( exc, args ); @@ -8631,7 +7707,10 @@ /* increment instruction counter and check if we didn't */ /* run this program for too long (e.g. infinite loops). */ if ( ++ins_counter > TT_CONFIG_OPTION_MAX_RUNNABLE_OPCODES ) - return FT_THROW( Execution_Too_Long ); + { + exc->error = FT_THROW( Execution_Too_Long ); + goto LErrorLabel_; + } LSuiteLabel_: if ( exc->IP >= exc->codeSize ) @@ -8647,9 +7726,10 @@ } while ( !exc->instruction_trap ); LNo_Error_: - FT_TRACE4(( " %d instruction%s executed\n", + FT_TRACE4(( " %ld instruction%s executed\n", ins_counter, ins_counter == 1 ? "" : "s" )); + return FT_Err_Ok; LErrorCodeOverflow_: @@ -8665,7 +7745,7 @@ #else /* !TT_USE_BYTECODE_INTERPRETER */ /* ANSI C doesn't like empty source files */ - typedef int _tt_interp_dummy; + typedef int tt_interp_dummy_; #endif /* !TT_USE_BYTECODE_INTERPRETER */ diff --git a/src/font/freetype-2.10.2/src/truetype/ttinterp.h b/3rdparty/freetype-2.13.2/src/truetype/ttinterp.h similarity index 74% rename from src/font/freetype-2.10.2/src/truetype/ttinterp.h rename to 3rdparty/freetype-2.13.2/src/truetype/ttinterp.h index 07e4ad689..e98e258fe 100644 --- a/src/font/freetype-2.10.2/src/truetype/ttinterp.h +++ b/3rdparty/freetype-2.13.2/src/truetype/ttinterp.h @@ -4,7 +4,7 @@ * * TrueType bytecode interpreter (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -19,7 +19,6 @@ #ifndef TTINTERP_H_ #define TTINTERP_H_ -#include #include "ttobjs.h" @@ -52,7 +51,7 @@ FT_BEGIN_HEADER typedef FT_F26Dot6 (*TT_Round_Func)( TT_ExecContext exc, FT_F26Dot6 distance, - FT_F26Dot6 compensation ); + FT_Int color ); /* Point displacement along the freedom vector routine */ typedef void @@ -99,83 +98,45 @@ FT_BEGIN_HEADER } TT_CallRec, *TT_CallStack; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - - /************************************************************************** - * - * These structures define rules used to tweak subpixel hinting for - * various fonts. "", 0, "", NULL value indicates to match any value. - */ - -#define SPH_MAX_NAME_SIZE 32 -#define SPH_MAX_CLASS_MEMBERS 100 - - typedef struct SPH_TweakRule_ - { - const char family[SPH_MAX_NAME_SIZE]; - const FT_UInt ppem; - const char style[SPH_MAX_NAME_SIZE]; - const FT_ULong glyph; - - } SPH_TweakRule; - - - typedef struct SPH_ScaleRule_ - { - const char family[SPH_MAX_NAME_SIZE]; - const FT_UInt ppem; - const char style[SPH_MAX_NAME_SIZE]; - const FT_ULong glyph; - const FT_ULong scale; - - } SPH_ScaleRule; - - - typedef struct SPH_Font_Class_ - { - const char name[SPH_MAX_NAME_SIZE]; - const char member[SPH_MAX_CLASS_MEMBERS][SPH_MAX_NAME_SIZE]; - - } SPH_Font_Class; - -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - - /************************************************************************** * * The main structure for the interpreter which collects all necessary * variables and states. + * + * Members that are initialized by `TT_Load_Context` are marked with '!'. + * Members that are initialized by `TT_Run_Context` are marked with '@'. */ typedef struct TT_ExecContextRec_ { - TT_Face face; - TT_Size size; + TT_Face face; /* ! */ + TT_Size size; /* ! */ FT_Memory memory; /* instructions state */ FT_Error error; /* last execution error */ - FT_Long top; /* top of exec. stack */ + FT_Long top; /* @ top of exec. stack */ - FT_Long stackSize; /* size of exec. stack */ - FT_Long* stack; /* current exec. stack */ + FT_Long stackSize; /* ! size of exec. stack */ + FT_Long* stack; /* ! current exec. stack */ FT_Long args; - FT_Long new_top; /* new top after exec. */ + FT_Long new_top; /* new top after exec. */ - TT_GlyphZoneRec zp0, /* zone records */ - zp1, - zp2, - pts, - twilight; + TT_GlyphZoneRec zp0, /* @! zone records */ + zp1, /* @! */ + zp2, /* @! */ + pts, /* ! */ + twilight; /* ! */ - FT_Long pointSize; /* in 26.6 format */ - FT_Size_Metrics metrics; - TT_Size_Metrics tt_metrics; /* size metrics */ + FT_Long pointSize; /* ! in 26.6 format */ + FT_Size_Metrics metrics; /* ! */ + TT_Size_Metrics tt_metrics; /* ! size metrics */ - TT_GraphicsState GS; /* current graphics state */ + TT_GraphicsState GS; /* !@ current graphics state */ + FT_Int iniRange; /* initial code range number */ FT_Int curRange; /* current code range number */ FT_Byte* code; /* current code range */ FT_Long IP; /* current instruction pointer */ @@ -186,43 +147,47 @@ FT_BEGIN_HEADER FT_Bool step_ins; /* true if the interpreter must */ /* increment IP after ins. exec */ - FT_ULong cvtSize; - FT_Long* cvt; + FT_ULong cvtSize; /* ! */ + FT_Long* cvt; /* ! */ + FT_ULong glyfCvtSize; + FT_Long* glyfCvt; /* cvt working copy for glyph */ - FT_UInt glyphSize; /* glyph instructions buffer size */ - FT_Byte* glyphIns; /* glyph instructions buffer */ + FT_UInt glyphSize; /* ! glyph instructions buffer size */ + FT_Byte* glyphIns; /* ! glyph instructions buffer */ - FT_UInt numFDefs; /* number of function defs */ - FT_UInt maxFDefs; /* maximum number of function defs */ - TT_DefArray FDefs; /* table of FDefs entries */ + FT_UInt numFDefs; /* ! number of function defs */ + FT_UInt maxFDefs; /* ! maximum number of function defs */ + TT_DefArray FDefs; /* table of FDefs entries */ - FT_UInt numIDefs; /* number of instruction defs */ - FT_UInt maxIDefs; /* maximum number of ins defs */ - TT_DefArray IDefs; /* table of IDefs entries */ + FT_UInt numIDefs; /* ! number of instruction defs */ + FT_UInt maxIDefs; /* ! maximum number of ins defs */ + TT_DefArray IDefs; /* table of IDefs entries */ - FT_UInt maxFunc; /* maximum function index */ - FT_UInt maxIns; /* maximum instruction index */ + FT_UInt maxFunc; /* ! maximum function index */ + FT_UInt maxIns; /* ! maximum instruction index */ - FT_Int callTop, /* top of call stack during execution */ - callSize; /* size of call stack */ - TT_CallStack callStack; /* call stack */ + FT_Int callTop, /* @ top of call stack during execution */ + callSize; /* size of call stack */ + TT_CallStack callStack; /* call stack */ FT_UShort maxPoints; /* capacity of this context's `pts' */ FT_Short maxContours; /* record, expressed in points and */ /* contours. */ - TT_CodeRangeTable codeRangeTable; /* table of valid code ranges */ - /* useful for the debugger */ + TT_CodeRangeTable codeRangeTable; /* ! table of valid code ranges */ + /* useful for the debugger */ - FT_UShort storeSize; /* size of current storage */ - FT_Long* storage; /* storage area */ + FT_UShort storeSize; /* ! size of current storage */ + FT_Long* storage; /* ! storage area */ + FT_UShort glyfStoreSize; + FT_Long* glyfStorage; /* storage working copy for glyph */ FT_F26Dot6 period; /* values used for the */ FT_F26Dot6 phase; /* `SuperRounding' */ FT_F26Dot6 threshold; - FT_Bool instruction_trap; /* If `True', the interpreter will */ - /* exit after each instruction */ + FT_Bool instruction_trap; /* ! If `True', the interpreter */ + /* exits after each instruction */ TT_GraphicsState default_GS; /* graphics state resulting from */ /* the prep program */ @@ -239,7 +204,7 @@ FT_BEGIN_HEADER func_dualproj, /* current dual proj. function */ func_freeProj; /* current freedom proj. func */ - TT_Move_Func func_move; /* current point move function */ + TT_Move_Func func_move; /* current point move function */ TT_Move_Func func_move_orig; /* move original position function */ TT_Cur_Ppem_Func func_cur_ppem; /* get current proj. ppem value */ @@ -392,38 +357,6 @@ FT_BEGIN_HEADER FT_Bool grayscale_cleartype; #endif /* TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL */ -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - TT_Round_Func func_round_sphn; /* subpixel rounding function */ - - FT_Bool subpixel_hinting; /* Using subpixel hinting? */ - FT_Bool ignore_x_mode; /* Standard rendering mode for */ - /* subpixel hinting. On if gray */ - /* or subpixel hinting is on. */ - - /* The following 6 aren't fully implemented but here for MS rasterizer */ - /* compatibility. */ - FT_Bool compatible_widths; /* compatible widths? */ - FT_Bool symmetrical_smoothing; /* symmetrical_smoothing? */ - FT_Bool bgr; /* bgr instead of rgb? */ - FT_Bool vertical_lcd; /* long side of LCD subpixel */ - /* rectangles is horizontal */ - FT_Bool subpixel_positioned; /* subpixel positioned */ - /* (DirectWrite ClearType)? */ - FT_Bool gray_cleartype; /* ClearType hinting but */ - /* grayscale rendering */ - - FT_Int rasterizer_version; /* MS rasterizer version */ - - FT_Bool iup_called; /* IUP called for glyph? */ - - FT_ULong sph_tweak_flags; /* flags to control */ - /* hint tweaks */ - - FT_ULong sph_in_func_flags; /* flags to indicate if in */ - /* special functions */ - -#endif /* TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY */ - /* We maintain two counters (in addition to the instruction counter) */ /* that act as loop detectors for LOOPCALL and jump opcodes with */ /* negative arguments. */ @@ -453,14 +386,6 @@ FT_BEGIN_HEADER FT_LOCAL( void ) TT_Clear_CodeRange( TT_ExecContext exec, FT_Int range ); - - - FT_LOCAL( FT_Error ) - Update_Max( FT_Memory memory, - FT_ULong* size, - FT_ULong multiplier, - void* _pbuff, - FT_ULong new_max ); #endif /* TT_USE_BYTECODE_INTERPRETER */ @@ -470,16 +395,15 @@ FT_BEGIN_HEADER * TT_New_Context * * @Description: - * Queries the face context for a given font. Note that there is - * now a _single_ execution context in the TrueType driver which is - * shared among faces. + * Create a `TT_ExecContext`. Note that there is now an execution + * context per `TT_Size` that is not shared among faces. * * @Input: - * face :: - * A handle to the source face object. + * driver :: + * A handle to the driver, used for memory allocation. * * @Return: - * A handle to the execution context. Initialized for `face'. + * A handle to a new empty execution context. * * @Note: * Only the glyph loader and debugger should call this function. @@ -530,7 +454,7 @@ FT_BEGIN_HEADER * invoked by the TrueType debugger. */ FT_EXPORT( FT_Error ) - TT_RunIns( TT_ExecContext exec ); + TT_RunIns( void* exec ); FT_END_HEADER diff --git a/src/font/freetype-2.10.2/src/truetype/ttobjs.c b/3rdparty/freetype-2.13.2/src/truetype/ttobjs.c similarity index 89% rename from src/font/freetype-2.10.2/src/truetype/ttobjs.c rename to 3rdparty/freetype-2.13.2/src/truetype/ttobjs.c index 730a5b8cd..5b56af711 100644 --- a/src/font/freetype-2.10.2/src/truetype/ttobjs.c +++ b/3rdparty/freetype-2.13.2/src/truetype/ttobjs.c @@ -4,7 +4,7 @@ * * Objects manager (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,12 +16,11 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_STREAM_H -#include FT_TRUETYPE_TAGS_H -#include FT_INTERNAL_SFNT_H -#include FT_DRIVER_H +#include +#include +#include +#include +#include #include "ttgload.h" #include "ttpload.h" @@ -141,7 +140,31 @@ return error; } -#endif /* TT_USE_BYTECODE_INTERPRETER */ + + + /* + * Fonts embedded in PDFs are made unique by prepending randomization + * prefixes to their names: as defined in Section 5.5.3, 'Font Subsets', + * of the PDF Reference, they consist of 6 uppercase letters followed by + * the `+` sign. For safety, we do not skip prefixes violating this rule. + */ + + static const FT_String* + tt_skip_pdffont_random_tag( const FT_String* name ) + { + unsigned int i; + + + if ( ft_strlen( name ) < 8 || name[6] != '+' ) + return name; + + for ( i = 0; i < 6; i++ ) + if ( !ft_isupper( name[i] ) ) + return name; + + FT_TRACE7(( "name without randomization tag: %s\n", name + 7 )); + return name + 7; + } /* Compare the face with a list of well-known `tricky' fonts. */ @@ -152,7 +175,7 @@ { #define TRICK_NAMES_MAX_CHARACTERS 19 -#define TRICK_NAMES_COUNT 26 +#define TRICK_NAMES_COUNT 20 static const char trick_names[TRICK_NAMES_COUNT] [TRICK_NAMES_MAX_CHARACTERS + 1] = @@ -172,22 +195,28 @@ "DFGirl-W6-WIN-BF", /* dftt-h6.ttf; version 1.00, 1993 */ "DFGothic-EB", /* DynaLab Inc. 1992-1995 */ "DFGyoSho-Lt", /* DynaLab Inc. 1992-1995 */ - "DFHei-Md-HK-BF", /* maybe DynaLab Inc. */ + "DFHei", /* DynaLab Inc. 1992-1995 [DFHei-Bd-WIN-HK-BF] */ + /* covers "DFHei-Md-HK-BF", maybe DynaLab Inc. */ + "DFHSGothic-W5", /* DynaLab Inc. 1992-1995 */ "DFHSMincho-W3", /* DynaLab Inc. 1992-1995 */ "DFHSMincho-W7", /* DynaLab Inc. 1992-1995 */ "DFKaiSho-SB", /* dfkaisb.ttf */ - "DFKaiShu", - "DFKaiShu-Md-HK-BF", /* maybe DynaLab Inc. */ + "DFKaiShu", /* covers "DFKaiShu-Md-HK-BF", maybe DynaLab Inc. */ "DFKai-SB", /* kaiu.ttf; version 3.00, 1998 [DFKaiShu-SB-Estd-BF] */ - "DFMing-Bd-HK-BF", /* maybe DynaLab Inc. */ + + "DFMing", /* DynaLab Inc. 1992-1995 [DFMing-Md-WIN-HK-BF] */ + /* covers "DFMing-Bd-HK-BF", maybe DynaLab Inc. */ + "DLC", /* dftt-m7.ttf; version 1.00, 1993 [DLCMingBold] */ /* dftt-f5.ttf; version 1.00, 1993 [DLCFongSung] */ - "DLCHayMedium", /* dftt-b5.ttf; version 1.00, 1993 */ - "DLCHayBold", /* dftt-b7.ttf; version 1.00, 1993 */ - "DLCKaiMedium", /* dftt-k5.ttf; version 1.00, 1992 */ - "DLCLiShu", /* dftt-l5.ttf; version 1.00, 1992 */ - "DLCRoundBold", /* dftt-r7.ttf; version 1.00, 1993 */ + /* covers following */ + /* "DLCHayMedium", dftt-b5.ttf; version 1.00, 1993 */ + /* "DLCHayBold", dftt-b7.ttf; version 1.00, 1993 */ + /* "DLCKaiMedium", dftt-k5.ttf; version 1.00, 1992 */ + /* "DLCLiShu", dftt-l5.ttf; version 1.00, 1992 */ + /* "DLCRoundBold", dftt-r7.ttf; version 1.00, 1993 */ + "HuaTianKaiTi?", /* htkt2.ttf */ "HuaTianSongTi?", /* htst3.ttf */ "Ming(for ISO10646)", /* hkscsiic.ttf; version 0.12, 2007 [Ming] */ @@ -200,10 +229,12 @@ }; int nn; + const FT_String* name_without_tag; + name_without_tag = tt_skip_pdffont_random_tag( name ); for ( nn = 0; nn < TRICK_NAMES_COUNT; nn++ ) - if ( ft_strstr( name, trick_names[nn] ) ) + if ( ft_strstr( name_without_tag, trick_names[nn] ) ) return TRUE; return FALSE; @@ -278,10 +309,11 @@ tt_check_trickyness_sfnt_ids( TT_Face face ) { #define TRICK_SFNT_IDS_PER_FACE 3 -#define TRICK_SFNT_IDS_NUM_FACES 29 +#define TRICK_SFNT_IDS_NUM_FACES 31 static const tt_sfnt_id_rec sfnt_id[TRICK_SFNT_IDS_NUM_FACES] - [TRICK_SFNT_IDS_PER_FACE] = { + [TRICK_SFNT_IDS_PER_FACE] = + { #define TRICK_SFNT_ID_cvt 0 #define TRICK_SFNT_ID_fpgm 1 @@ -431,6 +463,16 @@ { 0x00170003UL, 0x00000060UL }, /* cvt */ { 0xDBB4306EUL, 0x000058AAUL }, /* fpgm */ { 0xD643482AUL, 0x00000035UL } /* prep */ + }, + { /* DFHei-Bd-WIN-HK-BF, issue #1087 */ + { 0x1269EB58UL, 0x00000350UL }, /* cvt */ + { 0x5CD5957AUL, 0x00006A4EUL }, /* fpgm */ + { 0xF758323AUL, 0x00000380UL } /* prep */ + }, + { /* DFMing-Md-WIN-HK-BF, issue #1087 */ + { 0x122FEB0BUL, 0x00000350UL }, /* cvt */ + { 0x7F10919AUL, 0x000070A9UL }, /* fpgm */ + { 0x7CD7E7B7UL, 0x0000025CUL } /* prep */ } }; @@ -511,17 +553,27 @@ /* For first, check the face name for quick check. */ if ( face->family_name && tt_check_trickyness_family( face->family_name ) ) + { + FT_TRACE3(( "found as a tricky font" + " by its family name: %s\n", face->family_name )); return TRUE; + } /* Type42 fonts may lack `name' tables, we thus try to identify */ /* tricky fonts by checking the checksums of Type42-persistent */ /* sfnt tables (`cvt', `fpgm', and `prep'). */ if ( tt_check_trickyness_sfnt_ids( (TT_Face)face ) ) + { + FT_TRACE3(( "found as a tricky font" + " by its cvt/fpgm/prep table checksum\n" )); return TRUE; + } return FALSE; } +#endif /* TT_USE_BYTECODE_INTERPRETER */ + /* Check whether `.notdef' is the only glyph in the `loca' table. */ static FT_Bool @@ -530,7 +582,7 @@ FT_Bool result = FALSE; TT_Face face = (TT_Face)ttface; - FT_UInt asize; + FT_ULong asize; FT_ULong i; FT_ULong glyph_index = 0; FT_UInt count = 0; @@ -538,7 +590,7 @@ for( i = 0; i < face->num_locations; i++ ) { - tt_face_get_location( face, i, &asize ); + tt_face_get_location( ttface, i, &asize ); if ( asize > 0 ) { count += 1; @@ -667,14 +719,17 @@ if ( error ) goto Exit; +#ifdef TT_USE_BYTECODE_INTERPRETER if ( tt_check_trickyness( ttface ) ) ttface->face_flags |= FT_FACE_FLAG_TRICKY; +#endif error = tt_face_load_hdmx( face, stream ); if ( error ) goto Exit; - if ( FT_IS_SCALABLE( ttface ) ) + if ( FT_IS_SCALABLE( ttface ) || + FT_HAS_SBIX( ttface ) ) { #ifdef FT_CONFIG_OPTION_INCREMENTAL if ( !ttface->internal->incremental_interface ) @@ -713,8 +768,8 @@ tt_check_single_notdef( ttface ) ) { FT_TRACE5(( "tt_face_init:" - " Only the `.notdef' glyph has an outline.\n" - " " + " Only the `.notdef' glyph has an outline.\n" )); + FT_TRACE5(( " " " Resetting scalable flag to FALSE.\n" )); ttface->face_flags &= ~FT_FACE_FLAG_SCALABLE; @@ -723,7 +778,6 @@ } #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT - { FT_UInt instance_index = (FT_UInt)face_index >> 16; @@ -731,14 +785,11 @@ if ( FT_HAS_MULTIPLE_MASTERS( ttface ) && instance_index > 0 ) { - error = TT_Set_Named_Instance( face, instance_index ); + error = FT_Set_Named_Instance( ttface, instance_index ); if ( error ) goto Exit; - - tt_apply_mvar( face ); } } - #endif /* TT_CONFIG_OPTION_GX_VAR_SUPPORT */ /* initialize standard glyph loading routines */ @@ -804,7 +855,7 @@ face->cvt_program_size = 0; #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT - tt_done_blend( face ); + tt_done_blend( ttface ); face->blend = NULL; #endif } @@ -950,7 +1001,7 @@ { size->cvt[i] = FT_MulFix( face->cvt[i], scale ); FT_TRACE6(( " %3d: %f (%f)\n", - i, face->cvt[i] / 64.0, size->cvt[i] / 64.0 )); + i, (double)face->cvt[i] / 64, (double)size->cvt[i] / 64 )); } FT_TRACE6(( "\n" )); @@ -1116,10 +1167,10 @@ /* The Apple specification says that the compensation for */ /* `gray' is always zero. FreeType doesn't do any */ /* compensation at all. */ - tt_metrics->compensations[0] = 0; /* gray */ - tt_metrics->compensations[1] = 0; /* black */ - tt_metrics->compensations[2] = 0; /* white */ - tt_metrics->compensations[3] = 0; /* the same as gray */ + tt_metrics->compensations[0] = 0; /* gray */ + tt_metrics->compensations[1] = 0; /* black */ + tt_metrics->compensations[2] = 0; /* white */ + tt_metrics->compensations[3] = 0; /* zero */ } /* allocate function defs, instruction defs, cvt, and storage area */ @@ -1191,11 +1242,11 @@ /* rescale CVT when needed */ if ( size->cvt_ready < 0 ) { - FT_UInt i; + FT_UShort i; /* all twilight points are originally zero */ - for ( i = 0; i < (FT_UInt)size->twilight.n_points; i++ ) + for ( i = 0; i < size->twilight.n_points; i++ ) { size->twilight.org[i].x = 0; size->twilight.org[i].y = 0; @@ -1204,7 +1255,7 @@ } /* clear storage area */ - for ( i = 0; i < (FT_UInt)size->storage_size; i++ ) + for ( i = 0; i < size->storage_size; i++ ) size->storage[i] = 0; size->GS = tt_default_graphics_state; @@ -1284,39 +1335,29 @@ /************************************************************************** * * @Function: - * tt_size_reset + * tt_size_reset_height * * @Description: - * Reset a TrueType size when resolutions and character dimensions - * have been changed. + * Recompute a TrueType size's ascender, descender, and height + * when resolutions and character dimensions have been changed. + * Used for variation fonts as an iterator function. * * @Input: - * size :: - * A handle to the target size object. - * - * only_height :: - * Only recompute ascender, descender, and height; - * this flag is used for variation fonts where - * `tt_size_reset' is used as an iterator function. + * ft_size :: + * A handle to the target TT_Size object. This function will be called + * through a `FT_Size_Reset_Func` pointer which takes `FT_Size`. This + * function must take `FT_Size` as a result. The passed `FT_Size` is + * expected to point to a `TT_Size`. */ FT_LOCAL_DEF( FT_Error ) - tt_size_reset( TT_Size size, - FT_Bool only_height ) + tt_size_reset_height( FT_Size ft_size ) { - TT_Face face; - FT_Size_Metrics* size_metrics; - - - face = (TT_Face)size->root.face; - - /* nothing to do for CFF2 */ - if ( face->is_cff2 ) - return FT_Err_Ok; + TT_Size size = (TT_Size)ft_size; + TT_Face face = (TT_Face)size->root.face; + FT_Size_Metrics* size_metrics = &size->hinted_metrics; size->ttmetrics.valid = FALSE; - size_metrics = &size->hinted_metrics; - /* copy the result from base layer */ *size_metrics = size->root.metrics; @@ -1343,12 +1384,34 @@ size->ttmetrics.valid = TRUE; - if ( only_height ) - { - /* we must not recompute the scaling values here since */ - /* `tt_size_reset' was already called (with only_height = 0) */ - return FT_Err_Ok; - } + return FT_Err_Ok; + } + + + /************************************************************************** + * + * @Function: + * tt_size_reset + * + * @Description: + * Reset a TrueType size when resolutions and character dimensions + * have been changed. + * + * @Input: + * size :: + * A handle to the target size object. + */ + FT_LOCAL_DEF( FT_Error ) + tt_size_reset( TT_Size size ) + { + FT_Error error; + TT_Face face = (TT_Face)size->root.face; + FT_Size_Metrics* size_metrics = &size->hinted_metrics; + + + error = tt_size_reset_height( (FT_Size)size ); + if ( error ) + return error; if ( face->header.Flags & 8 ) { @@ -1382,6 +1445,8 @@ size->ttmetrics.y_ratio = 0x10000L; } + size->widthp = tt_face_get_device_metrics( face, size_metrics->x_ppem, 0 ); + size->metrics = size_metrics; #ifdef TT_USE_BYTECODE_INTERPRETER @@ -1416,9 +1481,6 @@ TT_Driver driver = (TT_Driver)ttdriver; driver->interpreter_version = TT_INTERPRETER_VERSION_35; -#ifdef TT_SUPPORT_SUBPIXEL_HINTING_INFINALITY - driver->interpreter_version = TT_INTERPRETER_VERSION_38; -#endif #ifdef TT_SUPPORT_SUBPIXEL_HINTING_MINIMAL driver->interpreter_version = TT_INTERPRETER_VERSION_40; #endif diff --git a/src/font/freetype-2.10.2/src/truetype/ttobjs.h b/3rdparty/freetype-2.13.2/src/truetype/ttobjs.h similarity index 97% rename from src/font/freetype-2.10.2/src/truetype/ttobjs.h rename to 3rdparty/freetype-2.13.2/src/truetype/ttobjs.h index 7c3fc7ef8..40eb37b4c 100644 --- a/src/font/freetype-2.10.2/src/truetype/ttobjs.h +++ b/3rdparty/freetype-2.13.2/src/truetype/ttobjs.h @@ -4,7 +4,7 @@ * * Objects manager (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,9 +20,8 @@ #define TTOBJS_H_ -#include -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_TRUETYPE_TYPES_H +#include +#include FT_BEGIN_HEADER @@ -163,8 +162,6 @@ FT_BEGIN_HEADER FT_Long end; /* where does it end? */ FT_UInt opc; /* function #, or instruction code */ FT_Bool active; /* is it active? */ - FT_Bool inline_delta; /* is function that defines inline delta? */ - FT_ULong sph_fdef_flags; /* flags to identify special functions */ } TT_DefRecord, *TT_DefArray; @@ -283,6 +280,8 @@ FT_BEGIN_HEADER TT_Size_Metrics ttmetrics; + FT_Byte* widthp; /* glyph widths from the hdmx table */ + FT_ULong strike_index; /* 0xFFFFFFFF to indicate invalid */ #ifdef TT_USE_BYTECODE_INTERPRETER @@ -390,8 +389,10 @@ FT_BEGIN_HEADER #endif /* TT_USE_BYTECODE_INTERPRETER */ FT_LOCAL( FT_Error ) - tt_size_reset( TT_Size size, - FT_Bool only_height ); + tt_size_reset_height( FT_Size size ); + + FT_LOCAL( FT_Error ) + tt_size_reset( TT_Size size ); /************************************************************************** diff --git a/src/font/freetype-2.10.2/src/truetype/ttpload.c b/3rdparty/freetype-2.13.2/src/truetype/ttpload.c similarity index 77% rename from src/font/freetype-2.10.2/src/truetype/ttpload.c rename to 3rdparty/freetype-2.13.2/src/truetype/ttpload.c index d35393a8b..54a64c7b4 100644 --- a/src/font/freetype-2.10.2/src/truetype/ttpload.c +++ b/3rdparty/freetype-2.13.2/src/truetype/ttpload.c @@ -4,7 +4,7 @@ * * TrueType-specific tables loader (body). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -16,11 +16,10 @@ */ -#include -#include FT_INTERNAL_DEBUG_H -#include FT_INTERNAL_OBJECTS_H -#include FT_INTERNAL_STREAM_H -#include FT_TRUETYPE_TAGS_H +#include +#include +#include +#include #include "ttpload.h" @@ -99,36 +98,23 @@ goto Exit; } - if ( face->header.Index_To_Loc_Format != 0 ) - { - shift = 2; + shift = face->header.Index_To_Loc_Format != 0 ? 2 : 1; - if ( table_len >= 0x40000L ) - { - FT_TRACE2(( "table too large\n" )); - table_len = 0x3FFFFL; - } - face->num_locations = table_len >> shift; - } - else + if ( table_len > 0x10000UL << shift ) { - shift = 1; - - if ( table_len >= 0x20000L ) - { - FT_TRACE2(( "table too large\n" )); - table_len = 0x1FFFFL; - } - face->num_locations = table_len >> shift; + FT_TRACE2(( "table too large\n" )); + table_len = 0x10000UL << shift; } + face->num_locations = table_len >> shift; + if ( face->num_locations != (FT_ULong)face->root.num_glyphs + 1 ) { - FT_TRACE2(( "glyph count mismatch! loca: %d, maxp: %d\n", + FT_TRACE2(( "glyph count mismatch! loca: %ld, maxp: %ld\n", face->num_locations - 1, face->root.num_glyphs )); /* we only handle the case where `maxp' gives a larger value */ - if ( face->num_locations <= (FT_ULong)face->root.num_glyphs ) + if ( face->num_locations < (FT_ULong)face->root.num_glyphs + 1 ) { FT_ULong new_loca_len = ( (FT_ULong)face->root.num_glyphs + 1 ) << shift; @@ -165,7 +151,7 @@ face->num_locations = (FT_ULong)face->root.num_glyphs + 1; table_len = new_loca_len; - FT_TRACE2(( "adjusting num_locations to %d\n", + FT_TRACE2(( "adjusting num_locations to %ld\n", face->num_locations )); } else @@ -173,7 +159,7 @@ face->root.num_glyphs = face->num_locations ? (FT_Long)face->num_locations - 1 : 0; - FT_TRACE2(( "adjusting num_glyphs to %d\n", + FT_TRACE2(( "adjusting num_glyphs to %ld\n", face->root.num_glyphs )); } } @@ -194,10 +180,11 @@ FT_LOCAL_DEF( FT_ULong ) - tt_face_get_location( TT_Face face, - FT_UInt gindex, - FT_UInt *asize ) + tt_face_get_location( FT_Face face, /* TT_Face */ + FT_UInt gindex, + FT_ULong *asize ) { + TT_Face ttface = (TT_Face)face; FT_ULong pos1, pos2; FT_Byte* p; FT_Byte* p_limit; @@ -205,12 +192,12 @@ pos1 = pos2 = 0; - if ( gindex < face->num_locations ) + if ( gindex < ttface->num_locations ) { - if ( face->header.Index_To_Loc_Format != 0 ) + if ( ttface->header.Index_To_Loc_Format != 0 ) { - p = face->glyph_locations + gindex * 4; - p_limit = face->glyph_locations + face->num_locations * 4; + p = ttface->glyph_locations + gindex * 4; + p_limit = ttface->glyph_locations + ttface->num_locations * 4; pos1 = FT_NEXT_ULONG( p ); pos2 = pos1; @@ -220,8 +207,8 @@ } else { - p = face->glyph_locations + gindex * 2; - p_limit = face->glyph_locations + face->num_locations * 2; + p = ttface->glyph_locations + gindex * 2; + p_limit = ttface->glyph_locations + ttface->num_locations * 2; pos1 = FT_NEXT_USHORT( p ); pos2 = pos1; @@ -235,36 +222,39 @@ } /* Check broken location data. */ - if ( pos1 > face->glyf_len ) + if ( pos1 > ttface->glyf_len ) { FT_TRACE1(( "tt_face_get_location:" - " too large offset (0x%08lx) found for glyph index %ld,\n" - " " + " too large offset (0x%08lx) found for glyph index %d,\n", + pos1, gindex )); + FT_TRACE1(( " " " exceeding the end of `glyf' table (0x%08lx)\n", - pos1, gindex, face->glyf_len )); + ttface->glyf_len )); *asize = 0; return 0; } - if ( pos2 > face->glyf_len ) + if ( pos2 > ttface->glyf_len ) { /* We try to sanitize the last `loca' entry. */ - if ( gindex == face->num_locations - 2 ) + if ( gindex == ttface->num_locations - 2 ) { FT_TRACE1(( "tt_face_get_location:" - " too large size (%ld bytes) found for glyph index %ld,\n" - " " + " too large size (%ld bytes) found for glyph index %d,\n", + pos2 - pos1, gindex )); + FT_TRACE1(( " " " truncating at the end of `glyf' table to %ld bytes\n", - pos2 - pos1, gindex, face->glyf_len - pos1 )); - pos2 = face->glyf_len; + ttface->glyf_len - pos1 )); + pos2 = ttface->glyf_len; } else { FT_TRACE1(( "tt_face_get_location:" - " too large offset (0x%08lx) found for glyph index %ld,\n" - " " + " too large offset (0x%08lx) found for glyph index %d,\n", + pos2, gindex + 1 )); + FT_TRACE1(( " " " exceeding the end of `glyf' table (0x%08lx)\n", - pos2, gindex + 1, face->glyf_len )); + ttface->glyf_len )); *asize = 0; return 0; } @@ -279,9 +269,9 @@ /* We get (intentionally) a wrong, non-zero result in case the */ /* `glyf' table is missing. */ if ( pos2 >= pos1 ) - *asize = (FT_UInt)( pos2 - pos1 ); + *asize = (FT_ULong)( pos2 - pos1 ); else - *asize = (FT_UInt)( face->glyf_len - pos1 ); + *asize = (FT_ULong)( ttface->glyf_len - pos1 ); return pos1; } @@ -345,7 +335,7 @@ face->cvt_size = table_len / 2; - if ( FT_NEW_ARRAY( face->cvt, face->cvt_size ) ) + if ( FT_QNEW_ARRAY( face->cvt, face->cvt_size ) ) goto Exit; if ( FT_FRAME_ENTER( face->cvt_size * 2L ) ) @@ -429,7 +419,7 @@ if ( FT_FRAME_EXTRACT( table_len, face->font_program ) ) goto Exit; - FT_TRACE2(( "loaded, %12d bytes\n", face->font_program_size )); + FT_TRACE2(( "loaded, %12ld bytes\n", face->font_program_size )); } Exit: @@ -492,7 +482,7 @@ if ( FT_FRAME_EXTRACT( table_len, face->cvt_program ) ) goto Exit; - FT_TRACE2(( "loaded, %12d bytes\n", face->cvt_program_size )); + FT_TRACE2(( "loaded, %12ld bytes\n", face->cvt_program_size )); } Exit: @@ -509,6 +499,14 @@ } + FT_COMPARE_DEF( int ) + compare_ppem( const void* a, + const void* b ) + { + return **(FT_Byte**)a - **(FT_Byte**)b; + } + + /************************************************************************** * * @Function: @@ -558,12 +556,6 @@ num_records = FT_NEXT_USHORT( p ); record_size = FT_NEXT_ULONG( p ); - /* The maximum number of bytes in an hdmx device record is the */ - /* maximum number of glyphs + 2; this is 0xFFFF + 2, thus */ - /* explaining why `record_size' is a long (which we read as */ - /* unsigned long for convenience). In practice, two bytes are */ - /* sufficient to hold the size value. */ - /* */ /* There are at least two fonts, HANNOM-A and HANNOM-B version */ /* 2.0 (2005), which get this wrong: The upper two bytes of */ /* the size value are set to 0xFF instead of 0x00. We catch */ @@ -572,32 +564,46 @@ if ( record_size >= 0xFFFF0000UL ) record_size &= 0xFFFFU; + FT_TRACE2(( "Hdmx " )); + /* The limit for `num_records' is a heuristic value. */ - if ( num_records > 255 || - ( num_records > 0 && - ( record_size > 0x10001L || - record_size < 4 ) ) ) + if ( num_records > 255 || num_records == 0 ) + { + FT_TRACE2(( "with unreasonable %u records rejected\n", num_records )); + goto Fail; + } + + /* Out-of-spec tables are rejected. The record size must be */ + /* equal to the number of glyphs + 2 + 32-bit padding. */ + if ( (FT_Long)record_size != ( ( face->root.num_glyphs + 2 + 3 ) & ~3 ) ) { - error = FT_THROW( Invalid_File_Format ); + FT_TRACE2(( "with record size off by %ld bytes rejected\n", + (FT_Long)record_size - + ( ( face->root.num_glyphs + 2 + 3 ) & ~3 ) )); goto Fail; } - if ( FT_NEW_ARRAY( face->hdmx_record_sizes, num_records ) ) + if ( FT_QNEW_ARRAY( face->hdmx_records, num_records ) ) goto Fail; for ( nn = 0; nn < num_records; nn++ ) { if ( p + record_size > limit ) break; - - face->hdmx_record_sizes[nn] = p[0]; - p += record_size; + face->hdmx_records[nn] = p; + p += record_size; } + /* The records must be already sorted by ppem but it does not */ + /* hurt to make sure so that the binary search works later. */ + ft_qsort( face->hdmx_records, nn, sizeof ( FT_Byte* ), compare_ppem ); + face->hdmx_record_count = nn; face->hdmx_table_size = table_size; face->hdmx_record_size = record_size; + FT_TRACE2(( "%ux%lu loaded\n", num_records, record_size )); + Exit: return error; @@ -615,7 +621,7 @@ FT_Memory memory = stream->memory; - FT_FREE( face->hdmx_record_sizes ); + FT_FREE( face->hdmx_records ); FT_FRAME_RELEASE( face->hdmx_table ); } @@ -623,27 +629,34 @@ /************************************************************************** * * Return the advance width table for a given pixel size if it is found - * in the font's `hdmx' table (if any). + * in the font's `hdmx' table (if any). The records must be sorted for + * the binary search to work properly. */ FT_LOCAL_DEF( FT_Byte* ) tt_face_get_device_metrics( TT_Face face, FT_UInt ppem, FT_UInt gindex ) { - FT_UInt nn; - FT_Byte* result = NULL; - FT_ULong record_size = face->hdmx_record_size; - FT_Byte* record = FT_OFFSET( face->hdmx_table, 8 ); + FT_UInt min = 0; + FT_UInt max = face->hdmx_record_count; + FT_UInt mid; + FT_Byte* result = NULL; + + while ( min < max ) + { + mid = ( min + max ) >> 1; - for ( nn = 0; nn < face->hdmx_record_count; nn++ ) - if ( face->hdmx_record_sizes[nn] == ppem ) + if ( face->hdmx_records[mid][0] > ppem ) + max = mid; + else if ( face->hdmx_records[mid][0] < ppem ) + min = mid + 1; + else { - gindex += 2; - if ( gindex < record_size ) - result = record + nn * record_size + gindex; + result = face->hdmx_records[mid] + 2 + gindex; break; } + } return result; } diff --git a/src/font/freetype-2.10.2/src/truetype/ttpload.h b/3rdparty/freetype-2.13.2/src/truetype/ttpload.h similarity index 87% rename from src/font/freetype-2.10.2/src/truetype/ttpload.h rename to 3rdparty/freetype-2.13.2/src/truetype/ttpload.h index 3bbd4add1..ed229fa46 100644 --- a/src/font/freetype-2.10.2/src/truetype/ttpload.h +++ b/3rdparty/freetype-2.13.2/src/truetype/ttpload.h @@ -4,7 +4,7 @@ * * TrueType-specific tables loader (specification). * - * Copyright (C) 1996-2020 by + * Copyright (C) 1996-2023 by * David Turner, Robert Wilhelm, and Werner Lemberg. * * This file is part of the FreeType project, and may only be used, @@ -20,8 +20,7 @@ #define TTPLOAD_H_ -#include -#include FT_INTERNAL_TRUETYPE_TYPES_H +#include FT_BEGIN_HEADER @@ -32,9 +31,9 @@ FT_BEGIN_HEADER FT_Stream stream ); FT_LOCAL( FT_ULong ) - tt_face_get_location( TT_Face face, - FT_UInt gindex, - FT_UInt *asize ); + tt_face_get_location( FT_Face face, + FT_UInt gindex, + FT_ULong *asize ); FT_LOCAL( void ) tt_face_done_loca( TT_Face face ); diff --git a/CMakeLists.txt b/CMakeLists.txt index efa257fb0..9cb2dddc0 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -14,7 +14,7 @@ # [MSVC] cd visual-studio; ctest -V -C Release # # A static build can be enabled with -DPARASOL_STATIC=ON if the intention is to embed Parasol into another project. -# This is particularly useful if you intend to use specific features like the vector graphics API. Static builds +# This may be useful if you intend to use a limited feature-set, like the vector graphics API. Static builds # should be customised with an isolated output folder that is exclusive to the target project. Sharing a static # build across multiple projects can otherwise lead to confusing outcomes. @@ -34,7 +34,7 @@ if (CMAKE_PROJECT_NAME STREQUAL PROJECT_NAME) include(CTest) endif() -project (Parasol VERSION 2023.6.12 LANGUAGES C CXX) +project (Parasol VERSION 2024.2.27 LANGUAGES C CXX) cmake_policy (SET CMP0082 NEW) # Process install commands in the order that they appear @@ -58,12 +58,12 @@ option (DISABLE_DOCUMENT "Disable document API" OFF) option (DISABLE_FONT "Disable font API" OFF) option (DISABLE_HTTP "Disable HTTP API" OFF) option (DISABLE_MP3 "Disable MP3 support" OFF) -option (DISABLE_NETWORK "Disable Network API" OFF) -option (DISABLE_PICTURE "Disable Picture API" OFF) +option (DISABLE_NETWORK "Disable network API" OFF) +option (DISABLE_PICTURE "Disable picture API" OFF) option (DISABLE_JPEG "Disable JPEG support" OFF) option (DISABLE_SCINTILLA "Disable Scintilla API" OFF) option (DISABLE_SVG "Disable SVG support" OFF) -option (DISABLE_VECTOR "Disable Vector API" OFF) +option (DISABLE_VECTOR "Disable vector API" OFF) option (INSTALL_EXAMPLES "Install the example scripts, typically for compiling a distribution" OFF) option (INSTALL_INCLUDES "Install the header files. Turn this off for client releases." OFF) option (INSTALL_TESTS "Install the test programs." OFF) @@ -401,12 +401,27 @@ endif () if (MSVC) # Turn off ugly warnings - add_compile_definitions ("_CRT_SECURE_NO_WARNINGS" ) + add_compile_definitions ("_CRT_SECURE_NO_WARNINGS") set (CMAKE_MSVC_RUNTIME_LIBRARY "MultiThreadedDLL") # These options override sub-projects linking to incorrect standard libraries. # https://learn.microsoft.com/en-us/previous-versions/visualstudio/visual-studio-6.0/aa267384(v=vs.60)?redirectedfrom=MSDN add_link_options ("/NODEFAULTLIB:libcmt.lib" "/NODEFAULTLIB:libcmtd.lib" "/NODEFAULTLIB:msvcrtd.lib") # add_link_options ("/VERBOSE:LIB") + if (ENABLE_ANALYSIS) + # Note that this option is not compatible with /ZI (edit-and-continue). To rectify complaints about the asan DLL, you may also need a line like this one added to each entry in launch.vs.json: + # "env": { "Path": "${env:Path};C:\\Program Files\\Microsoft Visual Studio\\2022\\Community\\VC\\Tools\\MSVC\\14.38.33130\\bin\\Hostx64\\x64" } + set (CMAKE_C_FLAGS "${CMAKE_C_FLAGS} /fsanitize=address") + set (CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} /fsanitize=address") + endif () + + # We don't use exceptions, so get the compiler to disable this functionality. This results in noticeably smaller binaries and more optimised code. + if (CMAKE_BUILD_TYPE STREQUAL "Release") + add_compile_definitions ("_HAS_EXCEPTIONS=0") + string(REPLACE "/EHsc" "" CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS}") + string(REPLACE "/EHsc" "" CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS}") + set (CMAKE_C_FLAGS "${CMAKE_C_FLAGS} /EHs-c- /GR") + set (CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} /EHs-c- /GR") + endif () else () if (CMAKE_SYSTEM_NAME STREQUAL "Darwin") add_compile_definitions ("_DARWIN_C_SOURCE") @@ -437,6 +452,10 @@ else () # In addition, gdb breakpoints are unlikely to work with these features enabled. set (CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -fsanitize=address -fsanitize=leak -DANALYSIS_ENABLED") set (CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fsanitize=address -fsanitize=leak -DANALYSIS_ENABLED") + set (DISABLE_AUDIO ON) + if (NOT PARASOL_STATIC) + message (FATAL_ERROR "Address analysis requires the build to be compiled with PARASOL_STATIC on.") + endif () endif () set (CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall -Wno-empty-body -Wno-unused-result -Wno-format-zero-length -Wno-unused-but-set-variable -Wno-stringop-overflow") @@ -469,64 +488,81 @@ set(CMAKE_INSTALL_RPATH "$ORIGIN/lib") add_subdirectory (3rdparty/zlib-1.2.11) # Note that when upgrading, the CMakeLists.txt is customised -add_subdirectory (src/link) -add_subdirectory (src/core) -add_subdirectory (src/fluid) -add_subdirectory (src/xml) -add_subdirectory (src/json) +add_subdirectory (3rdparty/freetype-2.13.2) if (NOT DISABLE_AUDIO) add_subdirectory (src/audio) + list (APPEND LIB_LIST audio) endif () if (NOT DISABLE_DISPLAY) add_subdirectory (src/display) + list (APPEND LIB_LIST display) endif () if ((NOT DISABLE_DOCUMENT) AND (NOT DISABLE_DISPLAY) AND (NOT DISABLE_VECTOR) AND (NOT DISABLE_FONT)) - #add_subdirectory (src/document) + add_subdirectory (src/document) + list (APPEND LIB_LIST document) endif () if (NOT DISABLE_FONT AND NOT DISABLE_DISPLAY) add_subdirectory (src/font) + list (APPEND LIB_LIST font) endif () if (NOT DISABLE_HTTP AND NOT DISABLE_NETWORK) add_subdirectory (src/http) + list (APPEND LIB_LIST http) endif () if (NOT DISABLE_MP3 AND NOT DISABLE_AUDIO) add_subdirectory (src/mp3) + list (APPEND LIB_LIST mp3) endif () if (NOT DISABLE_NETWORK) add_subdirectory (src/network) + list (APPEND LIB_LIST network) endif () if (NOT DISABLE_PICTURE AND NOT DISABLE_DISPLAY) add_subdirectory (src/picture) + list (APPEND LIB_LIST picture) endif () if (NOT DISABLE_JPEG AND NOT DISABLE_PICTURE) add_subdirectory (src/picture_jpeg) + list (APPEND LIB_LIST jpeg) endif () if (NOT DISABLE_SCINTILLA AND NOT DISABLE_DISPLAY AND NOT DISABLE_VECTOR AND NOT DISABLE_FONT) add_subdirectory (src/scintilla) + list (APPEND LIB_LIST scintilla) endif () if (NOT DISABLE_SVG AND NOT DISABLE_VECTOR AND NOT DISABLE_DISPLAY AND NOT DISABLE_FONT) add_subdirectory (src/svg) + list (APPEND LIB_LIST svg) endif () if (NOT DISABLE_VECTOR AND NOT DISABLE_DISPLAY AND NOT DISABLE_FONT) add_subdirectory (src/vector) + list (APPEND LIB_LIST vector) endif () if (X11_Xrandr_FOUND) add_subdirectory (src/xrandr) + list (APPEND LIB_LIST xrandr) endif () +list (APPEND LIB_LIST fluid json jpeg xml) + +add_subdirectory (src/link) +add_subdirectory (src/core) +add_subdirectory (src/fluid) +add_subdirectory (src/xml) +add_subdirectory (src/json) + add_subdirectory (src/launcher) # -------------------------------------------------------------------------------------------------------------------- diff --git a/data/fonts/fixed/courier.fon b/data/fonts/fixed/courier.fon deleted file mode 100644 index 6c3d33fc0..000000000 Binary files a/data/fonts/fixed/courier.fon and /dev/null differ diff --git a/data/fonts/fixed/little.fon b/data/fonts/fixed/little.fon deleted file mode 100644 index 7fb54e571..000000000 Binary files a/data/fonts/fixed/little.fon and /dev/null differ diff --git a/data/fonts/fixed/optismall.fon b/data/fonts/fixed/optismall.fon deleted file mode 100644 index 4c2ac2f96..000000000 Binary files a/data/fonts/fixed/optismall.fon and /dev/null differ diff --git a/data/fonts/fonts.cfg b/data/fonts/fonts.cfg index 0fa56a093..105a661a2 100644 --- a/data/fonts/fonts.cfg +++ b/data/fonts/fonts.cfg @@ -1,234 +1,285 @@ [Clean] +Bold = fonts:fixed/clean.fon +Bold Italic = fonts:fixed/clean.fon +Italic = fonts:fixed/clean.fon Name = Clean -Fixed:Regular = fonts:fixed/clean.fon -Fixed:Bold = fonts:fixed/clean.fon -Fixed:Bold Italic = fonts:fixed/clean.fon -Fixed:Italic = fonts:fixed/clean.fon Points = 8 +Regular = fonts:fixed/clean.fon Styles = Bold,Bold Italic,Italic,Regular -[Courier] -Name = Courier -Fixed:Regular = fonts:fixed/courier.fon -Fixed:Bold = fonts:fixed/courier.fon -Fixed:Bold Italic = fonts:fixed/courier.fon -Fixed:Italic = fonts:fixed/courier.fon -Points = 8,10,12 +[Courier Prime] +Bold = fonts:truetype/Courier Prime Bold.ttf +Bold Italic = fonts:truetype/Courier Prime Bold Italic.ttf +Italic = fonts:truetype/Courier Prime Italic.ttf +Name = Courier Prime +Regular = fonts:truetype/Courier Prime.ttf Scalable = Yes -Scale:Bold = fonts:truetype/Courier Prime Bold.ttf -Scale:Bold Italic = fonts:truetype/Courier Prime Bold Italic.ttf -Scale:Italic = fonts:truetype/Courier Prime Italic.ttf -Scale:Regular = fonts:truetype/Courier Prime.ttf Styles = Bold,Bold Italic,Italic,Regular -[Courier Sans] -Name = Courier Sans +[Crimson Pro] +Axes = wght +Black = fonts:truetype/CrimsonPro-VariableFont.ttf +Black Italic = fonts:truetype/CrimsonPro-Italic-VariableFont.ttf +Bold = fonts:truetype/CrimsonPro-VariableFont.ttf +Bold Italic = fonts:truetype/CrimsonPro-Italic-VariableFont.ttf +Extra Bold = fonts:truetype/CrimsonPro-VariableFont.ttf +Extra Bold Italic = fonts:truetype/CrimsonPro-Italic-VariableFont.ttf +Extra Light = fonts:truetype/CrimsonPro-VariableFont.ttf +Extra Light Italic = fonts:truetype/CrimsonPro-Italic-VariableFont.ttf +Italic = fonts:truetype/CrimsonPro-Italic-VariableFont.ttf +Light = fonts:truetype/CrimsonPro-VariableFont.ttf +Light Italic = fonts:truetype/CrimsonPro-Italic-VariableFont.ttf +Medium = fonts:truetype/CrimsonPro-VariableFont.ttf +Medium Italic = fonts:truetype/CrimsonPro-Italic-VariableFont.ttf +Name = Crimson Pro +Regular = fonts:truetype/CrimsonPro-VariableFont.ttf Scalable = Yes -Scale:Bold = fonts:truetype/Courier Prime Sans Bold.ttf -Scale:Bold Italic = fonts:truetype/Courier Prime Sans Bold Italic.ttf -Scale:Italic = fonts:truetype/Courier Prime Sans Italic.ttf -Scale:Regular = fonts:truetype/Courier Prime Sans.ttf -Styles = Bold,Bold Italic,Italic,Regular +Semi Bold = fonts:truetype/CrimsonPro-VariableFont.ttf +Semi Bold Italic = fonts:truetype/CrimsonPro-Italic-VariableFont.ttf +Styles = Black,Black Italic,Bold,Bold Italic,Extra Bold,Extra Bold Italic,Extra Light,Extra Light Italic,Italic,Light,Light Italic,Medium,Medium Italic,Regular,Semi Bold,Semi Bold Italic +Variable = Yes [Inconsolata] +Axes = wght,wdth +Black = fonts:truetype/Inconsolata-VariableFont.ttf +Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Condensed Black = fonts:truetype/Inconsolata-VariableFont.ttf +Condensed Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Condensed Extra Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Condensed Extra Light = fonts:truetype/Inconsolata-VariableFont.ttf +Condensed Light = fonts:truetype/Inconsolata-VariableFont.ttf +Condensed Medium = fonts:truetype/Inconsolata-VariableFont.ttf +Condensed Regular = fonts:truetype/Inconsolata-VariableFont.ttf +Condensed Semi Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Expanded Black = fonts:truetype/Inconsolata-VariableFont.ttf +Expanded Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Expanded Extra Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Expanded Extra Light = fonts:truetype/Inconsolata-VariableFont.ttf +Expanded Light = fonts:truetype/Inconsolata-VariableFont.ttf +Expanded Medium = fonts:truetype/Inconsolata-VariableFont.ttf +Expanded Regular = fonts:truetype/Inconsolata-VariableFont.ttf +Expanded Semi Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Condensed Black = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Condensed Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Condensed Extra Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Condensed Extra Light = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Condensed Light = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Condensed Medium = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Condensed Regular = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Condensed Semi Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Expanded Black = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Expanded Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Expanded Extra Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Expanded Extra Light = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Expanded Light = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Expanded Medium = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Expanded Regular = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Expanded Semi Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Extra Light = fonts:truetype/Inconsolata-VariableFont.ttf +Light = fonts:truetype/Inconsolata-VariableFont.ttf +Medium = fonts:truetype/Inconsolata-VariableFont.ttf Name = Inconsolata +Regular = fonts:truetype/Inconsolata-VariableFont.ttf Scalable = Yes -Scale:Bold = fonts:truetype/Inconsolata-Bold.ttf -Scale:Regular = fonts:truetype/Inconsolata-Regular.ttf -Styles = Bold,Regular - -[Liberation Mono] -Name = Liberation Mono -Scalable = Yes -Scale:Bold = fonts:truetype/LiberationMono-Bold.ttf -Scale:Bold Italic = fonts:truetype/LiberationMono-BoldItalic.ttf -Scale:Italic = fonts:truetype/LiberationMono-Italic.ttf -Scale:Regular = fonts:truetype/LiberationMono-Regular.ttf -Styles = Bold,Bold Italic,Italic,Regular - -[Liberation Sans] -Name = Liberation Sans -Scalable = Yes -Scale:Bold = fonts:truetype/LiberationSans-Bold.ttf -Scale:Bold Italic = fonts:truetype/LiberationSans-BoldItalic.ttf -Scale:Italic = fonts:truetype/LiberationSans-Italic.ttf -Scale:Regular = fonts:truetype/LiberationSans-Regular.ttf -Styles = Bold,Bold Italic,Italic,Regular - -[Liberation Serif] -Name = Liberation Serif -Scalable = Yes -Scale:Bold = fonts:truetype/LiberationSerif-Bold.ttf -Scale:Bold Italic = fonts:truetype/LiberationSerif-BoldItalic.ttf -Scale:Italic = fonts:truetype/LiberationSerif-Italic.ttf -Scale:Regular = fonts:truetype/LiberationSerif-Regular.ttf -Styles = Bold,Bold Italic,Italic,Regular - -[Little] -Name = Little -Fixed:Regular = fonts:fixed/little.fon -Fixed:Bold = fonts:fixed/little.fon -Fixed:Bold Italic = fonts:fixed/little.fon -Fixed:Italic = fonts:fixed/little.fon -Points = 8 -Styles = Bold,Bold Italic,Italic,Regular +Semi Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Semi Condensed Black = fonts:truetype/Inconsolata-VariableFont.ttf +Semi Condensed Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Semi Condensed Extra Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Semi Condensed Extra Light = fonts:truetype/Inconsolata-VariableFont.ttf +Semi Condensed Light = fonts:truetype/Inconsolata-VariableFont.ttf +Semi Condensed Medium = fonts:truetype/Inconsolata-VariableFont.ttf +Semi Condensed Regular = fonts:truetype/Inconsolata-VariableFont.ttf +Semi Condensed Semi Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Semi Expanded Black = fonts:truetype/Inconsolata-VariableFont.ttf +Semi Expanded Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Semi Expanded Extra Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Semi Expanded Extra Light = fonts:truetype/Inconsolata-VariableFont.ttf +Semi Expanded Light = fonts:truetype/Inconsolata-VariableFont.ttf +Semi Expanded Medium = fonts:truetype/Inconsolata-VariableFont.ttf +Semi Expanded Regular = fonts:truetype/Inconsolata-VariableFont.ttf +Semi Expanded Semi Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Styles = Black,Bold,Condensed Black,Condensed Bold,Condensed Extra Bold,Condensed Extra Light,Condensed Light,Condensed Medium,Condensed Regular,Condensed Semi Bold,Expanded Black,Expanded Bold,Expanded Extra Bold,Expanded Extra Light,Expanded Light,Expanded Medium,Expanded Regular,Expanded Semi Bold,Extra Bold,Extra Condensed Black,Extra Condensed Bold,Extra Condensed Extra Bold,Extra Condensed Extra Light,Extra Condensed Light,Extra Condensed Medium,Extra Condensed Regular,Extra Condensed Semi Bold,Extra Expanded Black,Extra Expanded Bold,Extra Expanded Extra Bold,Extra Expanded Extra Light,Extra Expanded Light,Extra Expanded Medium,Extra Expanded Regular,Extra Expanded Semi Bold,Extra Light,Light,Medium,Regular,Semi Bold,Semi Condensed Black,Semi Condensed Bold,Semi Condensed Extra Bold,Semi Condensed Extra Light,Semi Condensed Light,Semi Condensed Medium,Semi Condensed Regular,Semi Condensed Semi Bold,Semi Expanded Black,Semi Expanded Bold,Semi Expanded Extra Bold,Semi Expanded Extra Light,Semi Expanded Light,Semi Expanded Medium,Semi Expanded Regular,Semi Expanded Semi Bold,Ultra Condensed Black,Ultra Condensed Bold,Ultra Condensed Extra Bold,Ultra Condensed Extra Light,Ultra Condensed Light,Ultra Condensed Medium,Ultra Condensed Regular,Ultra Condensed Semi Bold,Ultra Expanded Black,Ultra Expanded Bold,Ultra Expanded Extra Bold,Ultra Expanded Extra Light,Ultra Expanded Light,Ultra Expanded Medium,Ultra Expanded Regular,Ultra Expanded Semi Bold +Ultra Condensed Black = fonts:truetype/Inconsolata-VariableFont.ttf +Ultra Condensed Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Ultra Condensed Extra Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Ultra Condensed Extra Light = fonts:truetype/Inconsolata-VariableFont.ttf +Ultra Condensed Light = fonts:truetype/Inconsolata-VariableFont.ttf +Ultra Condensed Medium = fonts:truetype/Inconsolata-VariableFont.ttf +Ultra Condensed Regular = fonts:truetype/Inconsolata-VariableFont.ttf +Ultra Condensed Semi Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Ultra Expanded Black = fonts:truetype/Inconsolata-VariableFont.ttf +Ultra Expanded Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Ultra Expanded Extra Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Ultra Expanded Extra Light = fonts:truetype/Inconsolata-VariableFont.ttf +Ultra Expanded Light = fonts:truetype/Inconsolata-VariableFont.ttf +Ultra Expanded Medium = fonts:truetype/Inconsolata-VariableFont.ttf +Ultra Expanded Regular = fonts:truetype/Inconsolata-VariableFont.ttf +Ultra Expanded Semi Bold = fonts:truetype/Inconsolata-VariableFont.ttf +Variable = Yes [Micro] Name = Micro +Regular = fonts:truetype/Micro-6.ttf Scalable = Yes -Scale:Regular = fonts:truetype/Micro-6.ttf Styles = Regular -[Open Sans] -Name = Open Sans +[Noto Color Emoji] +Name = Noto Color Emoji +Regular = fonts:truetype/NotoColorEmoji.ttf Scalable = Yes -Scale:Bold = fonts:truetype/OpenSans-Bold.ttf -Scale:Bold Italic = fonts:truetype/OpenSans-BoldItalic.ttf -Scale:Extra Bold = fonts:truetype/OpenSans-ExtraBold.ttf -Scale:Extra Bold Italic = fonts:truetype/OpenSans-ExtraBoldItalic.ttf -Scale:Italic = fonts:truetype/OpenSans-Italic.ttf -Scale:Light = fonts:truetype/OpenSans-Light.ttf -Scale:Light Italic = fonts:truetype/OpenSans-LightItalic.ttf -Scale:Regular = fonts:truetype/OpenSans-Regular.ttf -Scale:Semibold = fonts:truetype/OpenSans-Semibold.ttf -Scale:Semibold Italic = fonts:truetype/OpenSans-SemiboldItalic.ttf -Styles = Bold,Bold Italic,Extra Bold,Extra Bold Italic,Italic,Light,Light Italic,Regular,Semibold,Semibold Italic +Styles = Regular + +[Noto Sans] +Axes = wght,wdth +Black = fonts:truetype/NotoSans-VariableFont.ttf +Black Italic = fonts:truetype/NotoSans-Italic-VariableFont.ttf +Bold = fonts:truetype/NotoSans-VariableFont.ttf +Bold Italic = fonts:truetype/NotoSans-Italic-VariableFont.ttf +Extra Bold = fonts:truetype/NotoSans-VariableFont.ttf +Extra Bold Italic = fonts:truetype/NotoSans-Italic-VariableFont.ttf +Extra Light = fonts:truetype/NotoSans-VariableFont.ttf +Extra Light Italic = fonts:truetype/NotoSans-Italic-VariableFont.ttf +Italic = fonts:truetype/NotoSans-Italic-VariableFont.ttf +Light = fonts:truetype/NotoSans-VariableFont.ttf +Light Italic = fonts:truetype/NotoSans-Italic-VariableFont.ttf +Medium = fonts:truetype/NotoSans-VariableFont.ttf +Medium Italic = fonts:truetype/NotoSans-Italic-VariableFont.ttf +Name = Noto Sans +Regular = fonts:truetype/NotoSans-VariableFont.ttf +Scalable = Yes +Semi Bold = fonts:truetype/NotoSans-VariableFont.ttf +Semi Bold Italic = fonts:truetype/NotoSans-Italic-VariableFont.ttf +Styles = Black,Black Italic,Bold,Bold Italic,Extra Bold,Extra Bold Italic,Extra Light,Extra Light Italic,Italic,Light,Light Italic,Medium,Medium Italic,Regular,Semi Bold,Semi Bold Italic,Thin,Thin Italic +Thin = fonts:truetype/NotoSans-VariableFont.ttf +Thin Italic = fonts:truetype/NotoSans-Italic-VariableFont.ttf +Variable = Yes [Opti] +Bold = fonts:fixed/opti.fon +Bold Italic = fonts:fixed/opti.fon +Italic = fonts:fixed/opti.fon Name = Opti -Fixed:Regular = fonts:fixed/opti.fon -Fixed:Bold = fonts:fixed/opti.fon -Fixed:Bold Italic = fonts:fixed/opti.fon -Fixed:Italic = fonts:fixed/opti.fon Points = 8 +Regular = fonts:fixed/opti.fon Styles = Bold,Bold Italic,Italic,Regular -[Opti Small] -Name = Opti Small -Fixed:Regular = fonts:fixed/optismall.fon -Fixed:Bold = fonts:fixed/optismall.fon -Fixed:Bold Italic = fonts:fixed/optismall.fon -Fixed:Italic = fonts:fixed/optismall.fon -Points = 8 -Styles = Bold,Bold Italic,Italic,Regular - -[Roboto] -Name = Roboto -Scalable = Yes -Scale:Black = fonts:truetype/Roboto-Black.ttf -Scale:Black Italic = fonts:truetype/Roboto-BlackItalic.ttf -Scale:Bold = fonts:truetype/Roboto-Bold.ttf -Scale:Bold Italic = fonts:truetype/Roboto-BoldItalic.ttf -Scale:Italic = fonts:truetype/Roboto-Italic.ttf -Scale:Light = fonts:truetype/Roboto-Light.ttf -Scale:Light Italic = fonts:truetype/Roboto-LightItalic.ttf -Scale:Medium = fonts:truetype/Roboto-Medium.ttf -Scale:Medium Italic = fonts:truetype/Roboto-MediumItalic.ttf -Scale:Regular = fonts:truetype/Roboto-Regular.ttf -Scale:Thin = fonts:truetype/Roboto-Thin.ttf -Scale:Thin Italic = fonts:truetype/Roboto-ThinItalic.ttf -Styles = Black,Black Italic,Bold,Bold Italic,Italic,Light,Light Italic,Medium,Medium Italic,Regular,Thin,Thin Italic - -[Roboto Condensed] -Name = Roboto Condensed -Scalable = Yes -Scale:Bold = fonts:truetype/RobotoCondensed-Bold.ttf -Scale:Bold Italic = fonts:truetype/RobotoCondensed-BoldItalic.ttf -Scale:Italic = fonts:truetype/RobotoCondensed-Italic.ttf -Scale:Light = fonts:truetype/RobotoCondensed-Light.ttf -Scale:Light Italic = fonts:truetype/RobotoCondensed-LightItalic.ttf -Scale:Regular = fonts:truetype/RobotoCondensed-Regular.ttf -Styles = Bold,Bold Italic,Italic,Light,Light Italic,Regular - [Sans Serif] +Bold = fonts:fixed/sanserif.fon +Bold Italic = fonts:fixed/sanserif.fon +Italic = fonts:fixed/sanserif.fon Name = Sans Serif -Fixed:Regular = fonts:fixed/sanserif.fon -Fixed:Bold = fonts:fixed/sanserif.fon -Fixed:Bold Italic = fonts:fixed/sanserif.fon -Fixed:Italic = fonts:fixed/sanserif.fon Points = 8,10,12 +Regular = fonts:fixed/sanserif.fon Styles = Bold,Bold Italic,Italic,Regular [Small] +Bold = fonts:fixed/small.fon +Bold Italic = fonts:fixed/small.fon +Italic = fonts:fixed/small.fon Name = Small -Fixed:Regular = fonts:fixed/small.fon -Fixed:Bold = fonts:fixed/small.fon -Fixed:Bold Italic = fonts:fixed/small.fon -Fixed:Italic = fonts:fixed/small.fon Points = 8 +Regular = fonts:fixed/small.fon Styles = Bold,Bold Italic,Italic,Regular [Source Code Pro] +Axes = wght +Black = fonts:truetype/SourceCodePro-VariableFont.ttf +Black Italic = fonts:truetype/SourceCodePro-Italic-VariableFont.ttf +Bold = fonts:truetype/SourceCodePro-VariableFont.ttf +Bold Italic = fonts:truetype/SourceCodePro-Italic-VariableFont.ttf +Extra Bold = fonts:truetype/SourceCodePro-VariableFont.ttf +Extra Bold Italic = fonts:truetype/SourceCodePro-Italic-VariableFont.ttf +Extra Light = fonts:truetype/SourceCodePro-VariableFont.ttf +Extra Light Italic = fonts:truetype/SourceCodePro-Italic-VariableFont.ttf +Italic = fonts:truetype/SourceCodePro-Italic-VariableFont.ttf +Light = fonts:truetype/SourceCodePro-VariableFont.ttf +Light Italic = fonts:truetype/SourceCodePro-Italic-VariableFont.ttf +Medium = fonts:truetype/SourceCodePro-VariableFont.ttf +Medium Italic = fonts:truetype/SourceCodePro-Italic-VariableFont.ttf Name = Source Code Pro +Regular = fonts:truetype/SourceCodePro-VariableFont.ttf Scalable = Yes -Scale:Black = fonts:truetype/SourceCodePro-Black.ttf -Scale:Bold = fonts:truetype/SourceCodePro-Bold.ttf -Scale:ExtraLight = fonts:truetype/SourceCodePro-ExtraLight.ttf -Scale:Light = fonts:truetype/SourceCodePro-Light.ttf -Scale:Medium = fonts:truetype/SourceCodePro-Medium.ttf -Scale:Regular = fonts:truetype/SourceCodePro-Regular.ttf -Scale:Semibold = fonts:truetype/SourceCodePro-Semibold.ttf -Styles = Black,Bold,ExtraLight,Light,Medium,Regular,Semibold - -[Source Sans Pro] -Name = Source Sans Pro +Semi Bold = fonts:truetype/SourceCodePro-VariableFont.ttf +Semi Bold Italic = fonts:truetype/SourceCodePro-Italic-VariableFont.ttf +Styles = Black,Black Italic,Bold,Bold Italic,Extra Bold,Extra Bold Italic,Extra Light,Extra Light Italic,Italic,Light,Light Italic,Medium,Medium Italic,Regular,Semi Bold,Semi Bold Italic +Variable = Yes + +[Source Sans 3] +Axes = wght +Black = fonts:truetype/SourceSans3-VariableFont.ttf +Black Italic = fonts:truetype/SourceSans3-Italic-VariableFont.ttf +Bold = fonts:truetype/SourceSans3-VariableFont.ttf +Bold Italic = fonts:truetype/SourceSans3-Italic-VariableFont.ttf +Extra Bold = fonts:truetype/SourceSans3-VariableFont.ttf +Extra Bold Italic = fonts:truetype/SourceSans3-Italic-VariableFont.ttf +Extra Light = fonts:truetype/SourceSans3-VariableFont.ttf +Extra Light Italic = fonts:truetype/SourceSans3-Italic-VariableFont.ttf +Italic = fonts:truetype/SourceSans3-Italic-VariableFont.ttf +Light = fonts:truetype/SourceSans3-VariableFont.ttf +Light Italic = fonts:truetype/SourceSans3-Italic-VariableFont.ttf +Medium = fonts:truetype/SourceSans3-VariableFont.ttf +Medium Italic = fonts:truetype/SourceSans3-Italic-VariableFont.ttf +Name = Source Sans 3 +Regular = fonts:truetype/SourceSans3-VariableFont.ttf Scalable = Yes -Scale:Black = fonts:truetype/SourceSansPro-Black.ttf -Scale:Black Italic = fonts:truetype/SourceSansPro-BlackItalic.ttf -Scale:Bold = fonts:truetype/SourceSansPro-Bold.ttf -Scale:Bold Italic = fonts:truetype/SourceSansPro-BoldItalic.ttf -Scale:ExtraLight = fonts:truetype/SourceSansPro-ExtraLight.ttf -Scale:ExtraLight Italic = fonts:truetype/SourceSansPro-ExtraLightItalic.ttf -Scale:Italic = fonts:truetype/SourceSansPro-Italic.ttf -Scale:Light = fonts:truetype/SourceSansPro-Light.ttf -Scale:Light Italic = fonts:truetype/SourceSansPro-LightItalic.ttf -Scale:Regular = fonts:truetype/SourceSansPro-Regular.ttf -Scale:Semibold = fonts:truetype/SourceSansPro-Semibold.ttf -Scale:Semibold Italic = fonts:truetype/SourceSansPro-SemiboldItalic.ttf -Styles = Black,Black Italic,Bold,Bold Italic,ExtraLight,ExtraLight Italic,Italic,Light,Light Italic,Regular,Semibold,Semibold Italic +Semi Bold = fonts:truetype/SourceSans3-VariableFont.ttf +Semi Bold Italic = fonts:truetype/SourceSans3-Italic-VariableFont.ttf +Styles = Black,Black Italic,Bold,Bold Italic,Extra Bold,Extra Bold Italic,Extra Light,Extra Light Italic,Italic,Light,Light Italic,Medium,Medium Italic,Regular,Semi Bold,Semi Bold Italic +Variable = Yes [Speedy] +Bold = fonts:fixed/speedy.fon +Bold Italic = fonts:fixed/speedy.fon +Italic = fonts:fixed/speedy.fon Name = Speedy -Fixed:Regular = fonts:fixed/speedy.fon -Fixed:Bold = fonts:fixed/speedy.fon -Fixed:Bold Italic = fonts:fixed/speedy.fon -Fixed:Italic = fonts:fixed/speedy.fon Points = 8,9 +Regular = fonts:fixed/speedy.fon Styles = Bold,Bold Italic,Italic,Regular [Tiny] +Bold = fonts:fixed/tiny.fon +Bold Italic = fonts:fixed/tiny.fon +Italic = fonts:fixed/tiny.fon Name = Tiny -Fixed:Regular = fonts:fixed/tiny.fon -Fixed:Bold = fonts:fixed/tiny.fon -Fixed:Bold Italic = fonts:fixed/tiny.fon -Fixed:Italic = fonts:fixed/tiny.fon Points = 5,6 +Regular = fonts:fixed/tiny.fon Styles = Bold,Bold Italic,Italic,Regular [Totem] +Bold = fonts:fixed/totem.fon +Bold Italic = fonts:fixed/totem.fon +Italic = fonts:fixed/totem.fon Name = Totem -Fixed:Regular = fonts:fixed/totem.fon -Fixed:Bold = fonts:fixed/totem.fon -Fixed:Bold Italic = fonts:fixed/totem.fon -Fixed:Italic = fonts:fixed/totem.fon Points = 8,10,12 -Styles = Bold,Bold Italic,Italic,Regular - -[Utopia] -Name = Utopia -Scalable = Yes -Scale:Bold = fonts:truetype/Utopia-Bold.ttf -Scale:Bold Italic = fonts:truetype/Utopia-BoldItalic.ttf -Scale:Italic = fonts:truetype/Utopia-Italic.ttf -Scale:Regular = fonts:truetype/Utopia.ttf +Regular = fonts:fixed/totem.fon Styles = Bold,Bold Italic,Italic,Regular [Veranda] +Bold = fonts:fixed/veranda.fon +Bold Italic = fonts:fixed/veranda.fon +Italic = fonts:fixed/veranda.fon Name = Veranda -Fixed:Regular = fonts:fixed/veranda.fon -Fixed:Bold = fonts:fixed/veranda.fon -Fixed:Bold Italic = fonts:fixed/veranda.fon -Fixed:Italic = fonts:fixed/veranda.fon Points = 8,10,11 +Regular = fonts:fixed/veranda.fon Styles = Bold,Bold Italic,Italic,Regular + +[Vollkorn] +Axes = wght +Black = fonts:truetype/Vollkorn-VariableFont.ttf +Black Italic = fonts:truetype/Vollkorn-Italic-VariableFont.ttf +Bold = fonts:truetype/Vollkorn-VariableFont.ttf +Bold Italic = fonts:truetype/Vollkorn-Italic-VariableFont.ttf +Extra Bold = fonts:truetype/Vollkorn-VariableFont.ttf +Extra Bold Italic = fonts:truetype/Vollkorn-Italic-VariableFont.ttf +Italic = fonts:truetype/Vollkorn-Italic-VariableFont.ttf +Medium = fonts:truetype/Vollkorn-VariableFont.ttf +Medium Italic = fonts:truetype/Vollkorn-Italic-VariableFont.ttf +Name = Vollkorn +Regular = fonts:truetype/Vollkorn-VariableFont.ttf +Scalable = Yes +Semi Bold = fonts:truetype/Vollkorn-VariableFont.ttf +Semi Bold Italic = fonts:truetype/Vollkorn-Italic-VariableFont.ttf +Styles = Black,Black Italic,Bold,Bold Italic,Extra Bold,Extra Bold Italic,Italic,Medium,Medium Italic,Regular,Semi Bold,Semi Bold Italic +Variable = Yes diff --git a/data/fonts/license-courier-prime-sans.txt b/data/fonts/license-courier-prime-sans.txt deleted file mode 100644 index c2381ee02..000000000 --- a/data/fonts/license-courier-prime-sans.txt +++ /dev/null @@ -1,43 +0,0 @@ -Copyright (c) 2015, Quote-Unquote Apps (http://quoteunquoteapps.com), with Reserved Font Name Courier Prime Sans. - -This Font Software is licensed under the SIL Open Font License, Version 1.1. This license is copied below, and is also available with a FAQ at: http://scripts.sil.org/OFL - - ------------------------------------------------------------ -SIL OPEN FONT LICENSE Version 1.1 - 26 February 2007 ------------------------------------------------------------ - -PREAMBLE -The goals of the Open Font License (OFL) are to stimulate worldwide development of collaborative font projects, to support the font creation efforts of academic and linguistic communities, and to provide a free and open framework in which fonts may be shared and improved in partnership with others. - -The OFL allows the licensed fonts to be used, studied, modified and redistributed freely as long as they are not sold by themselves. The fonts, including any derivative works, can be bundled, embedded, redistributed and/or sold with any software provided that any reserved names are not used by derivative works. The fonts and derivatives, however, cannot be released under any other type of license. The requirement for fonts to remain under this license does not apply to any document created using the fonts or their derivatives. - -DEFINITIONS -"Font Software" refers to the set of files released by the Copyright Holder(s) under this license and clearly marked as such. This may include source files, build scripts and documentation. - -"Reserved Font Name" refers to any names specified as such after the copyright statement(s). - -"Original Version" refers to the collection of Font Software components as distributed by the Copyright Holder(s). - -"Modified Version" refers to any derivative made by adding to, deleting, or substituting -- in part or in whole -- any of the components of the Original Version, by changing formats or by porting the Font Software to a new environment. - -"Author" refers to any designer, engineer, programmer, technical writer or other person who contributed to the Font Software. - -PERMISSION & CONDITIONS -Permission is hereby granted, free of charge, to any person obtaining a copy of the Font Software, to use, study, copy, merge, embed, modify, redistribute, and sell modified and unmodified copies of the Font Software, subject to the following conditions: - -1) Neither the Font Software nor any of its individual components, in Original or Modified Versions, may be sold by itself. - -2) Original or Modified Versions of the Font Software may be bundled, redistributed and/or sold with any software, provided that each copy contains the above copyright notice and this license. These can be included either as stand-alone text files, human-readable headers or in the appropriate machine-readable metadata fields within text or binary files as long as those fields can be easily viewed by the user. - -3) No Modified Version of the Font Software may use the Reserved Font Name(s) unless explicit written permission is granted by the corresponding Copyright Holder. This restriction only applies to the primary font name as presented to the users. - -4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font Software shall not be used to promote, endorse or advertise any Modified Version, except to acknowledge the contribution(s) of the Copyright Holder(s) and the Author(s) or with their explicit written permission. - -5) The Font Software, modified or unmodified, in part or in whole, must be distributed entirely under this license, and must not be distributed under any other license. The requirement for fonts to remain under this license does not apply to any document created using the Font Software. - -TERMINATION -This license becomes null and void if any of the above conditions are not met. - -DISCLAIMER -THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM OTHER DEALINGS IN THE FONT SOFTWARE. \ No newline at end of file diff --git a/data/fonts/license-courier-prime.txt b/data/fonts/license-courier-prime.txt index c49013fb7..a160ca5c8 100644 --- a/data/fonts/license-courier-prime.txt +++ b/data/fonts/license-courier-prime.txt @@ -1,44 +1,93 @@ -ABOUT COURIER PRIME -=================== - -Courier Prime is a TrueType monospaced font designed specifically for screenplays. It was designed by Alan Dague-Greene for John August and released by Quote-Unquote Apps under the SIL Open Font License (OFL). - -Visit http://quoteunquoteapps.com/courierprime for more information and the latest updates. - -SIL Open Font License: http://scripts.sil.org/OFL - -INSTALLATION -============ - -Mac OS X: - -Select all the font files and double-click the selected files. Then, click 'Install Font' at the bottom of the preview window. - -Windows 7 & 8: - -The easiest way to install a font is to double-click on a font file to open the font preview and select 'Install'. - -Windows Vista: - -To install a TrueType or OpenType font on Windows Vista, right-click on the font file and then select 'Install'. You can also drag or paste a font into the Fonts Control Panel. - -Windows XP: - -1. From the 'Start' menu select 'Control Panel', then select the 'Appearance and Themes' category. - -2. Select 'Fonts' from the 'See Also' panel at the left of this screen. - -3. On the 'File' menu, select 'Install New Font...' - -4. Click the drive and folder that contain the fonts you want to add. - -5. To select more than one font to add, press and hold down the CTRL key, click the fonts you want, then click on 'OK'. - -For more information on installing fonts on Windows, visit this link: http://www.microsoft.com/typography/truetypeinstall.mspx - - -CHANGELOG -========= - -January 25, 2013 Courier Prime version 1.203 -- Initial release +Copyright 2015 The Courier Prime Project Authors (https://github.com/quoteunquoteapps/CourierPrime). + +This Font Software is licensed under the SIL Open Font License, Version 1.1. +This license is copied below, and is also available with a FAQ at: +https://openfontlicense.org + + +----------------------------------------------------------- +SIL OPEN FONT LICENSE Version 1.1 - 26 February 2007 +----------------------------------------------------------- + +PREAMBLE +The goals of the Open Font License (OFL) are to stimulate worldwide +development of collaborative font projects, to support the font creation +efforts of academic and linguistic communities, and to provide a free and +open framework in which fonts may be shared and improved in partnership +with others. + +The OFL allows the licensed fonts to be used, studied, modified and +redistributed freely as long as they are not sold by themselves. The +fonts, including any derivative works, can be bundled, embedded, +redistributed and/or sold with any software provided that any reserved +names are not used by derivative works. The fonts and derivatives, +however, cannot be released under any other type of license. The +requirement for fonts to remain under this license does not apply +to any document created using the fonts or their derivatives. + +DEFINITIONS +"Font Software" refers to the set of files released by the Copyright +Holder(s) under this license and clearly marked as such. This may +include source files, build scripts and documentation. + +"Reserved Font Name" refers to any names specified as such after the +copyright statement(s). + +"Original Version" refers to the collection of Font Software components as +distributed by the Copyright Holder(s). + +"Modified Version" refers to any derivative made by adding to, deleting, +or substituting -- in part or in whole -- any of the components of the +Original Version, by changing formats or by porting the Font Software to a +new environment. + +"Author" refers to any designer, engineer, programmer, technical +writer or other person who contributed to the Font Software. + +PERMISSION & CONDITIONS +Permission is hereby granted, free of charge, to any person obtaining +a copy of the Font Software, to use, study, copy, merge, embed, modify, +redistribute, and sell modified and unmodified copies of the Font +Software, subject to the following conditions: + +1) Neither the Font Software nor any of its individual components, +in Original or Modified Versions, may be sold by itself. + +2) Original or Modified Versions of the Font Software may be bundled, +redistributed and/or sold with any software, provided that each copy +contains the above copyright notice and this license. These can be +included either as stand-alone text files, human-readable headers or +in the appropriate machine-readable metadata fields within text or +binary files as long as those fields can be easily viewed by the user. + +3) No Modified Version of the Font Software may use the Reserved Font +Name(s) unless explicit written permission is granted by the corresponding +Copyright Holder. This restriction only applies to the primary font name as +presented to the users. + +4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font +Software shall not be used to promote, endorse or advertise any +Modified Version, except to acknowledge the contribution(s) of the +Copyright Holder(s) and the Author(s) or with their explicit written +permission. + +5) The Font Software, modified or unmodified, in part or in whole, +must be distributed entirely under this license, and must not be +distributed under any other license. The requirement for fonts to +remain under this license does not apply to any document created +using the Font Software. + +TERMINATION +This license becomes null and void if any of the above conditions are +not met. + +DISCLAIMER +THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT +OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE +COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL +DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM +OTHER DEALINGS IN THE FONT SOFTWARE. diff --git a/data/fonts/license-crimsonpro.txt b/data/fonts/license-crimsonpro.txt new file mode 100644 index 000000000..3a3affd8d --- /dev/null +++ b/data/fonts/license-crimsonpro.txt @@ -0,0 +1,93 @@ +Copyright 2018 The Crimson Pro Project Authors (https://github.com/Fonthausen/CrimsonPro) + +This Font Software is licensed under the SIL Open Font License, Version 1.1. +This license is copied below, and is also available with a FAQ at: +https://openfontlicense.org + + +----------------------------------------------------------- +SIL OPEN FONT LICENSE Version 1.1 - 26 February 2007 +----------------------------------------------------------- + +PREAMBLE +The goals of the Open Font License (OFL) are to stimulate worldwide +development of collaborative font projects, to support the font creation +efforts of academic and linguistic communities, and to provide a free and +open framework in which fonts may be shared and improved in partnership +with others. + +The OFL allows the licensed fonts to be used, studied, modified and +redistributed freely as long as they are not sold by themselves. The +fonts, including any derivative works, can be bundled, embedded, +redistributed and/or sold with any software provided that any reserved +names are not used by derivative works. The fonts and derivatives, +however, cannot be released under any other type of license. The +requirement for fonts to remain under this license does not apply +to any document created using the fonts or their derivatives. + +DEFINITIONS +"Font Software" refers to the set of files released by the Copyright +Holder(s) under this license and clearly marked as such. This may +include source files, build scripts and documentation. + +"Reserved Font Name" refers to any names specified as such after the +copyright statement(s). + +"Original Version" refers to the collection of Font Software components as +distributed by the Copyright Holder(s). + +"Modified Version" refers to any derivative made by adding to, deleting, +or substituting -- in part or in whole -- any of the components of the +Original Version, by changing formats or by porting the Font Software to a +new environment. + +"Author" refers to any designer, engineer, programmer, technical +writer or other person who contributed to the Font Software. + +PERMISSION & CONDITIONS +Permission is hereby granted, free of charge, to any person obtaining +a copy of the Font Software, to use, study, copy, merge, embed, modify, +redistribute, and sell modified and unmodified copies of the Font +Software, subject to the following conditions: + +1) Neither the Font Software nor any of its individual components, +in Original or Modified Versions, may be sold by itself. + +2) Original or Modified Versions of the Font Software may be bundled, +redistributed and/or sold with any software, provided that each copy +contains the above copyright notice and this license. These can be +included either as stand-alone text files, human-readable headers or +in the appropriate machine-readable metadata fields within text or +binary files as long as those fields can be easily viewed by the user. + +3) No Modified Version of the Font Software may use the Reserved Font +Name(s) unless explicit written permission is granted by the corresponding +Copyright Holder. This restriction only applies to the primary font name as +presented to the users. + +4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font +Software shall not be used to promote, endorse or advertise any +Modified Version, except to acknowledge the contribution(s) of the +Copyright Holder(s) and the Author(s) or with their explicit written +permission. + +5) The Font Software, modified or unmodified, in part or in whole, +must be distributed entirely under this license, and must not be +distributed under any other license. The requirement for fonts to +remain under this license does not apply to any document created +using the Font Software. + +TERMINATION +This license becomes null and void if any of the above conditions are +not met. + +DISCLAIMER +THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT +OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE +COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL +DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM +OTHER DEALINGS IN THE FONT SOFTWARE. diff --git a/data/fonts/license-inconsolata.txt b/data/fonts/license-inconsolata.txt index d9ae61592..55533e1e7 100644 --- a/data/fonts/license-inconsolata.txt +++ b/data/fonts/license-inconsolata.txt @@ -1,92 +1,93 @@ -Copyright (c) 2011, Raph Levien (firstname.lastname@gmail.com), Copyright (c) 2012, Cyreal (cyreal.org) -This Font Software is licensed under the SIL Open Font License, Version 1.1. -This license is copied below, and is also available with a FAQ at: -http://scripts.sil.org/OFL - - ------------------------------------------------------------ -SIL OPEN FONT LICENSE Version 1.1 - 26 February 2007 ------------------------------------------------------------ - -PREAMBLE -The goals of the Open Font License (OFL) are to stimulate worldwide -development of collaborative font projects, to support the font creation -efforts of academic and linguistic communities, and to provide a free and -open framework in which fonts may be shared and improved in partnership -with others. - -The OFL allows the licensed fonts to be used, studied, modified and -redistributed freely as long as they are not sold by themselves. The -fonts, including any derivative works, can be bundled, embedded, -redistributed and/or sold with any software provided that any reserved -names are not used by derivative works. The fonts and derivatives, -however, cannot be released under any other type of license. The -requirement for fonts to remain under this license does not apply -to any document created using the fonts or their derivatives. - -DEFINITIONS -"Font Software" refers to the set of files released by the Copyright -Holder(s) under this license and clearly marked as such. This may -include source files, build scripts and documentation. - -"Reserved Font Name" refers to any names specified as such after the -copyright statement(s). - -"Original Version" refers to the collection of Font Software components as -distributed by the Copyright Holder(s). - -"Modified Version" refers to any derivative made by adding to, deleting, -or substituting -- in part or in whole -- any of the components of the -Original Version, by changing formats or by porting the Font Software to a -new environment. - -"Author" refers to any designer, engineer, programmer, technical -writer or other person who contributed to the Font Software. - -PERMISSION & CONDITIONS -Permission is hereby granted, free of charge, to any person obtaining -a copy of the Font Software, to use, study, copy, merge, embed, modify, -redistribute, and sell modified and unmodified copies of the Font -Software, subject to the following conditions: - -1) Neither the Font Software nor any of its individual components, -in Original or Modified Versions, may be sold by itself. - -2) Original or Modified Versions of the Font Software may be bundled, -redistributed and/or sold with any software, provided that each copy -contains the above copyright notice and this license. These can be -included either as stand-alone text files, human-readable headers or -in the appropriate machine-readable metadata fields within text or -binary files as long as those fields can be easily viewed by the user. - -3) No Modified Version of the Font Software may use the Reserved Font -Name(s) unless explicit written permission is granted by the corresponding -Copyright Holder. This restriction only applies to the primary font name as -presented to the users. - -4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font -Software shall not be used to promote, endorse or advertise any -Modified Version, except to acknowledge the contribution(s) of the -Copyright Holder(s) and the Author(s) or with their explicit written -permission. - -5) The Font Software, modified or unmodified, in part or in whole, -must be distributed entirely under this license, and must not be -distributed under any other license. The requirement for fonts to -remain under this license does not apply to any document created -using the Font Software. - -TERMINATION -This license becomes null and void if any of the above conditions are -not met. - -DISCLAIMER -THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, -EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF -MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT -OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE -COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, -INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL -DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM -OTHER DEALINGS IN THE FONT SOFTWARE. +Copyright 2006 The Inconsolata Project Authors + +This Font Software is licensed under the SIL Open Font License, Version 1.1. +This license is copied below, and is also available with a FAQ at: +https://openfontlicense.org + + +----------------------------------------------------------- +SIL OPEN FONT LICENSE Version 1.1 - 26 February 2007 +----------------------------------------------------------- + +PREAMBLE +The goals of the Open Font License (OFL) are to stimulate worldwide +development of collaborative font projects, to support the font creation +efforts of academic and linguistic communities, and to provide a free and +open framework in which fonts may be shared and improved in partnership +with others. + +The OFL allows the licensed fonts to be used, studied, modified and +redistributed freely as long as they are not sold by themselves. The +fonts, including any derivative works, can be bundled, embedded, +redistributed and/or sold with any software provided that any reserved +names are not used by derivative works. The fonts and derivatives, +however, cannot be released under any other type of license. The +requirement for fonts to remain under this license does not apply +to any document created using the fonts or their derivatives. + +DEFINITIONS +"Font Software" refers to the set of files released by the Copyright +Holder(s) under this license and clearly marked as such. This may +include source files, build scripts and documentation. + +"Reserved Font Name" refers to any names specified as such after the +copyright statement(s). + +"Original Version" refers to the collection of Font Software components as +distributed by the Copyright Holder(s). + +"Modified Version" refers to any derivative made by adding to, deleting, +or substituting -- in part or in whole -- any of the components of the +Original Version, by changing formats or by porting the Font Software to a +new environment. + +"Author" refers to any designer, engineer, programmer, technical +writer or other person who contributed to the Font Software. + +PERMISSION & CONDITIONS +Permission is hereby granted, free of charge, to any person obtaining +a copy of the Font Software, to use, study, copy, merge, embed, modify, +redistribute, and sell modified and unmodified copies of the Font +Software, subject to the following conditions: + +1) Neither the Font Software nor any of its individual components, +in Original or Modified Versions, may be sold by itself. + +2) Original or Modified Versions of the Font Software may be bundled, +redistributed and/or sold with any software, provided that each copy +contains the above copyright notice and this license. These can be +included either as stand-alone text files, human-readable headers or +in the appropriate machine-readable metadata fields within text or +binary files as long as those fields can be easily viewed by the user. + +3) No Modified Version of the Font Software may use the Reserved Font +Name(s) unless explicit written permission is granted by the corresponding +Copyright Holder. This restriction only applies to the primary font name as +presented to the users. + +4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font +Software shall not be used to promote, endorse or advertise any +Modified Version, except to acknowledge the contribution(s) of the +Copyright Holder(s) and the Author(s) or with their explicit written +permission. + +5) The Font Software, modified or unmodified, in part or in whole, +must be distributed entirely under this license, and must not be +distributed under any other license. The requirement for fonts to +remain under this license does not apply to any document created +using the Font Software. + +TERMINATION +This license becomes null and void if any of the above conditions are +not met. + +DISCLAIMER +THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT +OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE +COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL +DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM +OTHER DEALINGS IN THE FONT SOFTWARE. diff --git a/data/fonts/license-liberation.txt b/data/fonts/license-liberation.txt deleted file mode 100644 index e972b52de..000000000 --- a/data/fonts/license-liberation.txt +++ /dev/null @@ -1,13 +0,0 @@ -LICENSE AGREEMENT AND LIMITED PRODUCT WARRANTY -LIBERATION FONT SOFTWARE - -This agreement governs the use of the Software and any updates to the Software, regardless of the delivery mechanism. Subject to the following terms, Red Hat, Inc. ("Red Hat") grants to the user ("Client") a license to this work pursuant to the GNU General Public License v.2 with the exceptions set forth below and such other terms as our set forth in this End User License Agreement. - - 1.The Software and License Exception. LIBERATION font software (the "Software") consists of TrueType-OpenType formatted font software for rendering LIBERATION typefaces in sans serif, serif, and monospaced character styles. You are licensed to use, modify, copy, and distribute the Software pursuant to the GNU General Public License v.2 with the following exceptions: -(a)As a special exception, if you create a document which uses this font, and embed this font or unaltered portions of this font into the document, this font does not by itself cause the resulting document to be covered by the GNU General Public License. This exception does not however invalidate any other reasons why the document might be covered by the GNU General Public License. If you modify this font, you may extend this exception to your version of the font, but you are not obligated to do so. If you do not wish to do so, delete this exception statement from your version. -(b)As a further exception, any distribution of the object code of the Software in a physical product must provide you the right to access and modify the source code for the Software and to reinstall that modified version of the Software in object code form on the same physical product on which you received it. - 2.Intellectual Property Rights. The Software and each of its components, including the source code, documentation, appearance, structure and organization are owned by Red Hat and others and are protected under copyright and other laws. Title to the Software and any component, or to any copy, modification, or merged portion shall remain with the aforementioned, subject to the applicable license. The "LIBERATION" trademark is a trademark of Red Hat, Inc. in the U.S. and other countries. This agreement does not permit Client to distribute modified versions of the Software using Red Hat's trademarks. If Client makes a redistribution of a modified version of the Software, then Client must modify the files names to remove any reference to the Red Hat trademarks and must not use the Red Hat trademarks in any way to reference or promote the modified Software. - 3.Limited Warranty. To the maximum extent permitted under applicable law, the Software is provided and licensed "as is" without warranty of any kind, expressed or implied, including the implied warranties of merchantability, non-infringement or fitness for a particular purpose. Red Hat does not warrant that the functions contained in the Software will meet Client's requirements or that the operation of the Software will be entirely error free or appear precisely as described in the accompanying documentation. - 4.Limitation of Remedies and Liability. To the maximum extent permitted by applicable law, Red Hat or any Red Hat authorized dealer will not be liable to Client for any incidental or consequential damages, including lost profits or lost savings arising out of the use or inability to use the Software, even if Red Hat or such dealer has been advised of the possibility of such damages. - 5.General. If any provision of this agreement is held to be unenforceable, that shall not affect the enforceability of the remaining provisions. This agreement shall be governed by the laws of the State of North Carolina and of the United States, without regard to any conflict of laws provisions, except that the United Nations Convention on the International Sale of Goods shall not apply. -Copyright © 2007 Red Hat, Inc. All rights reserved. LIBERATION is a trademark of Red Hat, Inc. diff --git a/data/fonts/license-noto.txt b/data/fonts/license-noto.txt new file mode 100644 index 000000000..979c943ef --- /dev/null +++ b/data/fonts/license-noto.txt @@ -0,0 +1,93 @@ +Copyright 2021 Google Inc. All Rights Reserved. + +This Font Software is licensed under the SIL Open Font License, Version 1.1. +This license is copied below, and is also available with a FAQ at: +https://openfontlicense.org + + +----------------------------------------------------------- +SIL OPEN FONT LICENSE Version 1.1 - 26 February 2007 +----------------------------------------------------------- + +PREAMBLE +The goals of the Open Font License (OFL) are to stimulate worldwide +development of collaborative font projects, to support the font creation +efforts of academic and linguistic communities, and to provide a free and +open framework in which fonts may be shared and improved in partnership +with others. + +The OFL allows the licensed fonts to be used, studied, modified and +redistributed freely as long as they are not sold by themselves. The +fonts, including any derivative works, can be bundled, embedded, +redistributed and/or sold with any software provided that any reserved +names are not used by derivative works. The fonts and derivatives, +however, cannot be released under any other type of license. The +requirement for fonts to remain under this license does not apply +to any document created using the fonts or their derivatives. + +DEFINITIONS +"Font Software" refers to the set of files released by the Copyright +Holder(s) under this license and clearly marked as such. This may +include source files, build scripts and documentation. + +"Reserved Font Name" refers to any names specified as such after the +copyright statement(s). + +"Original Version" refers to the collection of Font Software components as +distributed by the Copyright Holder(s). + +"Modified Version" refers to any derivative made by adding to, deleting, +or substituting -- in part or in whole -- any of the components of the +Original Version, by changing formats or by porting the Font Software to a +new environment. + +"Author" refers to any designer, engineer, programmer, technical +writer or other person who contributed to the Font Software. + +PERMISSION & CONDITIONS +Permission is hereby granted, free of charge, to any person obtaining +a copy of the Font Software, to use, study, copy, merge, embed, modify, +redistribute, and sell modified and unmodified copies of the Font +Software, subject to the following conditions: + +1) Neither the Font Software nor any of its individual components, +in Original or Modified Versions, may be sold by itself. + +2) Original or Modified Versions of the Font Software may be bundled, +redistributed and/or sold with any software, provided that each copy +contains the above copyright notice and this license. These can be +included either as stand-alone text files, human-readable headers or +in the appropriate machine-readable metadata fields within text or +binary files as long as those fields can be easily viewed by the user. + +3) No Modified Version of the Font Software may use the Reserved Font +Name(s) unless explicit written permission is granted by the corresponding +Copyright Holder. This restriction only applies to the primary font name as +presented to the users. + +4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font +Software shall not be used to promote, endorse or advertise any +Modified Version, except to acknowledge the contribution(s) of the +Copyright Holder(s) and the Author(s) or with their explicit written +permission. + +5) The Font Software, modified or unmodified, in part or in whole, +must be distributed entirely under this license, and must not be +distributed under any other license. The requirement for fonts to +remain under this license does not apply to any document created +using the Font Software. + +TERMINATION +This license becomes null and void if any of the above conditions are +not met. + +DISCLAIMER +THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT +OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE +COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL +DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM +OTHER DEALINGS IN THE FONT SOFTWARE. diff --git a/data/fonts/license-opensans.txt b/data/fonts/license-opensans.txt deleted file mode 100644 index d64569567..000000000 --- a/data/fonts/license-opensans.txt +++ /dev/null @@ -1,202 +0,0 @@ - - Apache License - Version 2.0, January 2004 - http://www.apache.org/licenses/ - - TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION - - 1. Definitions. - - "License" shall mean the terms and conditions for use, reproduction, - and distribution as defined by Sections 1 through 9 of this document. - - "Licensor" shall mean the copyright owner or entity authorized by - the copyright owner that is granting the License. - - "Legal Entity" shall mean the union of the acting entity and all - other entities that control, are controlled by, or are under common - control with that entity. For the purposes of this definition, - "control" means (i) the power, direct or indirect, to cause the - direction or management of such entity, whether by contract or - otherwise, or (ii) ownership of fifty percent (50%) or more of the - outstanding shares, or (iii) beneficial ownership of such entity. - - "You" (or "Your") shall mean an individual or Legal Entity - exercising permissions granted by this License. - - "Source" form shall mean the preferred form for making modifications, - including but not limited to software source code, documentation - source, and configuration files. - - "Object" form shall mean any form resulting from mechanical - transformation or translation of a Source form, including but - not limited to compiled object code, generated documentation, - and conversions to other media types. - - "Work" shall mean the work of authorship, whether in Source or - Object form, made available under the License, as indicated by a - copyright notice that is included in or attached to the work - (an example is provided in the Appendix below). - - "Derivative Works" shall mean any work, whether in Source or Object - form, that is based on (or derived from) the Work and for which the - editorial revisions, annotations, elaborations, or other modifications - represent, as a whole, an original work of authorship. For the purposes - of this License, Derivative Works shall not include works that remain - separable from, or merely link (or bind by name) to the interfaces of, - the Work and Derivative Works thereof. - - "Contribution" shall mean any work of authorship, including - the original version of the Work and any modifications or additions - to that Work or Derivative Works thereof, that is intentionally - submitted to Licensor for inclusion in the Work by the copyright owner - or by an individual or Legal Entity authorized to submit on behalf of - the copyright owner. For the purposes of this definition, "submitted" - means any form of electronic, verbal, or written communication sent - to the Licensor or its representatives, including but not limited to - communication on electronic mailing lists, source code control systems, - and issue tracking systems that are managed by, or on behalf of, the - Licensor for the purpose of discussing and improving the Work, but - excluding communication that is conspicuously marked or otherwise - designated in writing by the copyright owner as "Not a Contribution." - - "Contributor" shall mean Licensor and any individual or Legal Entity - on behalf of whom a Contribution has been received by Licensor and - subsequently incorporated within the Work. - - 2. Grant of Copyright License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - copyright license to reproduce, prepare Derivative Works of, - publicly display, publicly perform, sublicense, and distribute the - Work and such Derivative Works in Source or Object form. - - 3. Grant of Patent License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - (except as stated in this section) patent license to make, have made, - use, offer to sell, sell, import, and otherwise transfer the Work, - where such license applies only to those patent claims licensable - by such Contributor that are necessarily infringed by their - Contribution(s) alone or by combination of their Contribution(s) - with the Work to which such Contribution(s) was submitted. If You - institute patent litigation against any entity (including a - cross-claim or counterclaim in a lawsuit) alleging that the Work - or a Contribution incorporated within the Work constitutes direct - or contributory patent infringement, then any patent licenses - granted to You under this License for that Work shall terminate - as of the date such litigation is filed. - - 4. Redistribution. You may reproduce and distribute copies of the - Work or Derivative Works thereof in any medium, with or without - modifications, and in Source or Object form, provided that You - meet the following conditions: - - (a) You must give any other recipients of the Work or - Derivative Works a copy of this License; and - - (b) You must cause any modified files to carry prominent notices - stating that You changed the files; and - - (c) You must retain, in the Source form of any Derivative Works - that You distribute, all copyright, patent, trademark, and - attribution notices from the Source form of the Work, - excluding those notices that do not pertain to any part of - the Derivative Works; and - - (d) If the Work includes a "NOTICE" text file as part of its - distribution, then any Derivative Works that You distribute must - include a readable copy of the attribution notices contained - within such NOTICE file, excluding those notices that do not - pertain to any part of the Derivative Works, in at least one - of the following places: within a NOTICE text file distributed - as part of the Derivative Works; within the Source form or - documentation, if provided along with the Derivative Works; or, - within a display generated by the Derivative Works, if and - wherever such third-party notices normally appear. The contents - of the NOTICE file are for informational purposes only and - do not modify the License. You may add Your own attribution - notices within Derivative Works that You distribute, alongside - or as an addendum to the NOTICE text from the Work, provided - that such additional attribution notices cannot be construed - as modifying the License. - - You may add Your own copyright statement to Your modifications and - may provide additional or different license terms and conditions - for use, reproduction, or distribution of Your modifications, or - for any such Derivative Works as a whole, provided Your use, - reproduction, and distribution of the Work otherwise complies with - the conditions stated in this License. - - 5. Submission of Contributions. Unless You explicitly state otherwise, - any Contribution intentionally submitted for inclusion in the Work - by You to the Licensor shall be under the terms and conditions of - this License, without any additional terms or conditions. - Notwithstanding the above, nothing herein shall supersede or modify - the terms of any separate license agreement you may have executed - with Licensor regarding such Contributions. - - 6. Trademarks. This License does not grant permission to use the trade - names, trademarks, service marks, or product names of the Licensor, - except as required for reasonable and customary use in describing the - origin of the Work and reproducing the content of the NOTICE file. - - 7. Disclaimer of Warranty. Unless required by applicable law or - agreed to in writing, Licensor provides the Work (and each - Contributor provides its Contributions) on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or - implied, including, without limitation, any warranties or conditions - of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A - PARTICULAR PURPOSE. You are solely responsible for determining the - appropriateness of using or redistributing the Work and assume any - risks associated with Your exercise of permissions under this License. - - 8. Limitation of Liability. In no event and under no legal theory, - whether in tort (including negligence), contract, or otherwise, - unless required by applicable law (such as deliberate and grossly - negligent acts) or agreed to in writing, shall any Contributor be - liable to You for damages, including any direct, indirect, special, - incidental, or consequential damages of any character arising as a - result of this License or out of the use or inability to use the - Work (including but not limited to damages for loss of goodwill, - work stoppage, computer failure or malfunction, or any and all - other commercial damages or losses), even if such Contributor - has been advised of the possibility of such damages. - - 9. Accepting Warranty or Additional Liability. While redistributing - the Work or Derivative Works thereof, You may choose to offer, - and charge a fee for, acceptance of support, warranty, indemnity, - or other liability obligations and/or rights consistent with this - License. However, in accepting such obligations, You may act only - on Your own behalf and on Your sole responsibility, not on behalf - of any other Contributor, and only if You agree to indemnify, - defend, and hold each Contributor harmless for any liability - incurred by, or claims asserted against, such Contributor by reason - of your accepting any such warranty or additional liability. - - END OF TERMS AND CONDITIONS - - APPENDIX: How to apply the Apache License to your work. - - To apply the Apache License to your work, attach the following - boilerplate notice, with the fields enclosed by brackets "[]" - replaced with your own identifying information. (Don't include - the brackets!) The text should be enclosed in the appropriate - comment syntax for the file format. We also recommend that a - file or class name and description of purpose be included on the - same "printed page" as the copyright notice for easier - identification within third-party archives. - - Copyright [yyyy] [name of copyright owner] - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. diff --git a/data/fonts/license-others.txt b/data/fonts/license-others.txt index 7cbff5754..913ce38a8 100644 --- a/data/fonts/license-others.txt +++ b/data/fonts/license-others.txt @@ -2,106 +2,4 @@ The default fonts installed in this directory are freely distributable binary files (either originating from freely distributed packages or distributed as freeware by their authors). Bitmapped typefaces in particular are free under -US and international typeface laws. - - -DISTRIBUTION NOTICES --------------------- -The following notices apply to many of the installed TrueType fonts. Almost -all of these fonts were originally distributed as Postscript fonts and have -been converted to TrueType format for compatibility purposes. - ---- -Red Hat, Inc: Liberation Fonts - -LICENSE AGREEMENT AND LIMITED PRODUCT WARRANTY -LIBERATION FONT SOFTWARE - -This agreement governs the use of the Software and any updates to the -Software, regardless of the delivery mechanism. Subject to the following -terms, Red Hat, Inc. ("Red Hat") grants to the user ("Client") a license to -this work pursuant to the GNU General Public License v.2 with the exceptions -set forth below and such other terms as our set forth in this End User -License Agreement. - - 1.The Software and License Exception. LIBERATION font software (the - "Software") consists of TrueType-OpenType formatted font software for - rendering LIBERATION typefaces in sans serif, serif, and monospaced - character styles. You are licensed to use, modify, copy, and distribute the - Software pursuant to the GNU General Public License v.2 with the following - exceptions: - -(a)As a special exception, if you create a document which uses this font, -and embed this font or unaltered portions of this font into the document, -this font does not by itself cause the resulting document to be covered by -the GNU General Public License. This exception does not however invalidate -any other reasons why the document might be covered by the GNU General -Public License. If you modify this font, you may extend this exception to -your version of the font, but you are not obligated to do so. If you do not -wish to do so, delete this exception statement from your version. - -(b)As a further exception, any distribution of the object code of the -Software in a physical product must provide you the right to access and -modify the source code for the Software and to reinstall that modified -version of the Software in object code form on the same physical product on -which you received it. - - 2.Intellectual Property Rights. The Software and each of its components, - including the source code, documentation, appearance, structure and - organization are owned by Red Hat and others and are protected under - copyright and other laws. Title to the Software and any component, or to - any copy, modification, or merged portion shall remain with the - aforementioned, subject to the applicable license. The "LIBERATION" - trademark is a trademark of Red Hat, Inc. in the U.S. and other countries. - This agreement does not permit Client to distribute modified versions of - the Software using Red Hat's trademarks. If Client makes a redistribution - of a modified version of the Software, then Client must modify the files - names to remove any reference to the Red Hat trademarks and must not use - the Red Hat trademarks in any way to reference or promote the modified - Software. - - 3.Limited Warranty. To the maximum extent permitted under applicable law, - the Software is provided and licensed "as is" without warranty of any kind, - expressed or implied, including the implied warranties of merchantability, - non-infringement or fitness for a particular purpose. Red Hat does not - warrant that the functions contained in the Software will meet Client's - requirements or that the operation of the Software will be entirely error - free or appear precisely as described in the accompanying documentation. - - 4.Limitation of Remedies and Liability. To the maximum extent permitted by - applicable law, Red Hat or any Red Hat authorized dealer will not be liable - to Client for any incidental or consequential damages, including lost - profits or lost savings arising out of the use or inability to use the - Software, even if Red Hat or such dealer has been advised of the - possibility of such damages. - - 5.General. If any provision of this agreement is held to be unenforceable, - that shall not affect the enforceability of the remaining provisions. This - agreement shall be governed by the laws of the State of North Carolina and - of the United States, without regard to any conflict of laws provisions, - except that the United Nations Convention on the International Sale of - Goods shall not apply. - -Copyright © 2007 Red Hat, Inc. All rights reserved. LIBERATION is a -trademark of Red Hat, Inc. - ---- -Adobe Systems Inc: Utopia - -Permission to use, reproduce, display and distribute the listed -typefaces is hereby granted, provided that the Adobe Copyright notice -appears in all whole and partial copies of the software and that the -following trademark symbol and attribution appear in all unmodified -copies of the software: - - Copyright (c) 1989 Adobe Systems Incorporated - Utopia (R) - Utopia is a registered trademark of Adobe Systems Incorporated - -The Adobe typefaces (Type 1 font program, bitmaps and Adobe Font -Metric files) donated are: - - Utopia Regular - Utopia Italic - Utopia Bold - Utopia Bold Italic +US and international typeface laws, and we enforce no rights over these. diff --git a/data/fonts/license-roboto.txt b/data/fonts/license-roboto.txt deleted file mode 100644 index d64569567..000000000 --- a/data/fonts/license-roboto.txt +++ /dev/null @@ -1,202 +0,0 @@ - - Apache License - Version 2.0, January 2004 - http://www.apache.org/licenses/ - - TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION - - 1. Definitions. - - "License" shall mean the terms and conditions for use, reproduction, - and distribution as defined by Sections 1 through 9 of this document. - - "Licensor" shall mean the copyright owner or entity authorized by - the copyright owner that is granting the License. - - "Legal Entity" shall mean the union of the acting entity and all - other entities that control, are controlled by, or are under common - control with that entity. For the purposes of this definition, - "control" means (i) the power, direct or indirect, to cause the - direction or management of such entity, whether by contract or - otherwise, or (ii) ownership of fifty percent (50%) or more of the - outstanding shares, or (iii) beneficial ownership of such entity. - - "You" (or "Your") shall mean an individual or Legal Entity - exercising permissions granted by this License. - - "Source" form shall mean the preferred form for making modifications, - including but not limited to software source code, documentation - source, and configuration files. - - "Object" form shall mean any form resulting from mechanical - transformation or translation of a Source form, including but - not limited to compiled object code, generated documentation, - and conversions to other media types. - - "Work" shall mean the work of authorship, whether in Source or - Object form, made available under the License, as indicated by a - copyright notice that is included in or attached to the work - (an example is provided in the Appendix below). - - "Derivative Works" shall mean any work, whether in Source or Object - form, that is based on (or derived from) the Work and for which the - editorial revisions, annotations, elaborations, or other modifications - represent, as a whole, an original work of authorship. For the purposes - of this License, Derivative Works shall not include works that remain - separable from, or merely link (or bind by name) to the interfaces of, - the Work and Derivative Works thereof. - - "Contribution" shall mean any work of authorship, including - the original version of the Work and any modifications or additions - to that Work or Derivative Works thereof, that is intentionally - submitted to Licensor for inclusion in the Work by the copyright owner - or by an individual or Legal Entity authorized to submit on behalf of - the copyright owner. For the purposes of this definition, "submitted" - means any form of electronic, verbal, or written communication sent - to the Licensor or its representatives, including but not limited to - communication on electronic mailing lists, source code control systems, - and issue tracking systems that are managed by, or on behalf of, the - Licensor for the purpose of discussing and improving the Work, but - excluding communication that is conspicuously marked or otherwise - designated in writing by the copyright owner as "Not a Contribution." - - "Contributor" shall mean Licensor and any individual or Legal Entity - on behalf of whom a Contribution has been received by Licensor and - subsequently incorporated within the Work. - - 2. Grant of Copyright License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - copyright license to reproduce, prepare Derivative Works of, - publicly display, publicly perform, sublicense, and distribute the - Work and such Derivative Works in Source or Object form. - - 3. Grant of Patent License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - (except as stated in this section) patent license to make, have made, - use, offer to sell, sell, import, and otherwise transfer the Work, - where such license applies only to those patent claims licensable - by such Contributor that are necessarily infringed by their - Contribution(s) alone or by combination of their Contribution(s) - with the Work to which such Contribution(s) was submitted. If You - institute patent litigation against any entity (including a - cross-claim or counterclaim in a lawsuit) alleging that the Work - or a Contribution incorporated within the Work constitutes direct - or contributory patent infringement, then any patent licenses - granted to You under this License for that Work shall terminate - as of the date such litigation is filed. - - 4. Redistribution. You may reproduce and distribute copies of the - Work or Derivative Works thereof in any medium, with or without - modifications, and in Source or Object form, provided that You - meet the following conditions: - - (a) You must give any other recipients of the Work or - Derivative Works a copy of this License; and - - (b) You must cause any modified files to carry prominent notices - stating that You changed the files; and - - (c) You must retain, in the Source form of any Derivative Works - that You distribute, all copyright, patent, trademark, and - attribution notices from the Source form of the Work, - excluding those notices that do not pertain to any part of - the Derivative Works; and - - (d) If the Work includes a "NOTICE" text file as part of its - distribution, then any Derivative Works that You distribute must - include a readable copy of the attribution notices contained - within such NOTICE file, excluding those notices that do not - pertain to any part of the Derivative Works, in at least one - of the following places: within a NOTICE text file distributed - as part of the Derivative Works; within the Source form or - documentation, if provided along with the Derivative Works; or, - within a display generated by the Derivative Works, if and - wherever such third-party notices normally appear. The contents - of the NOTICE file are for informational purposes only and - do not modify the License. You may add Your own attribution - notices within Derivative Works that You distribute, alongside - or as an addendum to the NOTICE text from the Work, provided - that such additional attribution notices cannot be construed - as modifying the License. - - You may add Your own copyright statement to Your modifications and - may provide additional or different license terms and conditions - for use, reproduction, or distribution of Your modifications, or - for any such Derivative Works as a whole, provided Your use, - reproduction, and distribution of the Work otherwise complies with - the conditions stated in this License. - - 5. Submission of Contributions. Unless You explicitly state otherwise, - any Contribution intentionally submitted for inclusion in the Work - by You to the Licensor shall be under the terms and conditions of - this License, without any additional terms or conditions. - Notwithstanding the above, nothing herein shall supersede or modify - the terms of any separate license agreement you may have executed - with Licensor regarding such Contributions. - - 6. Trademarks. This License does not grant permission to use the trade - names, trademarks, service marks, or product names of the Licensor, - except as required for reasonable and customary use in describing the - origin of the Work and reproducing the content of the NOTICE file. - - 7. Disclaimer of Warranty. Unless required by applicable law or - agreed to in writing, Licensor provides the Work (and each - Contributor provides its Contributions) on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or - implied, including, without limitation, any warranties or conditions - of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A - PARTICULAR PURPOSE. You are solely responsible for determining the - appropriateness of using or redistributing the Work and assume any - risks associated with Your exercise of permissions under this License. - - 8. Limitation of Liability. In no event and under no legal theory, - whether in tort (including negligence), contract, or otherwise, - unless required by applicable law (such as deliberate and grossly - negligent acts) or agreed to in writing, shall any Contributor be - liable to You for damages, including any direct, indirect, special, - incidental, or consequential damages of any character arising as a - result of this License or out of the use or inability to use the - Work (including but not limited to damages for loss of goodwill, - work stoppage, computer failure or malfunction, or any and all - other commercial damages or losses), even if such Contributor - has been advised of the possibility of such damages. - - 9. Accepting Warranty or Additional Liability. While redistributing - the Work or Derivative Works thereof, You may choose to offer, - and charge a fee for, acceptance of support, warranty, indemnity, - or other liability obligations and/or rights consistent with this - License. However, in accepting such obligations, You may act only - on Your own behalf and on Your sole responsibility, not on behalf - of any other Contributor, and only if You agree to indemnify, - defend, and hold each Contributor harmless for any liability - incurred by, or claims asserted against, such Contributor by reason - of your accepting any such warranty or additional liability. - - END OF TERMS AND CONDITIONS - - APPENDIX: How to apply the Apache License to your work. - - To apply the Apache License to your work, attach the following - boilerplate notice, with the fields enclosed by brackets "[]" - replaced with your own identifying information. (Don't include - the brackets!) The text should be enclosed in the appropriate - comment syntax for the file format. We also recommend that a - file or class name and description of purpose be included on the - same "printed page" as the copyright notice for easier - identification within third-party archives. - - Copyright [yyyy] [name of copyright owner] - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. diff --git a/data/fonts/license-source.txt b/data/fonts/license-sourcecodepro.txt similarity index 97% rename from data/fonts/license-source.txt rename to data/fonts/license-sourcecodepro.txt index 117733042..54da4a42b 100644 --- a/data/fonts/license-source.txt +++ b/data/fonts/license-sourcecodepro.txt @@ -1,93 +1,93 @@ -Copyright 2010, 2012 Adobe Systems Incorporated (http://www.adobe.com/), with Reserved Font Name 'Source'. All Rights Reserved. Source is a trademark of Adobe Systems Incorporated in the United States and/or other countries. - -This Font Software is licensed under the SIL Open Font License, Version 1.1. - -This license is copied below, and is also available with a FAQ at: http://scripts.sil.org/OFL - - ------------------------------------------------------------ -SIL OPEN FONT LICENSE Version 1.1 - 26 February 2007 ------------------------------------------------------------ - -PREAMBLE -The goals of the Open Font License (OFL) are to stimulate worldwide -development of collaborative font projects, to support the font creation -efforts of academic and linguistic communities, and to provide a free and -open framework in which fonts may be shared and improved in partnership -with others. - -The OFL allows the licensed fonts to be used, studied, modified and -redistributed freely as long as they are not sold by themselves. The -fonts, including any derivative works, can be bundled, embedded, -redistributed and/or sold with any software provided that any reserved -names are not used by derivative works. The fonts and derivatives, -however, cannot be released under any other type of license. The -requirement for fonts to remain under this license does not apply -to any document created using the fonts or their derivatives. - -DEFINITIONS -"Font Software" refers to the set of files released by the Copyright -Holder(s) under this license and clearly marked as such. This may -include source files, build scripts and documentation. - -"Reserved Font Name" refers to any names specified as such after the -copyright statement(s). - -"Original Version" refers to the collection of Font Software components as -distributed by the Copyright Holder(s). - -"Modified Version" refers to any derivative made by adding to, deleting, -or substituting -- in part or in whole -- any of the components of the -Original Version, by changing formats or by porting the Font Software to a -new environment. - -"Author" refers to any designer, engineer, programmer, technical -writer or other person who contributed to the Font Software. - -PERMISSION & CONDITIONS -Permission is hereby granted, free of charge, to any person obtaining -a copy of the Font Software, to use, study, copy, merge, embed, modify, -redistribute, and sell modified and unmodified copies of the Font -Software, subject to the following conditions: - -1) Neither the Font Software nor any of its individual components, -in Original or Modified Versions, may be sold by itself. - -2) Original or Modified Versions of the Font Software may be bundled, -redistributed and/or sold with any software, provided that each copy -contains the above copyright notice and this license. These can be -included either as stand-alone text files, human-readable headers or -in the appropriate machine-readable metadata fields within text or -binary files as long as those fields can be easily viewed by the user. - -3) No Modified Version of the Font Software may use the Reserved Font -Name(s) unless explicit written permission is granted by the corresponding -Copyright Holder. This restriction only applies to the primary font name as -presented to the users. - -4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font -Software shall not be used to promote, endorse or advertise any -Modified Version, except to acknowledge the contribution(s) of the -Copyright Holder(s) and the Author(s) or with their explicit written -permission. - -5) The Font Software, modified or unmodified, in part or in whole, -must be distributed entirely under this license, and must not be -distributed under any other license. The requirement for fonts to -remain under this license does not apply to any document created -using the Font Software. - -TERMINATION -This license becomes null and void if any of the above conditions are -not met. - -DISCLAIMER -THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, -EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF -MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT -OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE -COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, -INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL -DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM -OTHER DEALINGS IN THE FONT SOFTWARE. +Copyright 2010, 2012 Adobe Systems Incorporated (http://www.adobe.com/), with Reserved Font Name 'Source'. All Rights Reserved. Source is a trademark of Adobe Systems Incorporated in the United States and/or other countries. + +This Font Software is licensed under the SIL Open Font License, Version 1.1. +This license is copied below, and is also available with a FAQ at: +https://openfontlicense.org + + +----------------------------------------------------------- +SIL OPEN FONT LICENSE Version 1.1 - 26 February 2007 +----------------------------------------------------------- + +PREAMBLE +The goals of the Open Font License (OFL) are to stimulate worldwide +development of collaborative font projects, to support the font creation +efforts of academic and linguistic communities, and to provide a free and +open framework in which fonts may be shared and improved in partnership +with others. + +The OFL allows the licensed fonts to be used, studied, modified and +redistributed freely as long as they are not sold by themselves. The +fonts, including any derivative works, can be bundled, embedded, +redistributed and/or sold with any software provided that any reserved +names are not used by derivative works. The fonts and derivatives, +however, cannot be released under any other type of license. The +requirement for fonts to remain under this license does not apply +to any document created using the fonts or their derivatives. + +DEFINITIONS +"Font Software" refers to the set of files released by the Copyright +Holder(s) under this license and clearly marked as such. This may +include source files, build scripts and documentation. + +"Reserved Font Name" refers to any names specified as such after the +copyright statement(s). + +"Original Version" refers to the collection of Font Software components as +distributed by the Copyright Holder(s). + +"Modified Version" refers to any derivative made by adding to, deleting, +or substituting -- in part or in whole -- any of the components of the +Original Version, by changing formats or by porting the Font Software to a +new environment. + +"Author" refers to any designer, engineer, programmer, technical +writer or other person who contributed to the Font Software. + +PERMISSION & CONDITIONS +Permission is hereby granted, free of charge, to any person obtaining +a copy of the Font Software, to use, study, copy, merge, embed, modify, +redistribute, and sell modified and unmodified copies of the Font +Software, subject to the following conditions: + +1) Neither the Font Software nor any of its individual components, +in Original or Modified Versions, may be sold by itself. + +2) Original or Modified Versions of the Font Software may be bundled, +redistributed and/or sold with any software, provided that each copy +contains the above copyright notice and this license. These can be +included either as stand-alone text files, human-readable headers or +in the appropriate machine-readable metadata fields within text or +binary files as long as those fields can be easily viewed by the user. + +3) No Modified Version of the Font Software may use the Reserved Font +Name(s) unless explicit written permission is granted by the corresponding +Copyright Holder. This restriction only applies to the primary font name as +presented to the users. + +4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font +Software shall not be used to promote, endorse or advertise any +Modified Version, except to acknowledge the contribution(s) of the +Copyright Holder(s) and the Author(s) or with their explicit written +permission. + +5) The Font Software, modified or unmodified, in part or in whole, +must be distributed entirely under this license, and must not be +distributed under any other license. The requirement for fonts to +remain under this license does not apply to any document created +using the Font Software. + +TERMINATION +This license becomes null and void if any of the above conditions are +not met. + +DISCLAIMER +THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT +OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE +COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL +DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM +OTHER DEALINGS IN THE FONT SOFTWARE. diff --git a/data/fonts/license-sourcesans3.txt b/data/fonts/license-sourcesans3.txt new file mode 100644 index 000000000..2f7468b2b --- /dev/null +++ b/data/fonts/license-sourcesans3.txt @@ -0,0 +1,93 @@ +Copyright 2010-2020 Adobe (http://www.adobe.com/), with Reserved Font Name 'Source'. All Rights Reserved. Source is a trademark of Adobe in the United States and/or other countries. + +This Font Software is licensed under the SIL Open Font License, Version 1.1. +This license is copied below, and is also available with a FAQ at: +https://openfontlicense.org + + +----------------------------------------------------------- +SIL OPEN FONT LICENSE Version 1.1 - 26 February 2007 +----------------------------------------------------------- + +PREAMBLE +The goals of the Open Font License (OFL) are to stimulate worldwide +development of collaborative font projects, to support the font creation +efforts of academic and linguistic communities, and to provide a free and +open framework in which fonts may be shared and improved in partnership +with others. + +The OFL allows the licensed fonts to be used, studied, modified and +redistributed freely as long as they are not sold by themselves. The +fonts, including any derivative works, can be bundled, embedded, +redistributed and/or sold with any software provided that any reserved +names are not used by derivative works. The fonts and derivatives, +however, cannot be released under any other type of license. The +requirement for fonts to remain under this license does not apply +to any document created using the fonts or their derivatives. + +DEFINITIONS +"Font Software" refers to the set of files released by the Copyright +Holder(s) under this license and clearly marked as such. This may +include source files, build scripts and documentation. + +"Reserved Font Name" refers to any names specified as such after the +copyright statement(s). + +"Original Version" refers to the collection of Font Software components as +distributed by the Copyright Holder(s). + +"Modified Version" refers to any derivative made by adding to, deleting, +or substituting -- in part or in whole -- any of the components of the +Original Version, by changing formats or by porting the Font Software to a +new environment. + +"Author" refers to any designer, engineer, programmer, technical +writer or other person who contributed to the Font Software. + +PERMISSION & CONDITIONS +Permission is hereby granted, free of charge, to any person obtaining +a copy of the Font Software, to use, study, copy, merge, embed, modify, +redistribute, and sell modified and unmodified copies of the Font +Software, subject to the following conditions: + +1) Neither the Font Software nor any of its individual components, +in Original or Modified Versions, may be sold by itself. + +2) Original or Modified Versions of the Font Software may be bundled, +redistributed and/or sold with any software, provided that each copy +contains the above copyright notice and this license. These can be +included either as stand-alone text files, human-readable headers or +in the appropriate machine-readable metadata fields within text or +binary files as long as those fields can be easily viewed by the user. + +3) No Modified Version of the Font Software may use the Reserved Font +Name(s) unless explicit written permission is granted by the corresponding +Copyright Holder. This restriction only applies to the primary font name as +presented to the users. + +4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font +Software shall not be used to promote, endorse or advertise any +Modified Version, except to acknowledge the contribution(s) of the +Copyright Holder(s) and the Author(s) or with their explicit written +permission. + +5) The Font Software, modified or unmodified, in part or in whole, +must be distributed entirely under this license, and must not be +distributed under any other license. The requirement for fonts to +remain under this license does not apply to any document created +using the Font Software. + +TERMINATION +This license becomes null and void if any of the above conditions are +not met. + +DISCLAIMER +THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT +OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE +COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL +DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM +OTHER DEALINGS IN THE FONT SOFTWARE. diff --git a/data/fonts/license-vollkorn.txt b/data/fonts/license-vollkorn.txt new file mode 100644 index 000000000..f72bad11b --- /dev/null +++ b/data/fonts/license-vollkorn.txt @@ -0,0 +1,93 @@ +Copyright 2017 The Vollkorn Project Authors (https://github.com/FAlthausen/Vollkorn-Typeface) + +This Font Software is licensed under the SIL Open Font License, Version 1.1. +This license is copied below, and is also available with a FAQ at: +https://openfontlicense.org + + +----------------------------------------------------------- +SIL OPEN FONT LICENSE Version 1.1 - 26 February 2007 +----------------------------------------------------------- + +PREAMBLE +The goals of the Open Font License (OFL) are to stimulate worldwide +development of collaborative font projects, to support the font creation +efforts of academic and linguistic communities, and to provide a free and +open framework in which fonts may be shared and improved in partnership +with others. + +The OFL allows the licensed fonts to be used, studied, modified and +redistributed freely as long as they are not sold by themselves. The +fonts, including any derivative works, can be bundled, embedded, +redistributed and/or sold with any software provided that any reserved +names are not used by derivative works. The fonts and derivatives, +however, cannot be released under any other type of license. The +requirement for fonts to remain under this license does not apply +to any document created using the fonts or their derivatives. + +DEFINITIONS +"Font Software" refers to the set of files released by the Copyright +Holder(s) under this license and clearly marked as such. This may +include source files, build scripts and documentation. + +"Reserved Font Name" refers to any names specified as such after the +copyright statement(s). + +"Original Version" refers to the collection of Font Software components as +distributed by the Copyright Holder(s). + +"Modified Version" refers to any derivative made by adding to, deleting, +or substituting -- in part or in whole -- any of the components of the +Original Version, by changing formats or by porting the Font Software to a +new environment. + +"Author" refers to any designer, engineer, programmer, technical +writer or other person who contributed to the Font Software. + +PERMISSION & CONDITIONS +Permission is hereby granted, free of charge, to any person obtaining +a copy of the Font Software, to use, study, copy, merge, embed, modify, +redistribute, and sell modified and unmodified copies of the Font +Software, subject to the following conditions: + +1) Neither the Font Software nor any of its individual components, +in Original or Modified Versions, may be sold by itself. + +2) Original or Modified Versions of the Font Software may be bundled, +redistributed and/or sold with any software, provided that each copy +contains the above copyright notice and this license. These can be +included either as stand-alone text files, human-readable headers or +in the appropriate machine-readable metadata fields within text or +binary files as long as those fields can be easily viewed by the user. + +3) No Modified Version of the Font Software may use the Reserved Font +Name(s) unless explicit written permission is granted by the corresponding +Copyright Holder. This restriction only applies to the primary font name as +presented to the users. + +4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font +Software shall not be used to promote, endorse or advertise any +Modified Version, except to acknowledge the contribution(s) of the +Copyright Holder(s) and the Author(s) or with their explicit written +permission. + +5) The Font Software, modified or unmodified, in part or in whole, +must be distributed entirely under this license, and must not be +distributed under any other license. The requirement for fonts to +remain under this license does not apply to any document created +using the Font Software. + +TERMINATION +This license becomes null and void if any of the above conditions are +not met. + +DISCLAIMER +THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT +OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE +COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL +DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM +OTHER DEALINGS IN THE FONT SOFTWARE. diff --git a/data/fonts/options.cfg b/data/fonts/options.cfg new file mode 100644 index 000000000..96ce7266d --- /dev/null +++ b/data/fonts/options.cfg @@ -0,0 +1,39 @@ +# Font options in this file will add/overwrite values in fonts.cfg, which is machine generated. +# The fonts.cfg file can be refreshed by deleting it, then running any program that uses the Parasol UI. +# +# Hinting options for scalable fonts are as follows. Please pay close attention to kerning results when adjusting the +# hinting of a font. +# +# Normal: The hinting information provided by the font should be given preference. +# Internal: The Freetype hinter should be used and font specific hinting can be ignored (generally not recommended). +# Light: The light version of the Freetype hinter should be used (apply internal hinting on the Y axis only). + +[Courier] +Name = Courier +Alias = Courier Prime +Hidden = Yes + +[Crimson Pro] +Hinting = Normal + +[Noto Sans] +Hinting = Light +Default = Yes + +[Vollkorn] +Hinting = Normal + +[Noto Color Emoji] +Hidden = Yes + +[Source Sans 3] +Hidden = Yes + +[Source Sans Pro] +Name = Source Sans Pro +Alias = Source Sans 3 + +[Times New Roman] +Name = Times New Roman +Alias = Crimson Pro +Hidden = Yes diff --git a/data/fonts/truetype/Courier Prime Bold Italic.ttf b/data/fonts/truetype/Courier Prime Bold Italic.ttf index d4e71869d..2e70ab7e0 100644 Binary files a/data/fonts/truetype/Courier Prime Bold Italic.ttf and b/data/fonts/truetype/Courier Prime Bold Italic.ttf differ diff --git a/data/fonts/truetype/Courier Prime Bold.ttf b/data/fonts/truetype/Courier Prime Bold.ttf index 1b0888c2e..7e6b22280 100644 Binary files a/data/fonts/truetype/Courier Prime Bold.ttf and b/data/fonts/truetype/Courier Prime Bold.ttf differ diff --git a/data/fonts/truetype/Courier Prime Italic.ttf b/data/fonts/truetype/Courier Prime Italic.ttf index 75a1343d7..15d9463c7 100644 Binary files a/data/fonts/truetype/Courier Prime Italic.ttf and b/data/fonts/truetype/Courier Prime Italic.ttf differ diff --git a/data/fonts/truetype/Courier Prime Sans Bold Italic.ttf b/data/fonts/truetype/Courier Prime Sans Bold Italic.ttf deleted file mode 100644 index fb69098cc..000000000 Binary files a/data/fonts/truetype/Courier Prime Sans Bold Italic.ttf and /dev/null differ diff --git a/data/fonts/truetype/Courier Prime Sans Bold.ttf b/data/fonts/truetype/Courier Prime Sans Bold.ttf deleted file mode 100644 index 76d2dfc24..000000000 Binary files a/data/fonts/truetype/Courier Prime Sans Bold.ttf and /dev/null differ diff --git a/data/fonts/truetype/Courier Prime Sans Italic.ttf b/data/fonts/truetype/Courier Prime Sans Italic.ttf deleted file mode 100644 index 93a7e70cd..000000000 Binary files a/data/fonts/truetype/Courier Prime Sans Italic.ttf and /dev/null differ diff --git a/data/fonts/truetype/Courier Prime Sans.ttf b/data/fonts/truetype/Courier Prime Sans.ttf deleted file mode 100644 index 32e795ab1..000000000 Binary files a/data/fonts/truetype/Courier Prime Sans.ttf and /dev/null differ diff --git a/data/fonts/truetype/Courier Prime.ttf b/data/fonts/truetype/Courier Prime.ttf index db4e6c14c..4af1ff54c 100644 Binary files a/data/fonts/truetype/Courier Prime.ttf and b/data/fonts/truetype/Courier Prime.ttf differ diff --git a/data/fonts/truetype/CrimsonPro-Italic-VariableFont.ttf b/data/fonts/truetype/CrimsonPro-Italic-VariableFont.ttf new file mode 100644 index 000000000..5c84bb6f2 Binary files /dev/null and b/data/fonts/truetype/CrimsonPro-Italic-VariableFont.ttf differ diff --git a/data/fonts/truetype/CrimsonPro-VariableFont.ttf b/data/fonts/truetype/CrimsonPro-VariableFont.ttf new file mode 100644 index 000000000..1b3935fe9 Binary files /dev/null and b/data/fonts/truetype/CrimsonPro-VariableFont.ttf differ diff --git a/data/fonts/truetype/Inconsolata-Bold.ttf b/data/fonts/truetype/Inconsolata-Bold.ttf deleted file mode 100644 index 035d57951..000000000 Binary files a/data/fonts/truetype/Inconsolata-Bold.ttf and /dev/null differ diff --git a/data/fonts/truetype/Inconsolata-Regular.ttf b/data/fonts/truetype/Inconsolata-Regular.ttf deleted file mode 100644 index bbc964755..000000000 Binary files a/data/fonts/truetype/Inconsolata-Regular.ttf and /dev/null differ diff --git a/data/fonts/truetype/Inconsolata-VariableFont.ttf b/data/fonts/truetype/Inconsolata-VariableFont.ttf new file mode 100644 index 000000000..95ad7181c Binary files /dev/null and b/data/fonts/truetype/Inconsolata-VariableFont.ttf differ diff --git a/data/fonts/truetype/LiberationMono-Bold.ttf b/data/fonts/truetype/LiberationMono-Bold.ttf deleted file mode 100644 index 15b7819bd..000000000 Binary files a/data/fonts/truetype/LiberationMono-Bold.ttf and /dev/null differ diff --git a/data/fonts/truetype/LiberationMono-BoldItalic.ttf b/data/fonts/truetype/LiberationMono-BoldItalic.ttf deleted file mode 100644 index 4c54e2d0e..000000000 Binary files a/data/fonts/truetype/LiberationMono-BoldItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/LiberationMono-Italic.ttf b/data/fonts/truetype/LiberationMono-Italic.ttf deleted file mode 100644 index 75ae2a941..000000000 Binary files a/data/fonts/truetype/LiberationMono-Italic.ttf and /dev/null differ diff --git a/data/fonts/truetype/LiberationMono-Regular.ttf b/data/fonts/truetype/LiberationMono-Regular.ttf deleted file mode 100644 index c3a9c0875..000000000 Binary files a/data/fonts/truetype/LiberationMono-Regular.ttf and /dev/null differ diff --git a/data/fonts/truetype/LiberationSans-Bold.ttf b/data/fonts/truetype/LiberationSans-Bold.ttf deleted file mode 100644 index dd584c2e0..000000000 Binary files a/data/fonts/truetype/LiberationSans-Bold.ttf and /dev/null differ diff --git a/data/fonts/truetype/LiberationSans-BoldItalic.ttf b/data/fonts/truetype/LiberationSans-BoldItalic.ttf deleted file mode 100644 index 528f3fc9e..000000000 Binary files a/data/fonts/truetype/LiberationSans-BoldItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/LiberationSans-Italic.ttf b/data/fonts/truetype/LiberationSans-Italic.ttf deleted file mode 100644 index a02f876ba..000000000 Binary files a/data/fonts/truetype/LiberationSans-Italic.ttf and /dev/null differ diff --git a/data/fonts/truetype/LiberationSans-Regular.ttf b/data/fonts/truetype/LiberationSans-Regular.ttf deleted file mode 100644 index f1466ec87..000000000 Binary files a/data/fonts/truetype/LiberationSans-Regular.ttf and /dev/null differ diff --git a/data/fonts/truetype/LiberationSerif-Bold.ttf b/data/fonts/truetype/LiberationSerif-Bold.ttf deleted file mode 100644 index 44ecc2320..000000000 Binary files a/data/fonts/truetype/LiberationSerif-Bold.ttf and /dev/null differ diff --git a/data/fonts/truetype/LiberationSerif-BoldItalic.ttf b/data/fonts/truetype/LiberationSerif-BoldItalic.ttf deleted file mode 100644 index 39a437736..000000000 Binary files a/data/fonts/truetype/LiberationSerif-BoldItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/LiberationSerif-Italic.ttf b/data/fonts/truetype/LiberationSerif-Italic.ttf deleted file mode 100644 index e9a21d6d5..000000000 Binary files a/data/fonts/truetype/LiberationSerif-Italic.ttf and /dev/null differ diff --git a/data/fonts/truetype/LiberationSerif-Regular.ttf b/data/fonts/truetype/LiberationSerif-Regular.ttf deleted file mode 100644 index b9dd19bdb..000000000 Binary files a/data/fonts/truetype/LiberationSerif-Regular.ttf and /dev/null differ diff --git a/data/fonts/truetype/NotoSans-Italic-VariableFont.ttf b/data/fonts/truetype/NotoSans-Italic-VariableFont.ttf new file mode 100644 index 000000000..4e962ee86 Binary files /dev/null and b/data/fonts/truetype/NotoSans-Italic-VariableFont.ttf differ diff --git a/data/fonts/truetype/NotoSans-VariableFont.ttf b/data/fonts/truetype/NotoSans-VariableFont.ttf new file mode 100644 index 000000000..f7d0d78ed Binary files /dev/null and b/data/fonts/truetype/NotoSans-VariableFont.ttf differ diff --git a/data/fonts/truetype/OpenSans-Bold.ttf b/data/fonts/truetype/OpenSans-Bold.ttf deleted file mode 100644 index fd79d43be..000000000 Binary files a/data/fonts/truetype/OpenSans-Bold.ttf and /dev/null differ diff --git a/data/fonts/truetype/OpenSans-BoldItalic.ttf b/data/fonts/truetype/OpenSans-BoldItalic.ttf deleted file mode 100644 index 9bc800958..000000000 Binary files a/data/fonts/truetype/OpenSans-BoldItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/OpenSans-ExtraBold.ttf b/data/fonts/truetype/OpenSans-ExtraBold.ttf deleted file mode 100644 index 21f6f84a0..000000000 Binary files a/data/fonts/truetype/OpenSans-ExtraBold.ttf and /dev/null differ diff --git a/data/fonts/truetype/OpenSans-ExtraBoldItalic.ttf b/data/fonts/truetype/OpenSans-ExtraBoldItalic.ttf deleted file mode 100644 index 31cb68834..000000000 Binary files a/data/fonts/truetype/OpenSans-ExtraBoldItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/OpenSans-Italic.ttf b/data/fonts/truetype/OpenSans-Italic.ttf deleted file mode 100644 index c90da48ff..000000000 Binary files a/data/fonts/truetype/OpenSans-Italic.ttf and /dev/null differ diff --git a/data/fonts/truetype/OpenSans-Light.ttf b/data/fonts/truetype/OpenSans-Light.ttf deleted file mode 100644 index 0d381897d..000000000 Binary files a/data/fonts/truetype/OpenSans-Light.ttf and /dev/null differ diff --git a/data/fonts/truetype/OpenSans-LightItalic.ttf b/data/fonts/truetype/OpenSans-LightItalic.ttf deleted file mode 100644 index 68299c4bc..000000000 Binary files a/data/fonts/truetype/OpenSans-LightItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/OpenSans-Regular.ttf b/data/fonts/truetype/OpenSans-Regular.ttf deleted file mode 100644 index db433349b..000000000 Binary files a/data/fonts/truetype/OpenSans-Regular.ttf and /dev/null differ diff --git a/data/fonts/truetype/OpenSans-Semibold.ttf b/data/fonts/truetype/OpenSans-Semibold.ttf deleted file mode 100644 index 1a7679e39..000000000 Binary files a/data/fonts/truetype/OpenSans-Semibold.ttf and /dev/null differ diff --git a/data/fonts/truetype/OpenSans-SemiboldItalic.ttf b/data/fonts/truetype/OpenSans-SemiboldItalic.ttf deleted file mode 100644 index 59b6d16b0..000000000 Binary files a/data/fonts/truetype/OpenSans-SemiboldItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/Roboto-Black.ttf b/data/fonts/truetype/Roboto-Black.ttf deleted file mode 100644 index fbde625d4..000000000 Binary files a/data/fonts/truetype/Roboto-Black.ttf and /dev/null differ diff --git a/data/fonts/truetype/Roboto-BlackItalic.ttf b/data/fonts/truetype/Roboto-BlackItalic.ttf deleted file mode 100644 index 60f7782a2..000000000 Binary files a/data/fonts/truetype/Roboto-BlackItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/Roboto-Bold.ttf b/data/fonts/truetype/Roboto-Bold.ttf deleted file mode 100644 index a355c27cd..000000000 Binary files a/data/fonts/truetype/Roboto-Bold.ttf and /dev/null differ diff --git a/data/fonts/truetype/Roboto-BoldItalic.ttf b/data/fonts/truetype/Roboto-BoldItalic.ttf deleted file mode 100644 index 3c9a7a373..000000000 Binary files a/data/fonts/truetype/Roboto-BoldItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/Roboto-Italic.ttf b/data/fonts/truetype/Roboto-Italic.ttf deleted file mode 100644 index ff6046d5b..000000000 Binary files a/data/fonts/truetype/Roboto-Italic.ttf and /dev/null differ diff --git a/data/fonts/truetype/Roboto-Light.ttf b/data/fonts/truetype/Roboto-Light.ttf deleted file mode 100644 index 94c6bcc67..000000000 Binary files a/data/fonts/truetype/Roboto-Light.ttf and /dev/null differ diff --git a/data/fonts/truetype/Roboto-LightItalic.ttf b/data/fonts/truetype/Roboto-LightItalic.ttf deleted file mode 100644 index 04cc00230..000000000 Binary files a/data/fonts/truetype/Roboto-LightItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/Roboto-Medium.ttf b/data/fonts/truetype/Roboto-Medium.ttf deleted file mode 100644 index 39c63d746..000000000 Binary files a/data/fonts/truetype/Roboto-Medium.ttf and /dev/null differ diff --git a/data/fonts/truetype/Roboto-MediumItalic.ttf b/data/fonts/truetype/Roboto-MediumItalic.ttf deleted file mode 100644 index dc743f0a6..000000000 Binary files a/data/fonts/truetype/Roboto-MediumItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/Roboto-Regular.ttf b/data/fonts/truetype/Roboto-Regular.ttf deleted file mode 100644 index 8c082c8de..000000000 Binary files a/data/fonts/truetype/Roboto-Regular.ttf and /dev/null differ diff --git a/data/fonts/truetype/Roboto-Thin.ttf b/data/fonts/truetype/Roboto-Thin.ttf deleted file mode 100644 index d69555029..000000000 Binary files a/data/fonts/truetype/Roboto-Thin.ttf and /dev/null differ diff --git a/data/fonts/truetype/Roboto-ThinItalic.ttf b/data/fonts/truetype/Roboto-ThinItalic.ttf deleted file mode 100644 index 07172ff66..000000000 Binary files a/data/fonts/truetype/Roboto-ThinItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/RobotoCondensed-Bold.ttf b/data/fonts/truetype/RobotoCondensed-Bold.ttf deleted file mode 100644 index 48dd63534..000000000 Binary files a/data/fonts/truetype/RobotoCondensed-Bold.ttf and /dev/null differ diff --git a/data/fonts/truetype/RobotoCondensed-BoldItalic.ttf b/data/fonts/truetype/RobotoCondensed-BoldItalic.ttf deleted file mode 100644 index ad728646a..000000000 Binary files a/data/fonts/truetype/RobotoCondensed-BoldItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/RobotoCondensed-Italic.ttf b/data/fonts/truetype/RobotoCondensed-Italic.ttf deleted file mode 100644 index a232513d5..000000000 Binary files a/data/fonts/truetype/RobotoCondensed-Italic.ttf and /dev/null differ diff --git a/data/fonts/truetype/RobotoCondensed-Light.ttf b/data/fonts/truetype/RobotoCondensed-Light.ttf deleted file mode 100644 index a6e368d40..000000000 Binary files a/data/fonts/truetype/RobotoCondensed-Light.ttf and /dev/null differ diff --git a/data/fonts/truetype/RobotoCondensed-LightItalic.ttf b/data/fonts/truetype/RobotoCondensed-LightItalic.ttf deleted file mode 100644 index 5b2b6ae08..000000000 Binary files a/data/fonts/truetype/RobotoCondensed-LightItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/RobotoCondensed-Regular.ttf b/data/fonts/truetype/RobotoCondensed-Regular.ttf deleted file mode 100644 index 65bf32a19..000000000 Binary files a/data/fonts/truetype/RobotoCondensed-Regular.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceCodePro-Black.ttf b/data/fonts/truetype/SourceCodePro-Black.ttf deleted file mode 100644 index ea73e60ee..000000000 Binary files a/data/fonts/truetype/SourceCodePro-Black.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceCodePro-Bold.ttf b/data/fonts/truetype/SourceCodePro-Bold.ttf deleted file mode 100644 index a56f1fa5d..000000000 Binary files a/data/fonts/truetype/SourceCodePro-Bold.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceCodePro-ExtraLight.ttf b/data/fonts/truetype/SourceCodePro-ExtraLight.ttf deleted file mode 100644 index f409b711f..000000000 Binary files a/data/fonts/truetype/SourceCodePro-ExtraLight.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceCodePro-Italic-VariableFont.ttf b/data/fonts/truetype/SourceCodePro-Italic-VariableFont.ttf new file mode 100644 index 000000000..d3678bc35 Binary files /dev/null and b/data/fonts/truetype/SourceCodePro-Italic-VariableFont.ttf differ diff --git a/data/fonts/truetype/SourceCodePro-Light.ttf b/data/fonts/truetype/SourceCodePro-Light.ttf deleted file mode 100644 index 51eb9630f..000000000 Binary files a/data/fonts/truetype/SourceCodePro-Light.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceCodePro-Medium.ttf b/data/fonts/truetype/SourceCodePro-Medium.ttf deleted file mode 100644 index 1ee45ebd5..000000000 Binary files a/data/fonts/truetype/SourceCodePro-Medium.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceCodePro-Regular.ttf b/data/fonts/truetype/SourceCodePro-Regular.ttf deleted file mode 100644 index b2cff928e..000000000 Binary files a/data/fonts/truetype/SourceCodePro-Regular.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceCodePro-Semibold.ttf b/data/fonts/truetype/SourceCodePro-Semibold.ttf deleted file mode 100644 index b425f9cee..000000000 Binary files a/data/fonts/truetype/SourceCodePro-Semibold.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceCodePro-VariableFont.ttf b/data/fonts/truetype/SourceCodePro-VariableFont.ttf new file mode 100644 index 000000000..19bb67127 Binary files /dev/null and b/data/fonts/truetype/SourceCodePro-VariableFont.ttf differ diff --git a/data/fonts/truetype/SourceSans3-Italic-VariableFont.ttf b/data/fonts/truetype/SourceSans3-Italic-VariableFont.ttf new file mode 100644 index 000000000..660ac45f2 Binary files /dev/null and b/data/fonts/truetype/SourceSans3-Italic-VariableFont.ttf differ diff --git a/data/fonts/truetype/SourceSans3-VariableFont.ttf b/data/fonts/truetype/SourceSans3-VariableFont.ttf new file mode 100644 index 000000000..8c15d261a Binary files /dev/null and b/data/fonts/truetype/SourceSans3-VariableFont.ttf differ diff --git a/data/fonts/truetype/SourceSansPro-Black.ttf b/data/fonts/truetype/SourceSansPro-Black.ttf deleted file mode 100644 index cb89a2d17..000000000 Binary files a/data/fonts/truetype/SourceSansPro-Black.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceSansPro-BlackItalic.ttf b/data/fonts/truetype/SourceSansPro-BlackItalic.ttf deleted file mode 100644 index c719243c0..000000000 Binary files a/data/fonts/truetype/SourceSansPro-BlackItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceSansPro-Bold.ttf b/data/fonts/truetype/SourceSansPro-Bold.ttf deleted file mode 100644 index 50d81bdad..000000000 Binary files a/data/fonts/truetype/SourceSansPro-Bold.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceSansPro-BoldItalic.ttf b/data/fonts/truetype/SourceSansPro-BoldItalic.ttf deleted file mode 100644 index d20dd0c5e..000000000 Binary files a/data/fonts/truetype/SourceSansPro-BoldItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceSansPro-ExtraLight.ttf b/data/fonts/truetype/SourceSansPro-ExtraLight.ttf deleted file mode 100644 index bb4176c6f..000000000 Binary files a/data/fonts/truetype/SourceSansPro-ExtraLight.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceSansPro-ExtraLightItalic.ttf b/data/fonts/truetype/SourceSansPro-ExtraLightItalic.ttf deleted file mode 100644 index 2c34f3b8d..000000000 Binary files a/data/fonts/truetype/SourceSansPro-ExtraLightItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceSansPro-Italic.ttf b/data/fonts/truetype/SourceSansPro-Italic.ttf deleted file mode 100644 index e5a1a86e6..000000000 Binary files a/data/fonts/truetype/SourceSansPro-Italic.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceSansPro-Light.ttf b/data/fonts/truetype/SourceSansPro-Light.ttf deleted file mode 100644 index 5f64679f6..000000000 Binary files a/data/fonts/truetype/SourceSansPro-Light.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceSansPro-LightItalic.ttf b/data/fonts/truetype/SourceSansPro-LightItalic.ttf deleted file mode 100644 index 88a6778d2..000000000 Binary files a/data/fonts/truetype/SourceSansPro-LightItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceSansPro-Regular.ttf b/data/fonts/truetype/SourceSansPro-Regular.ttf deleted file mode 100644 index 91e9ea575..000000000 Binary files a/data/fonts/truetype/SourceSansPro-Regular.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceSansPro-Semibold.ttf b/data/fonts/truetype/SourceSansPro-Semibold.ttf deleted file mode 100644 index 502059482..000000000 Binary files a/data/fonts/truetype/SourceSansPro-Semibold.ttf and /dev/null differ diff --git a/data/fonts/truetype/SourceSansPro-SemiboldItalic.ttf b/data/fonts/truetype/SourceSansPro-SemiboldItalic.ttf deleted file mode 100644 index 2c5ad3008..000000000 Binary files a/data/fonts/truetype/SourceSansPro-SemiboldItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/Utopia-Bold.ttf b/data/fonts/truetype/Utopia-Bold.ttf deleted file mode 100644 index 32e1f1e7f..000000000 Binary files a/data/fonts/truetype/Utopia-Bold.ttf and /dev/null differ diff --git a/data/fonts/truetype/Utopia-BoldItalic.ttf b/data/fonts/truetype/Utopia-BoldItalic.ttf deleted file mode 100644 index ecde01efb..000000000 Binary files a/data/fonts/truetype/Utopia-BoldItalic.ttf and /dev/null differ diff --git a/data/fonts/truetype/Utopia-Italic.ttf b/data/fonts/truetype/Utopia-Italic.ttf deleted file mode 100644 index 27aa2d3b0..000000000 Binary files a/data/fonts/truetype/Utopia-Italic.ttf and /dev/null differ diff --git a/data/fonts/truetype/Utopia.ttf b/data/fonts/truetype/Utopia.ttf deleted file mode 100644 index 8ae9bd327..000000000 Binary files a/data/fonts/truetype/Utopia.ttf and /dev/null differ diff --git a/data/fonts/truetype/Vollkorn-Italic-VariableFont.ttf b/data/fonts/truetype/Vollkorn-Italic-VariableFont.ttf new file mode 100644 index 000000000..80b2cdc28 Binary files /dev/null and b/data/fonts/truetype/Vollkorn-Italic-VariableFont.ttf differ diff --git a/data/fonts/truetype/Vollkorn-VariableFont.ttf b/data/fonts/truetype/Vollkorn-VariableFont.ttf new file mode 100644 index 000000000..188fd06f5 Binary files /dev/null and b/data/fonts/truetype/Vollkorn-VariableFont.ttf differ diff --git a/data/icons/Default/arrows/arrow_down.svg b/data/icons/Default/arrows/arrow_down.svg index 93c29cadc..f9fae796e 100644 --- a/data/icons/Default/arrows/arrow_down.svg +++ b/data/icons/Default/arrows/arrow_down.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/arrows/arrow_left.svg b/data/icons/Default/arrows/arrow_left.svg index 02eca778b..f442a43bb 100644 --- a/data/icons/Default/arrows/arrow_left.svg +++ b/data/icons/Default/arrows/arrow_left.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/arrows/arrow_right.svg b/data/icons/Default/arrows/arrow_right.svg index 5519e533b..091b54aff 100644 --- a/data/icons/Default/arrows/arrow_right.svg +++ b/data/icons/Default/arrows/arrow_right.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/arrows/arrow_up.svg b/data/icons/Default/arrows/arrow_up.svg index f25b51f63..4e9b53ca3 100644 --- a/data/icons/Default/arrows/arrow_up.svg +++ b/data/icons/Default/arrows/arrow_up.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/arrows/corner_up_right.svg b/data/icons/Default/arrows/corner_up_right.svg index 0ff8d182e..2aafa87cd 100644 --- a/data/icons/Default/arrows/corner_up_right.svg +++ b/data/icons/Default/arrows/corner_up_right.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/arrows/down.svg b/data/icons/Default/arrows/down.svg index 3c4cbceb9..7a8ef705b 100644 --- a/data/icons/Default/arrows/down.svg +++ b/data/icons/Default/arrows/down.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/arrows/left.svg b/data/icons/Default/arrows/left.svg index 8f3c17306..77d22455b 100644 --- a/data/icons/Default/arrows/left.svg +++ b/data/icons/Default/arrows/left.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/arrows/left_right.svg b/data/icons/Default/arrows/left_right.svg index a9b92b113..edf0f998e 100644 --- a/data/icons/Default/arrows/left_right.svg +++ b/data/icons/Default/arrows/left_right.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/arrows/right.svg b/data/icons/Default/arrows/right.svg index b5a7f2ebf..a2027b75e 100644 --- a/data/icons/Default/arrows/right.svg +++ b/data/icons/Default/arrows/right.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/arrows/up.svg b/data/icons/Default/arrows/up.svg index bccd6e96c..1bab64bdc 100644 --- a/data/icons/Default/arrows/up.svg +++ b/data/icons/Default/arrows/up.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/arrows/up_down.svg b/data/icons/Default/arrows/up_down.svg index f011fc808..8c03ff533 100644 --- a/data/icons/Default/arrows/up_down.svg +++ b/data/icons/Default/arrows/up_down.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/border/all.svg b/data/icons/Default/border/all.svg index b5e6a09d8..810276496 100644 --- a/data/icons/Default/border/all.svg +++ b/data/icons/Default/border/all.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/border/bottom.svg b/data/icons/Default/border/bottom.svg index 340e12c2f..83a4e779e 100644 --- a/data/icons/Default/border/bottom.svg +++ b/data/icons/Default/border/bottom.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/border/horizontal.svg b/data/icons/Default/border/horizontal.svg index 786327620..430adc1ea 100644 --- a/data/icons/Default/border/horizontal.svg +++ b/data/icons/Default/border/horizontal.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/border/inner.svg b/data/icons/Default/border/inner.svg index 7c3933421..392fb8cc0 100644 --- a/data/icons/Default/border/inner.svg +++ b/data/icons/Default/border/inner.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/border/left.svg b/data/icons/Default/border/left.svg index fe7067f83..88a1269d7 100644 --- a/data/icons/Default/border/left.svg +++ b/data/icons/Default/border/left.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/border/none.svg b/data/icons/Default/border/none.svg index 5fca8fccb..8de7b230b 100644 --- a/data/icons/Default/border/none.svg +++ b/data/icons/Default/border/none.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/border/outside.svg b/data/icons/Default/border/outside.svg index 8530c1826..e11526462 100644 --- a/data/icons/Default/border/outside.svg +++ b/data/icons/Default/border/outside.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/border/right.svg b/data/icons/Default/border/right.svg index e884f40c3..1f4d3a4b1 100644 --- a/data/icons/Default/border/right.svg +++ b/data/icons/Default/border/right.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/border/top.svg b/data/icons/Default/border/top.svg index 775a2b49e..52ad63208 100644 --- a/data/icons/Default/border/top.svg +++ b/data/icons/Default/border/top.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/border/vertical.svg b/data/icons/Default/border/vertical.svg index 39812b85f..2d1a6819c 100644 --- a/data/icons/Default/border/vertical.svg +++ b/data/icons/Default/border/vertical.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/amazon.svg b/data/icons/Default/brands/amazon.svg index 3a595271a..887fce654 100644 --- a/data/icons/Default/brands/amazon.svg +++ b/data/icons/Default/brands/amazon.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/android.svg b/data/icons/Default/brands/android.svg index 61fd6e1db..caf74b7e1 100644 --- a/data/icons/Default/brands/android.svg +++ b/data/icons/Default/brands/android.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/apple.svg b/data/icons/Default/brands/apple.svg index 7ef3b9f11..445d04e8f 100644 --- a/data/icons/Default/brands/apple.svg +++ b/data/icons/Default/brands/apple.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/arm.svg b/data/icons/Default/brands/arm.svg index 85e2aecfd..bc3c4b0af 100644 --- a/data/icons/Default/brands/arm.svg +++ b/data/icons/Default/brands/arm.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/digg.svg b/data/icons/Default/brands/digg.svg index 559b41081..9cebad33c 100644 --- a/data/icons/Default/brands/digg.svg +++ b/data/icons/Default/brands/digg.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/disqus.svg b/data/icons/Default/brands/disqus.svg index 932b99698..d58795990 100644 --- a/data/icons/Default/brands/disqus.svg +++ b/data/icons/Default/brands/disqus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/dot_net.svg b/data/icons/Default/brands/dot_net.svg index 018118568..f213808df 100644 --- a/data/icons/Default/brands/dot_net.svg +++ b/data/icons/Default/brands/dot_net.svg @@ -2,9 +2,9 @@ - - - - + + + + diff --git a/data/icons/Default/brands/facebook.svg b/data/icons/Default/brands/facebook.svg index a647c27fc..bfff66918 100644 --- a/data/icons/Default/brands/facebook.svg +++ b/data/icons/Default/brands/facebook.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/github.svg b/data/icons/Default/brands/github.svg index f66edd29a..59f9333a8 100644 --- a/data/icons/Default/brands/github.svg +++ b/data/icons/Default/brands/github.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/google.svg b/data/icons/Default/brands/google.svg index 7f785d6de..d941abda6 100644 --- a/data/icons/Default/brands/google.svg +++ b/data/icons/Default/brands/google.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/googleplus.svg b/data/icons/Default/brands/googleplus.svg index dcc43fc83..7874e92e8 100644 --- a/data/icons/Default/brands/googleplus.svg +++ b/data/icons/Default/brands/googleplus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/java.svg b/data/icons/Default/brands/java.svg index 80d774720..4e1e4fe22 100644 --- a/data/icons/Default/brands/java.svg +++ b/data/icons/Default/brands/java.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/java_text.svg b/data/icons/Default/brands/java_text.svg index dde9179b2..a7a207098 100644 --- a/data/icons/Default/brands/java_text.svg +++ b/data/icons/Default/brands/java_text.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/linkedin.svg b/data/icons/Default/brands/linkedin.svg index e0e50282a..338713c96 100644 --- a/data/icons/Default/brands/linkedin.svg +++ b/data/icons/Default/brands/linkedin.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/microsoft.svg b/data/icons/Default/brands/microsoft.svg index 1a4d83c18..623aa01de 100644 --- a/data/icons/Default/brands/microsoft.svg +++ b/data/icons/Default/brands/microsoft.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/os_windows.svg b/data/icons/Default/brands/os_windows.svg index d6fe13a10..7a5b278ac 100644 --- a/data/icons/Default/brands/os_windows.svg +++ b/data/icons/Default/brands/os_windows.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/paypal.svg b/data/icons/Default/brands/paypal.svg index c8e235519..42264ccd3 100644 --- a/data/icons/Default/brands/paypal.svg +++ b/data/icons/Default/brands/paypal.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/reddit.svg b/data/icons/Default/brands/reddit.svg index 349900470..0129f8932 100644 --- a/data/icons/Default/brands/reddit.svg +++ b/data/icons/Default/brands/reddit.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/skype.svg b/data/icons/Default/brands/skype.svg index 4209b41da..27466567d 100644 --- a/data/icons/Default/brands/skype.svg +++ b/data/icons/Default/brands/skype.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/tux.svg b/data/icons/Default/brands/tux.svg index ad65cb7e4..bf08b2a0a 100644 --- a/data/icons/Default/brands/tux.svg +++ b/data/icons/Default/brands/tux.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/twitter.svg b/data/icons/Default/brands/twitter.svg index 00472c09a..51dd7dada 100644 --- a/data/icons/Default/brands/twitter.svg +++ b/data/icons/Default/brands/twitter.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/twitter_hashtag.svg b/data/icons/Default/brands/twitter_hashtag.svg index ce7e8aa2b..33d893982 100644 --- a/data/icons/Default/brands/twitter_hashtag.svg +++ b/data/icons/Default/brands/twitter_hashtag.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/wikipedia.svg b/data/icons/Default/brands/wikipedia.svg index f6697e2c7..d024c2971 100644 --- a/data/icons/Default/brands/wikipedia.svg +++ b/data/icons/Default/brands/wikipedia.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/youtube.svg b/data/icons/Default/brands/youtube.svg index 4bae28413..651024d59 100644 --- a/data/icons/Default/brands/youtube.svg +++ b/data/icons/Default/brands/youtube.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/brands/youtube_play.svg b/data/icons/Default/brands/youtube_play.svg index b9ab82d60..3a9fc22b2 100644 --- a/data/icons/Default/brands/youtube_play.svg +++ b/data/icons/Default/brands/youtube_play.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/currency/cent.svg b/data/icons/Default/currency/cent.svg index 61377b928..e343027e8 100644 --- a/data/icons/Default/currency/cent.svg +++ b/data/icons/Default/currency/cent.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/currency/dollar.svg b/data/icons/Default/currency/dollar.svg index f1f8ed4c9..502794243 100644 --- a/data/icons/Default/currency/dollar.svg +++ b/data/icons/Default/currency/dollar.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/currency/euro.svg b/data/icons/Default/currency/euro.svg index 718e2c119..674eab82c 100644 --- a/data/icons/Default/currency/euro.svg +++ b/data/icons/Default/currency/euro.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/currency/grivna.svg b/data/icons/Default/currency/grivna.svg index 84051e72c..dd49470bf 100644 --- a/data/icons/Default/currency/grivna.svg +++ b/data/icons/Default/currency/grivna.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/currency/pound.svg b/data/icons/Default/currency/pound.svg index 01738083d..b78dc5a3f 100644 --- a/data/icons/Default/currency/pound.svg +++ b/data/icons/Default/currency/pound.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/currency/rubles.svg b/data/icons/Default/currency/rubles.svg index 505c61318..bde8b2c9a 100644 --- a/data/icons/Default/currency/rubles.svg +++ b/data/icons/Default/currency/rubles.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/currency/rupee.svg b/data/icons/Default/currency/rupee.svg index 50361b026..9dc871527 100644 --- a/data/icons/Default/currency/rupee.svg +++ b/data/icons/Default/currency/rupee.svg @@ -2,5 +2,5 @@ - + diff --git a/data/icons/Default/currency/yen.svg b/data/icons/Default/currency/yen.svg index 6c92f6e47..030809eee 100644 --- a/data/icons/Default/currency/yen.svg +++ b/data/icons/Default/currency/yen.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/dev/bit.svg b/data/icons/Default/dev/bit.svg index cf34bea37..5e8a5414a 100644 --- a/data/icons/Default/dev/bit.svg +++ b/data/icons/Default/dev/bit.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/dev/boolean.svg b/data/icons/Default/dev/boolean.svg index ae011a575..d6731f7b3 100644 --- a/data/icons/Default/dev/boolean.svg +++ b/data/icons/Default/dev/boolean.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/dev/braces.svg b/data/icons/Default/dev/braces.svg index b56bcfb32..b5e1af54b 100644 --- a/data/icons/Default/dev/braces.svg +++ b/data/icons/Default/dev/braces.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/dev/brackets.svg b/data/icons/Default/dev/brackets.svg index 5171c0698..7e6c5c2df 100644 --- a/data/icons/Default/dev/brackets.svg +++ b/data/icons/Default/dev/brackets.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/dev/bug.svg b/data/icons/Default/dev/bug.svg index 28de692ba..1968cd3cf 100644 --- a/data/icons/Default/dev/bug.svg +++ b/data/icons/Default/dev/bug.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/dev/debug_restart.svg b/data/icons/Default/dev/debug_restart.svg index fdbce806f..1b10e3cd1 100644 --- a/data/icons/Default/dev/debug_restart.svg +++ b/data/icons/Default/dev/debug_restart.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/dev/debug_step_into.svg b/data/icons/Default/dev/debug_step_into.svg index 8b21b39d7..b2493354b 100644 --- a/data/icons/Default/dev/debug_step_into.svg +++ b/data/icons/Default/dev/debug_step_into.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/dev/debug_step_out.svg b/data/icons/Default/dev/debug_step_out.svg index 7c08693aa..994c3f66c 100644 --- a/data/icons/Default/dev/debug_step_out.svg +++ b/data/icons/Default/dev/debug_step_out.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/dev/debug_step_over.svg b/data/icons/Default/dev/debug_step_over.svg index 2e470bdd3..84a4d82dc 100644 --- a/data/icons/Default/dev/debug_step_over.svg +++ b/data/icons/Default/dev/debug_step_over.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/dev/debug_stop.svg b/data/icons/Default/dev/debug_stop.svg index 1b3819f6a..4dabfaa80 100644 --- a/data/icons/Default/dev/debug_stop.svg +++ b/data/icons/Default/dev/debug_stop.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/dev/markup.svg b/data/icons/Default/dev/markup.svg index f8bce7bec..2646d1a8a 100644 --- a/data/icons/Default/dev/markup.svg +++ b/data/icons/Default/dev/markup.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/dev/null.svg b/data/icons/Default/dev/null.svg index 519eee9f7..fc2c53d43 100644 --- a/data/icons/Default/dev/null.svg +++ b/data/icons/Default/dev/null.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/dev/resource.svg b/data/icons/Default/dev/resource.svg index 39d6ec060..5be4384e3 100644 --- a/data/icons/Default/dev/resource.svg +++ b/data/icons/Default/dev/resource.svg @@ -3,5 +3,5 @@ - + diff --git a/data/icons/Default/dev/resource_group.svg b/data/icons/Default/dev/resource_group.svg index b683c0f7d..8f5cdfc93 100644 --- a/data/icons/Default/dev/resource_group.svg +++ b/data/icons/Default/dev/resource_group.svg @@ -3,5 +3,5 @@ - + diff --git a/data/icons/Default/dev/xml.svg b/data/icons/Default/dev/xml.svg index 49f18a3a1..8424fc653 100644 --- a/data/icons/Default/dev/xml.svg +++ b/data/icons/Default/dev/xml.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/battery.svg b/data/icons/Default/devices/battery.svg index eb42aa96e..4968b59d0 100644 --- a/data/icons/Default/devices/battery.svg +++ b/data/icons/Default/devices/battery.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/battery0.svg b/data/icons/Default/devices/battery0.svg index 70cad4cae..bc93e64ba 100644 --- a/data/icons/Default/devices/battery0.svg +++ b/data/icons/Default/devices/battery0.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/battery1.svg b/data/icons/Default/devices/battery1.svg index 7069589e4..b8824556c 100644 --- a/data/icons/Default/devices/battery1.svg +++ b/data/icons/Default/devices/battery1.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/battery2.svg b/data/icons/Default/devices/battery2.svg index 4783d243d..86bf31c89 100644 --- a/data/icons/Default/devices/battery2.svg +++ b/data/icons/Default/devices/battery2.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/battery_charging.svg b/data/icons/Default/devices/battery_charging.svg index ed6359406..8855581d8 100644 --- a/data/icons/Default/devices/battery_charging.svg +++ b/data/icons/Default/devices/battery_charging.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/bluetooth.svg b/data/icons/Default/devices/bluetooth.svg index 897818492..89ac1e7ad 100644 --- a/data/icons/Default/devices/bluetooth.svg +++ b/data/icons/Default/devices/bluetooth.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/camera.svg b/data/icons/Default/devices/camera.svg index d2e34f0e9..05980eb5b 100644 --- a/data/icons/Default/devices/camera.svg +++ b/data/icons/Default/devices/camera.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/compactdisc.svg b/data/icons/Default/devices/compactdisc.svg index 442cc696b..3f11263d4 100644 --- a/data/icons/Default/devices/compactdisc.svg +++ b/data/icons/Default/devices/compactdisc.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/compactdisc_eject.svg b/data/icons/Default/devices/compactdisc_eject.svg index 1cfc99e6c..f84bb5608 100644 --- a/data/icons/Default/devices/compactdisc_eject.svg +++ b/data/icons/Default/devices/compactdisc_eject.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/connect_range1.svg b/data/icons/Default/devices/connect_range1.svg index fc53a3ccc..4052602b5 100644 --- a/data/icons/Default/devices/connect_range1.svg +++ b/data/icons/Default/devices/connect_range1.svg @@ -1,6 +1,6 @@  - + diff --git a/data/icons/Default/devices/connect_range2.svg b/data/icons/Default/devices/connect_range2.svg index 51affa23a..0cd80df49 100644 --- a/data/icons/Default/devices/connect_range2.svg +++ b/data/icons/Default/devices/connect_range2.svg @@ -2,5 +2,5 @@ - + diff --git a/data/icons/Default/devices/connect_range3.svg b/data/icons/Default/devices/connect_range3.svg index 0051807d7..b5dca9140 100644 --- a/data/icons/Default/devices/connect_range3.svg +++ b/data/icons/Default/devices/connect_range3.svg @@ -2,5 +2,5 @@ - + diff --git a/data/icons/Default/devices/connect_range4.svg b/data/icons/Default/devices/connect_range4.svg index 9894b1c39..d3db93214 100644 --- a/data/icons/Default/devices/connect_range4.svg +++ b/data/icons/Default/devices/connect_range4.svg @@ -1,6 +1,6 @@  - + diff --git a/data/icons/Default/devices/connect_range5.svg b/data/icons/Default/devices/connect_range5.svg index d7d16ae70..5f762328c 100644 --- a/data/icons/Default/devices/connect_range5.svg +++ b/data/icons/Default/devices/connect_range5.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/connection_1x.svg b/data/icons/Default/devices/connection_1x.svg index 32d0be2e5..a59246889 100644 --- a/data/icons/Default/devices/connection_1x.svg +++ b/data/icons/Default/devices/connection_1x.svg @@ -2,7 +2,7 @@ - - + + diff --git a/data/icons/Default/devices/connection_3g.svg b/data/icons/Default/devices/connection_3g.svg index 7638b556d..8a38d56b8 100644 --- a/data/icons/Default/devices/connection_3g.svg +++ b/data/icons/Default/devices/connection_3g.svg @@ -2,7 +2,7 @@ - - + + diff --git a/data/icons/Default/devices/connection_4g.svg b/data/icons/Default/devices/connection_4g.svg index bc09e4988..ce8608cb6 100644 --- a/data/icons/Default/devices/connection_4g.svg +++ b/data/icons/Default/devices/connection_4g.svg @@ -2,7 +2,7 @@ - - + + diff --git a/data/icons/Default/devices/connection_ev.svg b/data/icons/Default/devices/connection_ev.svg index bdb75f42b..46a630e6f 100644 --- a/data/icons/Default/devices/connection_ev.svg +++ b/data/icons/Default/devices/connection_ev.svg @@ -2,7 +2,7 @@ - - + + diff --git a/data/icons/Default/devices/cpu.svg b/data/icons/Default/devices/cpu.svg index 05852d878..da5270ee7 100644 --- a/data/icons/Default/devices/cpu.svg +++ b/data/icons/Default/devices/cpu.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/dvd.svg b/data/icons/Default/devices/dvd.svg index 442cc696b..3f11263d4 100644 --- a/data/icons/Default/devices/dvd.svg +++ b/data/icons/Default/devices/dvd.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/floppydisk.svg b/data/icons/Default/devices/floppydisk.svg index 1830d1b7b..5a2983458 100644 --- a/data/icons/Default/devices/floppydisk.svg +++ b/data/icons/Default/devices/floppydisk.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/gamepad.svg b/data/icons/Default/devices/gamepad.svg index bc6adeafb..cfe2aede1 100644 --- a/data/icons/Default/devices/gamepad.svg +++ b/data/icons/Default/devices/gamepad.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/headphones.svg b/data/icons/Default/devices/headphones.svg index 18db30123..fa23484d7 100644 --- a/data/icons/Default/devices/headphones.svg +++ b/data/icons/Default/devices/headphones.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/headphones_bluetooth.svg b/data/icons/Default/devices/headphones_bluetooth.svg index 71b34a439..7b788f391 100644 --- a/data/icons/Default/devices/headphones_bluetooth.svg +++ b/data/icons/Default/devices/headphones_bluetooth.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/headset.svg b/data/icons/Default/devices/headset.svg index 198faecb2..ff44d41e2 100644 --- a/data/icons/Default/devices/headset.svg +++ b/data/icons/Default/devices/headset.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/iphone.svg b/data/icons/Default/devices/iphone.svg index 87f19a6fe..e0a1855c3 100644 --- a/data/icons/Default/devices/iphone.svg +++ b/data/icons/Default/devices/iphone.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/keyboard.svg b/data/icons/Default/devices/keyboard.svg index 2de42be6b..a3e5c9d4f 100644 --- a/data/icons/Default/devices/keyboard.svg +++ b/data/icons/Default/devices/keyboard.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/laptop.svg b/data/icons/Default/devices/laptop.svg index 522b70038..e197dc89f 100644 --- a/data/icons/Default/devices/laptop.svg +++ b/data/icons/Default/devices/laptop.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/microphone.svg b/data/icons/Default/devices/microphone.svg index c6cc90403..664e00a6f 100644 --- a/data/icons/Default/devices/microphone.svg +++ b/data/icons/Default/devices/microphone.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/monitor.svg b/data/icons/Default/devices/monitor.svg index 477252f98..3a5a6922e 100644 --- a/data/icons/Default/devices/monitor.svg +++ b/data/icons/Default/devices/monitor.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/monitor_add.svg b/data/icons/Default/devices/monitor_add.svg index 9ac8241df..627ea5038 100644 --- a/data/icons/Default/devices/monitor_add.svg +++ b/data/icons/Default/devices/monitor_add.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/monitor_delete.svg b/data/icons/Default/devices/monitor_delete.svg index 7cea29cbf..6a3a9efc4 100644 --- a/data/icons/Default/devices/monitor_delete.svg +++ b/data/icons/Default/devices/monitor_delete.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/monitor_film.svg b/data/icons/Default/devices/monitor_film.svg index f2b47718e..561537c42 100644 --- a/data/icons/Default/devices/monitor_film.svg +++ b/data/icons/Default/devices/monitor_film.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/monitor_identify.svg b/data/icons/Default/devices/monitor_identify.svg index 35504152a..1f6899575 100644 --- a/data/icons/Default/devices/monitor_identify.svg +++ b/data/icons/Default/devices/monitor_identify.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/monitor_minus.svg b/data/icons/Default/devices/monitor_minus.svg index 202207551..0a316ab6d 100644 --- a/data/icons/Default/devices/monitor_minus.svg +++ b/data/icons/Default/devices/monitor_minus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/monitor_to.svg b/data/icons/Default/devices/monitor_to.svg index 6212f1b8a..311744771 100644 --- a/data/icons/Default/devices/monitor_to.svg +++ b/data/icons/Default/devices/monitor_to.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/mouse.svg b/data/icons/Default/devices/mouse.svg index 96b4e089b..b5f535a0a 100644 --- a/data/icons/Default/devices/mouse.svg +++ b/data/icons/Default/devices/mouse.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/network.svg b/data/icons/Default/devices/network.svg index bb96fceaf..0cf709c0e 100644 --- a/data/icons/Default/devices/network.svg +++ b/data/icons/Default/devices/network.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/network_disconnect.svg b/data/icons/Default/devices/network_disconnect.svg index 3560581e7..c57aa14c3 100644 --- a/data/icons/Default/devices/network_disconnect.svg +++ b/data/icons/Default/devices/network_disconnect.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/network_home.svg b/data/icons/Default/devices/network_home.svg index 8c7bc8856..be3497dd5 100644 --- a/data/icons/Default/devices/network_home.svg +++ b/data/icons/Default/devices/network_home.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/network_home_disconnect.svg b/data/icons/Default/devices/network_home_disconnect.svg index e4ca94aff..9d40f3d56 100644 --- a/data/icons/Default/devices/network_home_disconnect.svg +++ b/data/icons/Default/devices/network_home_disconnect.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/network_server.svg b/data/icons/Default/devices/network_server.svg index f321afa39..61e7a9bef 100644 --- a/data/icons/Default/devices/network_server.svg +++ b/data/icons/Default/devices/network_server.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/network_server_connecting.svg b/data/icons/Default/devices/network_server_connecting.svg index aa3288c66..a17fa76bc 100644 --- a/data/icons/Default/devices/network_server_connecting.svg +++ b/data/icons/Default/devices/network_server_connecting.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/network_server_disconnect.svg b/data/icons/Default/devices/network_server_disconnect.svg index 8175a4d8d..bda5014f9 100644 --- a/data/icons/Default/devices/network_server_disconnect.svg +++ b/data/icons/Default/devices/network_server_disconnect.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/nfc.svg b/data/icons/Default/devices/nfc.svg index 9cd6e5b80..5e19b8109 100644 --- a/data/icons/Default/devices/nfc.svg +++ b/data/icons/Default/devices/nfc.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/phone.svg b/data/icons/Default/devices/phone.svg index 9f8e8af7d..8e8703635 100644 --- a/data/icons/Default/devices/phone.svg +++ b/data/icons/Default/devices/phone.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/phone_hangup.svg b/data/icons/Default/devices/phone_hangup.svg index cb5bf4623..5dcfeef36 100644 --- a/data/icons/Default/devices/phone_hangup.svg +++ b/data/icons/Default/devices/phone_hangup.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/power.svg b/data/icons/Default/devices/power.svg index 7f4c70203..ffde6be14 100644 --- a/data/icons/Default/devices/power.svg +++ b/data/icons/Default/devices/power.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/printer.svg b/data/icons/Default/devices/printer.svg index e5f761297..811d77aea 100644 --- a/data/icons/Default/devices/printer.svg +++ b/data/icons/Default/devices/printer.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/projector.svg b/data/icons/Default/devices/projector.svg index 7ce2ece26..da7fa0a0d 100644 --- a/data/icons/Default/devices/projector.svg +++ b/data/icons/Default/devices/projector.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/projector_screen.svg b/data/icons/Default/devices/projector_screen.svg index dd27931eb..bb613c2a2 100644 --- a/data/icons/Default/devices/projector_screen.svg +++ b/data/icons/Default/devices/projector_screen.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/radar.svg b/data/icons/Default/devices/radar.svg index 1d398719d..ff9fd546d 100644 --- a/data/icons/Default/devices/radar.svg +++ b/data/icons/Default/devices/radar.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/sd.svg b/data/icons/Default/devices/sd.svg index d6c1e6c52..0cfb01e7a 100644 --- a/data/icons/Default/devices/sd.svg +++ b/data/icons/Default/devices/sd.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/sd_micro.svg b/data/icons/Default/devices/sd_micro.svg index d428d8073..f0bb18b3d 100644 --- a/data/icons/Default/devices/sd_micro.svg +++ b/data/icons/Default/devices/sd_micro.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/server.svg b/data/icons/Default/devices/server.svg index b605fdcb3..f495fc89c 100644 --- a/data/icons/Default/devices/server.svg +++ b/data/icons/Default/devices/server.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/simcard.svg b/data/icons/Default/devices/simcard.svg index 0c77b5711..29550741f 100644 --- a/data/icons/Default/devices/simcard.svg +++ b/data/icons/Default/devices/simcard.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/simcard_micro.svg b/data/icons/Default/devices/simcard_micro.svg index 5343cd076..a6f6e08e3 100644 --- a/data/icons/Default/devices/simcard_micro.svg +++ b/data/icons/Default/devices/simcard_micro.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/speaker.svg b/data/icons/Default/devices/speaker.svg index e27658a1c..549da792b 100644 --- a/data/icons/Default/devices/speaker.svg +++ b/data/icons/Default/devices/speaker.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/tablet.svg b/data/icons/Default/devices/tablet.svg index d480e287a..c2dd3ea7b 100644 --- a/data/icons/Default/devices/tablet.svg +++ b/data/icons/Default/devices/tablet.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/tower.svg b/data/icons/Default/devices/tower.svg index bdb5d07ec..3ec19b747 100644 --- a/data/icons/Default/devices/tower.svg +++ b/data/icons/Default/devices/tower.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/tv_news.svg b/data/icons/Default/devices/tv_news.svg index 27375d435..8b6cffa20 100644 --- a/data/icons/Default/devices/tv_news.svg +++ b/data/icons/Default/devices/tv_news.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/tv_remote.svg b/data/icons/Default/devices/tv_remote.svg index 3a65a66b0..0b786b664 100644 --- a/data/icons/Default/devices/tv_remote.svg +++ b/data/icons/Default/devices/tv_remote.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/usb.svg b/data/icons/Default/devices/usb.svg index f7f3fa81e..c60104c68 100644 --- a/data/icons/Default/devices/usb.svg +++ b/data/icons/Default/devices/usb.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/usb_drive.svg b/data/icons/Default/devices/usb_drive.svg index bea976828..d53fb9818 100644 --- a/data/icons/Default/devices/usb_drive.svg +++ b/data/icons/Default/devices/usb_drive.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/webcam.svg b/data/icons/Default/devices/webcam.svg index 0d343648a..c3eafc680 100644 --- a/data/icons/Default/devices/webcam.svg +++ b/data/icons/Default/devices/webcam.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/wifi.svg b/data/icons/Default/devices/wifi.svg index f523f4167..ac4965464 100644 --- a/data/icons/Default/devices/wifi.svg +++ b/data/icons/Default/devices/wifi.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/devices/wifi_pulse.svg b/data/icons/Default/devices/wifi_pulse.svg index 14552bf40..c69b8ed7c 100644 --- a/data/icons/Default/devices/wifi_pulse.svg +++ b/data/icons/Default/devices/wifi_pulse.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/emoticons/angry.svg b/data/icons/Default/emoticons/angry.svg index 3dd2bde6e..0315332a6 100644 --- a/data/icons/Default/emoticons/angry.svg +++ b/data/icons/Default/emoticons/angry.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/emoticons/cry.svg b/data/icons/Default/emoticons/cry.svg index db1a23d72..7bf84610c 100644 --- a/data/icons/Default/emoticons/cry.svg +++ b/data/icons/Default/emoticons/cry.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/emoticons/frown.svg b/data/icons/Default/emoticons/frown.svg index 1546c191d..75879a440 100644 --- a/data/icons/Default/emoticons/frown.svg +++ b/data/icons/Default/emoticons/frown.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/emoticons/glasses.svg b/data/icons/Default/emoticons/glasses.svg index 03141e337..68564377d 100644 --- a/data/icons/Default/emoticons/glasses.svg +++ b/data/icons/Default/emoticons/glasses.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/emoticons/grin.svg b/data/icons/Default/emoticons/grin.svg index ae337dd43..11b5b84db 100644 --- a/data/icons/Default/emoticons/grin.svg +++ b/data/icons/Default/emoticons/grin.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/emoticons/grumpy.svg b/data/icons/Default/emoticons/grumpy.svg index c7ee0e89b..731fba033 100644 --- a/data/icons/Default/emoticons/grumpy.svg +++ b/data/icons/Default/emoticons/grumpy.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/emoticons/happy.svg b/data/icons/Default/emoticons/happy.svg index a7f14095b..f3520ba9a 100644 --- a/data/icons/Default/emoticons/happy.svg +++ b/data/icons/Default/emoticons/happy.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/emoticons/kiki.svg b/data/icons/Default/emoticons/kiki.svg index fc45e1fff..dc52368c9 100644 --- a/data/icons/Default/emoticons/kiki.svg +++ b/data/icons/Default/emoticons/kiki.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/emoticons/squint.svg b/data/icons/Default/emoticons/squint.svg index c7c27a8c9..fc1d91748 100644 --- a/data/icons/Default/emoticons/squint.svg +++ b/data/icons/Default/emoticons/squint.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/emoticons/tounge.svg b/data/icons/Default/emoticons/tounge.svg index f8667a19a..43c367617 100644 --- a/data/icons/Default/emoticons/tounge.svg +++ b/data/icons/Default/emoticons/tounge.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/emoticons/what.svg b/data/icons/Default/emoticons/what.svg index 7ce049ec1..5a4c289ec 100644 --- a/data/icons/Default/emoticons/what.svg +++ b/data/icons/Default/emoticons/what.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/archive.svg b/data/icons/Default/filetypes/archive.svg index 042ca60cb..1a0cb42dc 100644 --- a/data/icons/Default/filetypes/archive.svg +++ b/data/icons/Default/filetypes/archive.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/audio.svg b/data/icons/Default/filetypes/audio.svg index 6aa2ebfbc..e2a34901a 100644 --- a/data/icons/Default/filetypes/audio.svg +++ b/data/icons/Default/filetypes/audio.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/binary.svg b/data/icons/Default/filetypes/binary.svg index cf34bea37..5e8a5414a 100644 --- a/data/icons/Default/filetypes/binary.svg +++ b/data/icons/Default/filetypes/binary.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/broken.svg b/data/icons/Default/filetypes/broken.svg index 135e76cc0..60ad7e2eb 100644 --- a/data/icons/Default/filetypes/broken.svg +++ b/data/icons/Default/filetypes/broken.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/calendar.svg b/data/icons/Default/filetypes/calendar.svg index c7ad2f391..5895e849a 100644 --- a/data/icons/Default/filetypes/calendar.svg +++ b/data/icons/Default/filetypes/calendar.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/cdimage.svg b/data/icons/Default/filetypes/cdimage.svg index 442cc696b..3f11263d4 100644 --- a/data/icons/Default/filetypes/cdimage.svg +++ b/data/icons/Default/filetypes/cdimage.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/cdtrack.svg b/data/icons/Default/filetypes/cdtrack.svg index 442cc696b..3f11263d4 100644 --- a/data/icons/Default/filetypes/cdtrack.svg +++ b/data/icons/Default/filetypes/cdtrack.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/core.svg b/data/icons/Default/filetypes/core.svg index 24a92dc0c..191c11cc3 100644 --- a/data/icons/Default/filetypes/core.svg +++ b/data/icons/Default/filetypes/core.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/download.svg b/data/icons/Default/filetypes/download.svg index 455d3a4bb..ed92b1619 100644 --- a/data/icons/Default/filetypes/download.svg +++ b/data/icons/Default/filetypes/download.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/encrypted.svg b/data/icons/Default/filetypes/encrypted.svg index a0d03075a..28686fe94 100644 --- a/data/icons/Default/filetypes/encrypted.svg +++ b/data/icons/Default/filetypes/encrypted.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/excel.svg b/data/icons/Default/filetypes/excel.svg index 223e2ec60..bf01f53a6 100644 --- a/data/icons/Default/filetypes/excel.svg +++ b/data/icons/Default/filetypes/excel.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/font.svg b/data/icons/Default/filetypes/font.svg index facc2b31e..b18d9a7f1 100644 --- a/data/icons/Default/filetypes/font.svg +++ b/data/icons/Default/filetypes/font.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/gif.svg b/data/icons/Default/filetypes/gif.svg index f73f148aa..5846b0c42 100644 --- a/data/icons/Default/filetypes/gif.svg +++ b/data/icons/Default/filetypes/gif.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/html.svg b/data/icons/Default/filetypes/html.svg index b175c4c4f..f6ec5a052 100644 --- a/data/icons/Default/filetypes/html.svg +++ b/data/icons/Default/filetypes/html.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/image.svg b/data/icons/Default/filetypes/image.svg index 9aaff8be4..48af2f26c 100644 --- a/data/icons/Default/filetypes/image.svg +++ b/data/icons/Default/filetypes/image.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/jpg.svg b/data/icons/Default/filetypes/jpg.svg index f41c02b44..6ee8c1780 100644 --- a/data/icons/Default/filetypes/jpg.svg +++ b/data/icons/Default/filetypes/jpg.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/locked.svg b/data/icons/Default/filetypes/locked.svg index 7b645f10e..6bfc646f5 100644 --- a/data/icons/Default/filetypes/locked.svg +++ b/data/icons/Default/filetypes/locked.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/log.svg b/data/icons/Default/filetypes/log.svg index f85b02722..bdbb5c330 100644 --- a/data/icons/Default/filetypes/log.svg +++ b/data/icons/Default/filetypes/log.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/make.svg b/data/icons/Default/filetypes/make.svg index b56bcfb32..b5e1af54b 100644 --- a/data/icons/Default/filetypes/make.svg +++ b/data/icons/Default/filetypes/make.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/onenote.svg b/data/icons/Default/filetypes/onenote.svg index 43e10664a..15855de9c 100644 --- a/data/icons/Default/filetypes/onenote.svg +++ b/data/icons/Default/filetypes/onenote.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/pdf.svg b/data/icons/Default/filetypes/pdf.svg index a4c18bec9..84c7b2b6e 100644 --- a/data/icons/Default/filetypes/pdf.svg +++ b/data/icons/Default/filetypes/pdf.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/php.svg b/data/icons/Default/filetypes/php.svg index b56bcfb32..b5e1af54b 100644 --- a/data/icons/Default/filetypes/php.svg +++ b/data/icons/Default/filetypes/php.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/png.svg b/data/icons/Default/filetypes/png.svg index 9a30ccb3d..6c5272650 100644 --- a/data/icons/Default/filetypes/png.svg +++ b/data/icons/Default/filetypes/png.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/readme.svg b/data/icons/Default/filetypes/readme.svg index 75e36f9e9..10c3012fa 100644 --- a/data/icons/Default/filetypes/readme.svg +++ b/data/icons/Default/filetypes/readme.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/shellscript.svg b/data/icons/Default/filetypes/shellscript.svg index 39646a58f..4f5d46d20 100644 --- a/data/icons/Default/filetypes/shellscript.svg +++ b/data/icons/Default/filetypes/shellscript.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/source.svg b/data/icons/Default/filetypes/source.svg index b56bcfb32..b5e1af54b 100644 --- a/data/icons/Default/filetypes/source.svg +++ b/data/icons/Default/filetypes/source.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/source_c.svg b/data/icons/Default/filetypes/source_c.svg index b56bcfb32..b5e1af54b 100644 --- a/data/icons/Default/filetypes/source_c.svg +++ b/data/icons/Default/filetypes/source_c.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/source_cpp.svg b/data/icons/Default/filetypes/source_cpp.svg index b56bcfb32..b5e1af54b 100644 --- a/data/icons/Default/filetypes/source_cpp.svg +++ b/data/icons/Default/filetypes/source_cpp.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/source_h.svg b/data/icons/Default/filetypes/source_h.svg index b56bcfb32..b5e1af54b 100644 --- a/data/icons/Default/filetypes/source_h.svg +++ b/data/icons/Default/filetypes/source_h.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/source_java.svg b/data/icons/Default/filetypes/source_java.svg index b56bcfb32..b5e1af54b 100644 --- a/data/icons/Default/filetypes/source_java.svg +++ b/data/icons/Default/filetypes/source_java.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/source_o.svg b/data/icons/Default/filetypes/source_o.svg index b56bcfb32..b5e1af54b 100644 --- a/data/icons/Default/filetypes/source_o.svg +++ b/data/icons/Default/filetypes/source_o.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/source_pl.svg b/data/icons/Default/filetypes/source_pl.svg index b56bcfb32..b5e1af54b 100644 --- a/data/icons/Default/filetypes/source_pl.svg +++ b/data/icons/Default/filetypes/source_pl.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/source_py.svg b/data/icons/Default/filetypes/source_py.svg index b56bcfb32..b5e1af54b 100644 --- a/data/icons/Default/filetypes/source_py.svg +++ b/data/icons/Default/filetypes/source_py.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/source_s.svg b/data/icons/Default/filetypes/source_s.svg index b56bcfb32..b5e1af54b 100644 --- a/data/icons/Default/filetypes/source_s.svg +++ b/data/icons/Default/filetypes/source_s.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/spreadsheet.svg b/data/icons/Default/filetypes/spreadsheet.svg index 30632a4f2..d5adeef71 100644 --- a/data/icons/Default/filetypes/spreadsheet.svg +++ b/data/icons/Default/filetypes/spreadsheet.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/temp.svg b/data/icons/Default/filetypes/temp.svg index 91dcbbf4f..8bcd48bac 100644 --- a/data/icons/Default/filetypes/temp.svg +++ b/data/icons/Default/filetypes/temp.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/vectorgfx.svg b/data/icons/Default/filetypes/vectorgfx.svg index 55eaeec7e..3c66a4cd5 100644 --- a/data/icons/Default/filetypes/vectorgfx.svg +++ b/data/icons/Default/filetypes/vectorgfx.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/video.svg b/data/icons/Default/filetypes/video.svg index 0d93aa696..aa2f220a9 100644 --- a/data/icons/Default/filetypes/video.svg +++ b/data/icons/Default/filetypes/video.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/wordprocessing.svg b/data/icons/Default/filetypes/wordprocessing.svg index 59ef8a829..b8b677cc2 100644 --- a/data/icons/Default/filetypes/wordprocessing.svg +++ b/data/icons/Default/filetypes/wordprocessing.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/xml.svg b/data/icons/Default/filetypes/xml.svg index 49f18a3a1..8424fc653 100644 --- a/data/icons/Default/filetypes/xml.svg +++ b/data/icons/Default/filetypes/xml.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/filetypes/zip.svg b/data/icons/Default/filetypes/zip.svg index 042ca60cb..1a0cb42dc 100644 --- a/data/icons/Default/filetypes/zip.svg +++ b/data/icons/Default/filetypes/zip.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/folders/folder_contacts.svg b/data/icons/Default/folders/folder_contacts.svg index fcdb8dbf7..0e8945bfc 100644 --- a/data/icons/Default/folders/folder_contacts.svg +++ b/data/icons/Default/folders/folder_contacts.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/folders/folder_lock.svg b/data/icons/Default/folders/folder_lock.svg index 0c131ecd2..410d86ccc 100644 --- a/data/icons/Default/folders/folder_lock.svg +++ b/data/icons/Default/folders/folder_lock.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/folders/folder_open.svg b/data/icons/Default/folders/folder_open.svg index 2ef9b625a..612ccbb89 100644 --- a/data/icons/Default/folders/folder_open.svg +++ b/data/icons/Default/folders/folder_open.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/access.svg b/data/icons/Default/items/access.svg index c5ba95cda..100aa4879 100644 --- a/data/icons/Default/items/access.svg +++ b/data/icons/Default/items/access.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/anchor.svg b/data/icons/Default/items/anchor.svg index 4063782af..0700e97ad 100644 --- a/data/icons/Default/items/anchor.svg +++ b/data/icons/Default/items/anchor.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/app.svg b/data/icons/Default/items/app.svg index 44ff5fcab..d2e01ac18 100644 --- a/data/icons/Default/items/app.svg +++ b/data/icons/Default/items/app.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/app_favorite.svg b/data/icons/Default/items/app_favorite.svg index 4225125d0..bc7e7d31e 100644 --- a/data/icons/Default/items/app_favorite.svg +++ b/data/icons/Default/items/app_favorite.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/app_minus.svg b/data/icons/Default/items/app_minus.svg index 0bc7a7d5e..e6086cc89 100644 --- a/data/icons/Default/items/app_minus.svg +++ b/data/icons/Default/items/app_minus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/app_plus.svg b/data/icons/Default/items/app_plus.svg index d8be5b0ad..6f81f1a12 100644 --- a/data/icons/Default/items/app_plus.svg +++ b/data/icons/Default/items/app_plus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/app_remove.svg b/data/icons/Default/items/app_remove.svg index 4a43baaa1..e87758067 100644 --- a/data/icons/Default/items/app_remove.svg +++ b/data/icons/Default/items/app_remove.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/back.svg b/data/icons/Default/items/back.svg index 8f3c17306..77d22455b 100644 --- a/data/icons/Default/items/back.svg +++ b/data/icons/Default/items/back.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/bookmark.svg b/data/icons/Default/items/bookmark.svg index 988f7dd67..8ae4fe043 100644 --- a/data/icons/Default/items/bookmark.svg +++ b/data/icons/Default/items/bookmark.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/cancel.svg b/data/icons/Default/items/cancel.svg index 16d893cb6..7a197057b 100644 --- a/data/icons/Default/items/cancel.svg +++ b/data/icons/Default/items/cancel.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/caution.svg b/data/icons/Default/items/caution.svg index ca87552fa..c4c55ffd2 100644 --- a/data/icons/Default/items/caution.svg +++ b/data/icons/Default/items/caution.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/checkmark.svg b/data/icons/Default/items/checkmark.svg index 3f85c7f37..771bd9ceb 100644 --- a/data/icons/Default/items/checkmark.svg +++ b/data/icons/Default/items/checkmark.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/checkmark_box.svg b/data/icons/Default/items/checkmark_box.svg index 07ab46c56..3a2e9c719 100644 --- a/data/icons/Default/items/checkmark_box.svg +++ b/data/icons/Default/items/checkmark_box.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/checkmark_cross.svg b/data/icons/Default/items/checkmark_cross.svg index ae20e2b47..c23e04252 100644 --- a/data/icons/Default/items/checkmark_cross.svg +++ b/data/icons/Default/items/checkmark_cross.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/checkmark_uncrossed.svg b/data/icons/Default/items/checkmark_uncrossed.svg index 7798e5465..029ac711f 100644 --- a/data/icons/Default/items/checkmark_uncrossed.svg +++ b/data/icons/Default/items/checkmark_uncrossed.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/clear_left.svg b/data/icons/Default/items/clear_left.svg index ade91ac52..6f8d0cf8c 100644 --- a/data/icons/Default/items/clear_left.svg +++ b/data/icons/Default/items/clear_left.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/clearline.svg b/data/icons/Default/items/clearline.svg index ade91ac52..6f8d0cf8c 100644 --- a/data/icons/Default/items/clearline.svg +++ b/data/icons/Default/items/clearline.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/clipboard.svg b/data/icons/Default/items/clipboard.svg index 189d65ff2..287d0e0e4 100644 --- a/data/icons/Default/items/clipboard.svg +++ b/data/icons/Default/items/clipboard.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/clipboard_empty.svg b/data/icons/Default/items/clipboard_empty.svg index 075d3ceb5..64700700b 100644 --- a/data/icons/Default/items/clipboard_empty.svg +++ b/data/icons/Default/items/clipboard_empty.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/compress.svg b/data/icons/Default/items/compress.svg index 042ca60cb..1a0cb42dc 100644 --- a/data/icons/Default/items/compress.svg +++ b/data/icons/Default/items/compress.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/connect.svg b/data/icons/Default/items/connect.svg index 9d9faee0d..3b12b3200 100644 --- a/data/icons/Default/items/connect.svg +++ b/data/icons/Default/items/connect.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/connected.svg b/data/icons/Default/items/connected.svg index 027b5d079..d023c35b6 100644 --- a/data/icons/Default/items/connected.svg +++ b/data/icons/Default/items/connected.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/database.svg b/data/icons/Default/items/database.svg index 3427dda13..8fff3c738 100644 --- a/data/icons/Default/items/database.svg +++ b/data/icons/Default/items/database.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/database_sql.svg b/data/icons/Default/items/database_sql.svg index ae21a948f..dc6f01f73 100644 --- a/data/icons/Default/items/database_sql.svg +++ b/data/icons/Default/items/database_sql.svg @@ -2,5 +2,5 @@ - + diff --git a/data/icons/Default/items/delete.svg b/data/icons/Default/items/delete.svg index bc61dd569..b2e404060 100644 --- a/data/icons/Default/items/delete.svg +++ b/data/icons/Default/items/delete.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/disconnect.svg b/data/icons/Default/items/disconnect.svg index 027b5d079..d023c35b6 100644 --- a/data/icons/Default/items/disconnect.svg +++ b/data/icons/Default/items/disconnect.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/disconnected.svg b/data/icons/Default/items/disconnected.svg index 9d9faee0d..3b12b3200 100644 --- a/data/icons/Default/items/disconnected.svg +++ b/data/icons/Default/items/disconnected.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/down.svg b/data/icons/Default/items/down.svg index 3c4cbceb9..7a8ef705b 100644 --- a/data/icons/Default/items/down.svg +++ b/data/icons/Default/items/down.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/encrypted.svg b/data/icons/Default/items/encrypted.svg index a0d03075a..28686fe94 100644 --- a/data/icons/Default/items/encrypted.svg +++ b/data/icons/Default/items/encrypted.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/error.svg b/data/icons/Default/items/error.svg index 2005dc8ab..f4974c0b4 100644 --- a/data/icons/Default/items/error.svg +++ b/data/icons/Default/items/error.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/file_new.svg b/data/icons/Default/items/file_new.svg index d3b661b05..7f4e870c5 100644 --- a/data/icons/Default/items/file_new.svg +++ b/data/icons/Default/items/file_new.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/file_print.svg b/data/icons/Default/items/file_print.svg index 1b593f1b4..b12add6a9 100644 --- a/data/icons/Default/items/file_print.svg +++ b/data/icons/Default/items/file_print.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/find.svg b/data/icons/Default/items/find.svg index 32acace37..8ce46c694 100644 --- a/data/icons/Default/items/find.svg +++ b/data/icons/Default/items/find.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/font_size.svg b/data/icons/Default/items/font_size.svg index facc2b31e..b18d9a7f1 100644 --- a/data/icons/Default/items/font_size.svg +++ b/data/icons/Default/items/font_size.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/forward.svg b/data/icons/Default/items/forward.svg index b5a7f2ebf..a2027b75e 100644 --- a/data/icons/Default/items/forward.svg +++ b/data/icons/Default/items/forward.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/fullscreen.svg b/data/icons/Default/items/fullscreen.svg index e30d16446..ef9f095a5 100644 --- a/data/icons/Default/items/fullscreen.svg +++ b/data/icons/Default/items/fullscreen.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/goto.svg b/data/icons/Default/items/goto.svg index 20d538f6f..94599c24f 100644 --- a/data/icons/Default/items/goto.svg +++ b/data/icons/Default/items/goto.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/help.svg b/data/icons/Default/items/help.svg index 78cbcf7c2..fec86b547 100644 --- a/data/icons/Default/items/help.svg +++ b/data/icons/Default/items/help.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/home_question.svg b/data/icons/Default/items/home_question.svg index a7961361a..f88592f5c 100644 --- a/data/icons/Default/items/home_question.svg +++ b/data/icons/Default/items/home_question.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/idea.svg b/data/icons/Default/items/idea.svg index 0fa024a68..b0cb8ace3 100644 --- a/data/icons/Default/items/idea.svg +++ b/data/icons/Default/items/idea.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/info.svg b/data/icons/Default/items/info.svg index 736f4f745..de4d86d5b 100644 --- a/data/icons/Default/items/info.svg +++ b/data/icons/Default/items/info.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/info_plain.svg b/data/icons/Default/items/info_plain.svg index ec8913789..feb5300e5 100644 --- a/data/icons/Default/items/info_plain.svg +++ b/data/icons/Default/items/info_plain.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/launch.svg b/data/icons/Default/items/launch.svg index d13e1938e..faff20cf1 100644 --- a/data/icons/Default/items/launch.svg +++ b/data/icons/Default/items/launch.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/link.svg b/data/icons/Default/items/link.svg index cbd00003e..1380b6cc1 100644 --- a/data/icons/Default/items/link.svg +++ b/data/icons/Default/items/link.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/locale.svg b/data/icons/Default/items/locale.svg index b175c4c4f..f6ec5a052 100644 --- a/data/icons/Default/items/locale.svg +++ b/data/icons/Default/items/locale.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/lock.svg b/data/icons/Default/items/lock.svg index 7b645f10e..6bfc646f5 100644 --- a/data/icons/Default/items/lock.svg +++ b/data/icons/Default/items/lock.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/minus.svg b/data/icons/Default/items/minus.svg index 06e20487e..1b2d70072 100644 --- a/data/icons/Default/items/minus.svg +++ b/data/icons/Default/items/minus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/new.svg b/data/icons/Default/items/new.svg index 998b071ad..c3ed5959c 100644 --- a/data/icons/Default/items/new.svg +++ b/data/icons/Default/items/new.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/notification.svg b/data/icons/Default/items/notification.svg index c2050834d..8a954f1aa 100644 --- a/data/icons/Default/items/notification.svg +++ b/data/icons/Default/items/notification.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/notification_above.svg b/data/icons/Default/items/notification_above.svg index 0b11064f2..0adcc4f7d 100644 --- a/data/icons/Default/items/notification_above.svg +++ b/data/icons/Default/items/notification_above.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/notification_above_multiple.svg b/data/icons/Default/items/notification_above_multiple.svg index af72097e0..bcf20d499 100644 --- a/data/icons/Default/items/notification_above_multiple.svg +++ b/data/icons/Default/items/notification_above_multiple.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/notification_multiple.svg b/data/icons/Default/items/notification_multiple.svg index 382b00736..c750a9349 100644 --- a/data/icons/Default/items/notification_multiple.svg +++ b/data/icons/Default/items/notification_multiple.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/notification_star.svg b/data/icons/Default/items/notification_star.svg index 7c9d974a0..48e7000f0 100644 --- a/data/icons/Default/items/notification_star.svg +++ b/data/icons/Default/items/notification_star.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/player_eject.svg b/data/icons/Default/items/player_eject.svg index c1f7919a0..9be9c3c3d 100644 --- a/data/icons/Default/items/player_eject.svg +++ b/data/icons/Default/items/player_eject.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/player_forward.svg b/data/icons/Default/items/player_forward.svg index 45df1e35e..eb7e31c19 100644 --- a/data/icons/Default/items/player_forward.svg +++ b/data/icons/Default/items/player_forward.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/player_guide.svg b/data/icons/Default/items/player_guide.svg index 868740f06..13cea3b27 100644 --- a/data/icons/Default/items/player_guide.svg +++ b/data/icons/Default/items/player_guide.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/player_loop.svg b/data/icons/Default/items/player_loop.svg index ca7d0dfe6..edb47465a 100644 --- a/data/icons/Default/items/player_loop.svg +++ b/data/icons/Default/items/player_loop.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/player_next.svg b/data/icons/Default/items/player_next.svg index 4700669fc..21f5c4989 100644 --- a/data/icons/Default/items/player_next.svg +++ b/data/icons/Default/items/player_next.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/player_pause.svg b/data/icons/Default/items/player_pause.svg index f4f70928e..2a353cc21 100644 --- a/data/icons/Default/items/player_pause.svg +++ b/data/icons/Default/items/player_pause.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/player_play.svg b/data/icons/Default/items/player_play.svg index 7a9b0b0dd..21097a69a 100644 --- a/data/icons/Default/items/player_play.svg +++ b/data/icons/Default/items/player_play.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/player_prev.svg b/data/icons/Default/items/player_prev.svg index 29485b930..11c0bd356 100644 --- a/data/icons/Default/items/player_prev.svg +++ b/data/icons/Default/items/player_prev.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/player_repeat.svg b/data/icons/Default/items/player_repeat.svg index f0904eda4..7466f5f8f 100644 --- a/data/icons/Default/items/player_repeat.svg +++ b/data/icons/Default/items/player_repeat.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/player_resume.svg b/data/icons/Default/items/player_resume.svg index 06ac0d71a..a9d229c1d 100644 --- a/data/icons/Default/items/player_resume.svg +++ b/data/icons/Default/items/player_resume.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/player_rewind.svg b/data/icons/Default/items/player_rewind.svg index 079c9bf74..1e73e5ea1 100644 --- a/data/icons/Default/items/player_rewind.svg +++ b/data/icons/Default/items/player_rewind.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/player_shuffle.svg b/data/icons/Default/items/player_shuffle.svg index 6fbedb819..8a5379a0b 100644 --- a/data/icons/Default/items/player_shuffle.svg +++ b/data/icons/Default/items/player_shuffle.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/player_stop.svg b/data/icons/Default/items/player_stop.svg index 6eda46476..6b41e813a 100644 --- a/data/icons/Default/items/player_stop.svg +++ b/data/icons/Default/items/player_stop.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/qr.svg b/data/icons/Default/items/qr.svg index 8e54279ed..a4212a94d 100644 --- a/data/icons/Default/items/qr.svg +++ b/data/icons/Default/items/qr.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/question.svg b/data/icons/Default/items/question.svg index 75e36f9e9..10c3012fa 100644 --- a/data/icons/Default/items/question.svg +++ b/data/icons/Default/items/question.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/quit.svg b/data/icons/Default/items/quit.svg index 44fd51eb7..ced19148b 100644 --- a/data/icons/Default/items/quit.svg +++ b/data/icons/Default/items/quit.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/redo.svg b/data/icons/Default/items/redo.svg index 0d88f7fcb..d41dcfb56 100644 --- a/data/icons/Default/items/redo.svg +++ b/data/icons/Default/items/redo.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/reload.svg b/data/icons/Default/items/reload.svg index ee23fbfea..bd8d3aeaa 100644 --- a/data/icons/Default/items/reload.svg +++ b/data/icons/Default/items/reload.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/return.svg b/data/icons/Default/items/return.svg index 68c16ce55..44b4c76b5 100644 --- a/data/icons/Default/items/return.svg +++ b/data/icons/Default/items/return.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/securityoff.svg b/data/icons/Default/items/securityoff.svg index 7c67d35dc..6ac8ab99f 100644 --- a/data/icons/Default/items/securityoff.svg +++ b/data/icons/Default/items/securityoff.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/securityon.svg b/data/icons/Default/items/securityon.svg index 7b645f10e..6bfc646f5 100644 --- a/data/icons/Default/items/securityon.svg +++ b/data/icons/Default/items/securityon.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/star.svg b/data/icons/Default/items/star.svg index 9037b4b53..66369c5c9 100644 --- a/data/icons/Default/items/star.svg +++ b/data/icons/Default/items/star.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/star_add.svg b/data/icons/Default/items/star_add.svg index 843390252..28e68cbca 100644 --- a/data/icons/Default/items/star_add.svg +++ b/data/icons/Default/items/star_add.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/star_minus.svg b/data/icons/Default/items/star_minus.svg index 8203dc50b..ad3a9ac19 100644 --- a/data/icons/Default/items/star_minus.svg +++ b/data/icons/Default/items/star_minus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/stop.svg b/data/icons/Default/items/stop.svg index 5eb215a0a..d21bbdd12 100644 --- a/data/icons/Default/items/stop.svg +++ b/data/icons/Default/items/stop.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/stream.svg b/data/icons/Default/items/stream.svg index 1c0225a3b..a17287f2d 100644 --- a/data/icons/Default/items/stream.svg +++ b/data/icons/Default/items/stream.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/thumbs_down.svg b/data/icons/Default/items/thumbs_down.svg index a13fc5b3d..4aeea1e4e 100644 --- a/data/icons/Default/items/thumbs_down.svg +++ b/data/icons/Default/items/thumbs_down.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/thumbs_up.svg b/data/icons/Default/items/thumbs_up.svg index 7552de9f0..657e44a80 100644 --- a/data/icons/Default/items/thumbs_up.svg +++ b/data/icons/Default/items/thumbs_up.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/trash.svg b/data/icons/Default/items/trash.svg index bc61dd569..b2e404060 100644 --- a/data/icons/Default/items/trash.svg +++ b/data/icons/Default/items/trash.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/undo.svg b/data/icons/Default/items/undo.svg index 2af4b79a0..a851e4233 100644 --- a/data/icons/Default/items/undo.svg +++ b/data/icons/Default/items/undo.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/unlock.svg b/data/icons/Default/items/unlock.svg index 7c67d35dc..6ac8ab99f 100644 --- a/data/icons/Default/items/unlock.svg +++ b/data/icons/Default/items/unlock.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/warning.svg b/data/icons/Default/items/warning.svg index 2005dc8ab..f4974c0b4 100644 --- a/data/icons/Default/items/warning.svg +++ b/data/icons/Default/items/warning.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/whatis.svg b/data/icons/Default/items/whatis.svg index 0dc6572bc..634170949 100644 --- a/data/icons/Default/items/whatis.svg +++ b/data/icons/Default/items/whatis.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/window_maximise.svg b/data/icons/Default/items/window_maximise.svg index 66459fe44..a38231702 100644 --- a/data/icons/Default/items/window_maximise.svg +++ b/data/icons/Default/items/window_maximise.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/window_minimise.svg b/data/icons/Default/items/window_minimise.svg index d09bf6f17..e9002e57d 100644 --- a/data/icons/Default/items/window_minimise.svg +++ b/data/icons/Default/items/window_minimise.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/window_restore.svg b/data/icons/Default/items/window_restore.svg index 3942b7313..69169d0a0 100644 --- a/data/icons/Default/items/window_restore.svg +++ b/data/icons/Default/items/window_restore.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/items/yes_no.svg b/data/icons/Default/items/yes_no.svg index c2b83411a..64e528c85 100644 --- a/data/icons/Default/items/yes_no.svg +++ b/data/icons/Default/items/yes_no.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layer/add.svg b/data/icons/Default/layer/add.svg index 9f3c37571..eff74eb2c 100644 --- a/data/icons/Default/layer/add.svg +++ b/data/icons/Default/layer/add.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layer/bringforward.svg b/data/icons/Default/layer/bringforward.svg index 7a0ff03ba..5c48623c2 100644 --- a/data/icons/Default/layer/bringforward.svg +++ b/data/icons/Default/layer/bringforward.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layer/bringtofront.svg b/data/icons/Default/layer/bringtofront.svg index d8146dd5b..f588ee43f 100644 --- a/data/icons/Default/layer/bringtofront.svg +++ b/data/icons/Default/layer/bringtofront.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layer/delete.svg b/data/icons/Default/layer/delete.svg index 7a5deba74..def797d43 100644 --- a/data/icons/Default/layer/delete.svg +++ b/data/icons/Default/layer/delete.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layer/down.svg b/data/icons/Default/layer/down.svg index ff1cdb83f..b570f86ab 100644 --- a/data/icons/Default/layer/down.svg +++ b/data/icons/Default/layer/down.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layer/layers.svg b/data/icons/Default/layer/layers.svg index fbd8a584b..87aae616c 100644 --- a/data/icons/Default/layer/layers.svg +++ b/data/icons/Default/layer/layers.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layer/layers_thick.svg b/data/icons/Default/layer/layers_thick.svg index 49219ef3c..66091e446 100644 --- a/data/icons/Default/layer/layers_thick.svg +++ b/data/icons/Default/layer/layers_thick.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layer/minus.svg b/data/icons/Default/layer/minus.svg index e82ab0ff1..4fc6bed67 100644 --- a/data/icons/Default/layer/minus.svg +++ b/data/icons/Default/layer/minus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layer/perspective_up.svg b/data/icons/Default/layer/perspective_up.svg index 291c69000..fa38d1cbe 100644 --- a/data/icons/Default/layer/perspective_up.svg +++ b/data/icons/Default/layer/perspective_up.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layer/sendbackward.svg b/data/icons/Default/layer/sendbackward.svg index bdec768ce..fb6395a01 100644 --- a/data/icons/Default/layer/sendbackward.svg +++ b/data/icons/Default/layer/sendbackward.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layer/sendtoback.svg b/data/icons/Default/layer/sendtoback.svg index 412c68aca..d8c0f71c4 100644 --- a/data/icons/Default/layer/sendtoback.svg +++ b/data/icons/Default/layer/sendtoback.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layer/solid_bringforward.svg b/data/icons/Default/layer/solid_bringforward.svg index ccdae59de..47fd42cb7 100644 --- a/data/icons/Default/layer/solid_bringforward.svg +++ b/data/icons/Default/layer/solid_bringforward.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layer/solid_bringtofront.svg b/data/icons/Default/layer/solid_bringtofront.svg index e5a7e4f82..1b8b17df1 100644 --- a/data/icons/Default/layer/solid_bringtofront.svg +++ b/data/icons/Default/layer/solid_bringtofront.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layer/solid_sendbackward.svg b/data/icons/Default/layer/solid_sendbackward.svg index b43c4ad97..18c03a5be 100644 --- a/data/icons/Default/layer/solid_sendbackward.svg +++ b/data/icons/Default/layer/solid_sendbackward.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layer/solid_sendtoback.svg b/data/icons/Default/layer/solid_sendtoback.svg index ea1bf5c54..56a49a2e7 100644 --- a/data/icons/Default/layer/solid_sendtoback.svg +++ b/data/icons/Default/layer/solid_sendtoback.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layer/up.svg b/data/icons/Default/layer/up.svg index 1aef4e1f6..460072c72 100644 --- a/data/icons/Default/layer/up.svg +++ b/data/icons/Default/layer/up.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/align_center.svg b/data/icons/Default/layout/align_center.svg index bcf495b28..9a2241787 100644 --- a/data/icons/Default/layout/align_center.svg +++ b/data/icons/Default/layout/align_center.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/align_justify.svg b/data/icons/Default/layout/align_justify.svg index abb0c2be8..8c86515b9 100644 --- a/data/icons/Default/layout/align_justify.svg +++ b/data/icons/Default/layout/align_justify.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/align_left.svg b/data/icons/Default/layout/align_left.svg index 685a0e96d..8245b167f 100644 --- a/data/icons/Default/layout/align_left.svg +++ b/data/icons/Default/layout/align_left.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/align_right.svg b/data/icons/Default/layout/align_right.svg index 236df18e0..087f67951 100644 --- a/data/icons/Default/layout/align_right.svg +++ b/data/icons/Default/layout/align_right.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/box_height.svg b/data/icons/Default/layout/box_height.svg index 6c6469773..d24c55a18 100644 --- a/data/icons/Default/layout/box_height.svg +++ b/data/icons/Default/layout/box_height.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/box_width.svg b/data/icons/Default/layout/box_width.svg index 5aee88f1f..75d6c026d 100644 --- a/data/icons/Default/layout/box_width.svg +++ b/data/icons/Default/layout/box_width.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/cell_align.svg b/data/icons/Default/layout/cell_align.svg index a553371cc..dea690ba4 100644 --- a/data/icons/Default/layout/cell_align.svg +++ b/data/icons/Default/layout/cell_align.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/cell_column_delete.svg b/data/icons/Default/layout/cell_column_delete.svg index e909ab225..08518e233 100644 --- a/data/icons/Default/layout/cell_column_delete.svg +++ b/data/icons/Default/layout/cell_column_delete.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/cell_down.svg b/data/icons/Default/layout/cell_down.svg index 869bc20b8..5abf898dc 100644 --- a/data/icons/Default/layout/cell_down.svg +++ b/data/icons/Default/layout/cell_down.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/cell_function.svg b/data/icons/Default/layout/cell_function.svg index 8324a1866..ae9116ed6 100644 --- a/data/icons/Default/layout/cell_function.svg +++ b/data/icons/Default/layout/cell_function.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/cell_insert_above.svg b/data/icons/Default/layout/cell_insert_above.svg index e382df781..f8a6f8a8c 100644 --- a/data/icons/Default/layout/cell_insert_above.svg +++ b/data/icons/Default/layout/cell_insert_above.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/cell_insert_below.svg b/data/icons/Default/layout/cell_insert_below.svg index bf8636221..08156cf57 100644 --- a/data/icons/Default/layout/cell_insert_below.svg +++ b/data/icons/Default/layout/cell_insert_below.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/cell_merge.svg b/data/icons/Default/layout/cell_merge.svg index 82de2256f..fb56e69f8 100644 --- a/data/icons/Default/layout/cell_merge.svg +++ b/data/icons/Default/layout/cell_merge.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/cell_row_delete.svg b/data/icons/Default/layout/cell_row_delete.svg index eb76e48c2..2446dfa11 100644 --- a/data/icons/Default/layout/cell_row_delete.svg +++ b/data/icons/Default/layout/cell_row_delete.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/cell_up.svg b/data/icons/Default/layout/cell_up.svg index efee987d5..f4249bfc2 100644 --- a/data/icons/Default/layout/cell_up.svg +++ b/data/icons/Default/layout/cell_up.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/collapse.svg b/data/icons/Default/layout/collapse.svg index 6b93e19ea..f4662cd63 100644 --- a/data/icons/Default/layout/collapse.svg +++ b/data/icons/Default/layout/collapse.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/column_one.svg b/data/icons/Default/layout/column_one.svg index 1c3cf80ea..6a44733d9 100644 --- a/data/icons/Default/layout/column_one.svg +++ b/data/icons/Default/layout/column_one.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/column_three.svg b/data/icons/Default/layout/column_three.svg index 78c1a7045..cd5a5daf8 100644 --- a/data/icons/Default/layout/column_three.svg +++ b/data/icons/Default/layout/column_three.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/column_two.svg b/data/icons/Default/layout/column_two.svg index d1752dfeb..1c916de70 100644 --- a/data/icons/Default/layout/column_two.svg +++ b/data/icons/Default/layout/column_two.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/diagram.svg b/data/icons/Default/layout/diagram.svg index 9e7d57af1..ee206303f 100644 --- a/data/icons/Default/layout/diagram.svg +++ b/data/icons/Default/layout/diagram.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/expand.svg b/data/icons/Default/layout/expand.svg index 722dd7eec..0cdbcd700 100644 --- a/data/icons/Default/layout/expand.svg +++ b/data/icons/Default/layout/expand.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/form_basic.svg b/data/icons/Default/layout/form_basic.svg index 03e5f2fa7..cb18eb108 100644 --- a/data/icons/Default/layout/form_basic.svg +++ b/data/icons/Default/layout/form_basic.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/form_editable.svg b/data/icons/Default/layout/form_editable.svg index 2b8227d8e..4b984bce5 100644 --- a/data/icons/Default/layout/form_editable.svg +++ b/data/icons/Default/layout/form_editable.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/grid.svg b/data/icons/Default/layout/grid.svg index 0d54a06c7..212373e41 100644 --- a/data/icons/Default/layout/grid.svg +++ b/data/icons/Default/layout/grid.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/input_box.svg b/data/icons/Default/layout/input_box.svg index d6d464dd1..712561e7e 100644 --- a/data/icons/Default/layout/input_box.svg +++ b/data/icons/Default/layout/input_box.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/input_pen.svg b/data/icons/Default/layout/input_pen.svg index 6021781fc..4a49cadfe 100644 --- a/data/icons/Default/layout/input_pen.svg +++ b/data/icons/Default/layout/input_pen.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/input_question.svg b/data/icons/Default/layout/input_question.svg index 84eb63988..0e3c94f88 100644 --- a/data/icons/Default/layout/input_question.svg +++ b/data/icons/Default/layout/input_question.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/interface_button.svg b/data/icons/Default/layout/interface_button.svg index 89e7a9699..30c18992d 100644 --- a/data/icons/Default/layout/interface_button.svg +++ b/data/icons/Default/layout/interface_button.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/interface_dropdown.svg b/data/icons/Default/layout/interface_dropdown.svg index 241d57905..6372c8a1c 100644 --- a/data/icons/Default/layout/interface_dropdown.svg +++ b/data/icons/Default/layout/interface_dropdown.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/interface_list.svg b/data/icons/Default/layout/interface_list.svg index e47dbb7b1..1f94a8221 100644 --- a/data/icons/Default/layout/interface_list.svg +++ b/data/icons/Default/layout/interface_list.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/interface_password.svg b/data/icons/Default/layout/interface_password.svg index 247b577b4..dec1a1457 100644 --- a/data/icons/Default/layout/interface_password.svg +++ b/data/icons/Default/layout/interface_password.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/interface_textbox.svg b/data/icons/Default/layout/interface_textbox.svg index 72e1fa8be..af71e64c4 100644 --- a/data/icons/Default/layout/interface_textbox.svg +++ b/data/icons/Default/layout/interface_textbox.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/layout.svg b/data/icons/Default/layout/layout.svg index 8a9b5494d..4af48d5c9 100644 --- a/data/icons/Default/layout/layout.svg +++ b/data/icons/Default/layout/layout.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/layout_body.svg b/data/icons/Default/layout/layout_body.svg index 0c1cec425..4e18ff6fb 100644 --- a/data/icons/Default/layout/layout_body.svg +++ b/data/icons/Default/layout/layout_body.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/layout_collapse_left.svg b/data/icons/Default/layout/layout_collapse_left.svg index 4da4d1714..fef26fd07 100644 --- a/data/icons/Default/layout/layout_collapse_left.svg +++ b/data/icons/Default/layout/layout_collapse_left.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/layout_collapse_left_variant.svg b/data/icons/Default/layout/layout_collapse_left_variant.svg index 2c858490f..d9ad63183 100644 --- a/data/icons/Default/layout/layout_collapse_left_variant.svg +++ b/data/icons/Default/layout/layout_collapse_left_variant.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/layout_collapse_right.svg b/data/icons/Default/layout/layout_collapse_right.svg index 4b249767e..1f38e90ca 100644 --- a/data/icons/Default/layout/layout_collapse_right.svg +++ b/data/icons/Default/layout/layout_collapse_right.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/layout_collapse_right_variant.svg b/data/icons/Default/layout/layout_collapse_right_variant.svg index 8fa6a96bb..582dac2b5 100644 --- a/data/icons/Default/layout/layout_collapse_right_variant.svg +++ b/data/icons/Default/layout/layout_collapse_right_variant.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/layout_expand_left.svg b/data/icons/Default/layout/layout_expand_left.svg index 7cd3552d2..8e900eb00 100644 --- a/data/icons/Default/layout/layout_expand_left.svg +++ b/data/icons/Default/layout/layout_expand_left.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/layout_expand_left_variant.svg b/data/icons/Default/layout/layout_expand_left_variant.svg index 65421dca9..fe40b74c8 100644 --- a/data/icons/Default/layout/layout_expand_left_variant.svg +++ b/data/icons/Default/layout/layout_expand_left_variant.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/layout_expand_right.svg b/data/icons/Default/layout/layout_expand_right.svg index bcb400ace..6abf3f007 100644 --- a/data/icons/Default/layout/layout_expand_right.svg +++ b/data/icons/Default/layout/layout_expand_right.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/layout_expand_right_variant.svg b/data/icons/Default/layout/layout_expand_right_variant.svg index 3d1828873..70e3bab37 100644 --- a/data/icons/Default/layout/layout_expand_right_variant.svg +++ b/data/icons/Default/layout/layout_expand_right_variant.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/layout_header.svg b/data/icons/Default/layout/layout_header.svg index b4796e8a9..abda4588f 100644 --- a/data/icons/Default/layout/layout_header.svg +++ b/data/icons/Default/layout/layout_header.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/layout_sidebar.svg b/data/icons/Default/layout/layout_sidebar.svg index 56897d9e7..b4620dd46 100644 --- a/data/icons/Default/layout/layout_sidebar.svg +++ b/data/icons/Default/layout/layout_sidebar.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/line_height.svg b/data/icons/Default/layout/line_height.svg index f0ab2a0d5..bf4df1f59 100644 --- a/data/icons/Default/layout/line_height.svg +++ b/data/icons/Default/layout/line_height.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/line_height_short.svg b/data/icons/Default/layout/line_height_short.svg index 8d4d1a632..f05490184 100644 --- a/data/icons/Default/layout/line_height_short.svg +++ b/data/icons/Default/layout/line_height_short.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/line_width.svg b/data/icons/Default/layout/line_width.svg index 94ef45291..86dc85115 100644 --- a/data/icons/Default/layout/line_width.svg +++ b/data/icons/Default/layout/line_width.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/line_width_short.svg b/data/icons/Default/layout/line_width_short.svg index 42aceae8f..6f37c4634 100644 --- a/data/icons/Default/layout/line_width_short.svg +++ b/data/icons/Default/layout/line_width_short.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/lines_horizontal_4.svg b/data/icons/Default/layout/lines_horizontal_4.svg index 8e27d50cd..10722de2d 100644 --- a/data/icons/Default/layout/lines_horizontal_4.svg +++ b/data/icons/Default/layout/lines_horizontal_4.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list.svg b/data/icons/Default/layout/list.svg index 29d34929e..9d5234e8b 100644 --- a/data/icons/Default/layout/list.svg +++ b/data/icons/Default/layout/list.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list_add.svg b/data/icons/Default/layout/list_add.svg index b9fbde399..2e8f26bda 100644 --- a/data/icons/Default/layout/list_add.svg +++ b/data/icons/Default/layout/list_add.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list_add_above.svg b/data/icons/Default/layout/list_add_above.svg index 481309ccc..db5978d02 100644 --- a/data/icons/Default/layout/list_add_above.svg +++ b/data/icons/Default/layout/list_add_above.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list_add_below.svg b/data/icons/Default/layout/list_add_below.svg index c0b3f01cf..e3fba23c1 100644 --- a/data/icons/Default/layout/list_add_below.svg +++ b/data/icons/Default/layout/list_add_below.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list_check.svg b/data/icons/Default/layout/list_check.svg index 9e72a6aae..b390b674c 100644 --- a/data/icons/Default/layout/list_check.svg +++ b/data/icons/Default/layout/list_check.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list_create.svg b/data/icons/Default/layout/list_create.svg index c8d48b183..906cd878c 100644 --- a/data/icons/Default/layout/list_create.svg +++ b/data/icons/Default/layout/list_create.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list_delete.svg b/data/icons/Default/layout/list_delete.svg index 3c163085c..769eaf578 100644 --- a/data/icons/Default/layout/list_delete.svg +++ b/data/icons/Default/layout/list_delete.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list_delete_inline.svg b/data/icons/Default/layout/list_delete_inline.svg index 9c7f4f8d2..e389858a7 100644 --- a/data/icons/Default/layout/list_delete_inline.svg +++ b/data/icons/Default/layout/list_delete_inline.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list_gear.svg b/data/icons/Default/layout/list_gear.svg index e8202b0e1..16b355227 100644 --- a/data/icons/Default/layout/list_gear.svg +++ b/data/icons/Default/layout/list_gear.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list_hidden.svg b/data/icons/Default/layout/list_hidden.svg index 3ff32a432..ed6970a35 100644 --- a/data/icons/Default/layout/list_hidden.svg +++ b/data/icons/Default/layout/list_hidden.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list_merge.svg b/data/icons/Default/layout/list_merge.svg index 81aae0921..b839c8f14 100644 --- a/data/icons/Default/layout/list_merge.svg +++ b/data/icons/Default/layout/list_merge.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list_one.svg b/data/icons/Default/layout/list_one.svg index 8acff7d43..e6eb1c0bf 100644 --- a/data/icons/Default/layout/list_one.svg +++ b/data/icons/Default/layout/list_one.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list_reorder.svg b/data/icons/Default/layout/list_reorder.svg index 074d4ff6d..77f5d236f 100644 --- a/data/icons/Default/layout/list_reorder.svg +++ b/data/icons/Default/layout/list_reorder.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list_reorder_down.svg b/data/icons/Default/layout/list_reorder_down.svg index 226e5db42..8b6cec011 100644 --- a/data/icons/Default/layout/list_reorder_down.svg +++ b/data/icons/Default/layout/list_reorder_down.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list_reorder_up.svg b/data/icons/Default/layout/list_reorder_up.svg index 82f7a0b5e..d85a14ed5 100644 --- a/data/icons/Default/layout/list_reorder_up.svg +++ b/data/icons/Default/layout/list_reorder_up.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list_select.svg b/data/icons/Default/layout/list_select.svg index 14daed26d..6568bb8e1 100644 --- a/data/icons/Default/layout/list_select.svg +++ b/data/icons/Default/layout/list_select.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list_star.svg b/data/icons/Default/layout/list_star.svg index 91a6cb592..899880b65 100644 --- a/data/icons/Default/layout/list_star.svg +++ b/data/icons/Default/layout/list_star.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/list_two.svg b/data/icons/Default/layout/list_two.svg index 96d6fe876..30c9b7377 100644 --- a/data/icons/Default/layout/list_two.svg +++ b/data/icons/Default/layout/list_two.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/section_collapse.svg b/data/icons/Default/layout/section_collapse.svg index 2d3ce3094..45404b4a6 100644 --- a/data/icons/Default/layout/section_collapse.svg +++ b/data/icons/Default/layout/section_collapse.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/section_collapse_all.svg b/data/icons/Default/layout/section_collapse_all.svg index 38045e041..ad9ef4c1b 100644 --- a/data/icons/Default/layout/section_collapse_all.svg +++ b/data/icons/Default/layout/section_collapse_all.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/section_expand.svg b/data/icons/Default/layout/section_expand.svg index 700dd3ab3..b54313369 100644 --- a/data/icons/Default/layout/section_expand.svg +++ b/data/icons/Default/layout/section_expand.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/section_expand_all.svg b/data/icons/Default/layout/section_expand_all.svg index 7a4eb234e..bba61b5ad 100644 --- a/data/icons/Default/layout/section_expand_all.svg +++ b/data/icons/Default/layout/section_expand_all.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/sidebar_left_collapse.svg b/data/icons/Default/layout/sidebar_left_collapse.svg index 312cca859..bdbd59074 100644 --- a/data/icons/Default/layout/sidebar_left_collapse.svg +++ b/data/icons/Default/layout/sidebar_left_collapse.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/sidebar_left_expand.svg b/data/icons/Default/layout/sidebar_left_expand.svg index 7266d7830..baa8484f9 100644 --- a/data/icons/Default/layout/sidebar_left_expand.svg +++ b/data/icons/Default/layout/sidebar_left_expand.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/sidebar_right_collapse.svg b/data/icons/Default/layout/sidebar_right_collapse.svg index 4d7daed69..3fcdc43a4 100644 --- a/data/icons/Default/layout/sidebar_right_collapse.svg +++ b/data/icons/Default/layout/sidebar_right_collapse.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/sidebar_right_expand.svg b/data/icons/Default/layout/sidebar_right_expand.svg index 9215dca00..16ad80dc8 100644 --- a/data/icons/Default/layout/sidebar_right_expand.svg +++ b/data/icons/Default/layout/sidebar_right_expand.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/sort.svg b/data/icons/Default/layout/sort.svg index 36994dec9..bde7d1a49 100644 --- a/data/icons/Default/layout/sort.svg +++ b/data/icons/Default/layout/sort.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/sort_alpha.svg b/data/icons/Default/layout/sort_alpha.svg index 20c7f09e0..91f87e086 100644 --- a/data/icons/Default/layout/sort_alpha.svg +++ b/data/icons/Default/layout/sort_alpha.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/sort_alpha_asc.svg b/data/icons/Default/layout/sort_alpha_asc.svg index f4bb4a02a..749b1f316 100644 --- a/data/icons/Default/layout/sort_alpha_asc.svg +++ b/data/icons/Default/layout/sort_alpha_asc.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/sort_alpha_desc.svg b/data/icons/Default/layout/sort_alpha_desc.svg index 445b64a0a..3ed48b4b0 100644 --- a/data/icons/Default/layout/sort_alpha_desc.svg +++ b/data/icons/Default/layout/sort_alpha_desc.svg @@ -1,7 +1,7 @@  - - - + + + diff --git a/data/icons/Default/layout/swap.svg b/data/icons/Default/layout/swap.svg index 33e8644ec..ce0929d10 100644 --- a/data/icons/Default/layout/swap.svg +++ b/data/icons/Default/layout/swap.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/table.svg b/data/icons/Default/layout/table.svg index 025eee606..3f6c96aec 100644 --- a/data/icons/Default/layout/table.svg +++ b/data/icons/Default/layout/table.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/table_add.svg b/data/icons/Default/layout/table_add.svg index 0e7a290b9..d2d03e265 100644 --- a/data/icons/Default/layout/table_add.svg +++ b/data/icons/Default/layout/table_add.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/table_delete.svg b/data/icons/Default/layout/table_delete.svg index 66edb3252..afa31d36f 100644 --- a/data/icons/Default/layout/table_delete.svg +++ b/data/icons/Default/layout/table_delete.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/table_select.svg b/data/icons/Default/layout/table_select.svg index ccc332eab..8a42a5e43 100644 --- a/data/icons/Default/layout/table_select.svg +++ b/data/icons/Default/layout/table_select.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/table_unselect.svg b/data/icons/Default/layout/table_unselect.svg index 1e1f6e7c5..bfc612d7c 100644 --- a/data/icons/Default/layout/table_unselect.svg +++ b/data/icons/Default/layout/table_unselect.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/text_bold.svg b/data/icons/Default/layout/text_bold.svg index aaa8ee018..be326b8d9 100644 --- a/data/icons/Default/layout/text_bold.svg +++ b/data/icons/Default/layout/text_bold.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/text_italic.svg b/data/icons/Default/layout/text_italic.svg index 9fcc29943..ff13fefa0 100644 --- a/data/icons/Default/layout/text_italic.svg +++ b/data/icons/Default/layout/text_italic.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/text_overline.svg b/data/icons/Default/layout/text_overline.svg index d9e85faa0..dd139fc10 100644 --- a/data/icons/Default/layout/text_overline.svg +++ b/data/icons/Default/layout/text_overline.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/text_sans.svg b/data/icons/Default/layout/text_sans.svg index a2c1403af..302adb6e1 100644 --- a/data/icons/Default/layout/text_sans.svg +++ b/data/icons/Default/layout/text_sans.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/text_script.svg b/data/icons/Default/layout/text_script.svg index 4d4e436a1..7986747c6 100644 --- a/data/icons/Default/layout/text_script.svg +++ b/data/icons/Default/layout/text_script.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/text_serif.svg b/data/icons/Default/layout/text_serif.svg index ddffde2a1..330b9281b 100644 --- a/data/icons/Default/layout/text_serif.svg +++ b/data/icons/Default/layout/text_serif.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/text_size.svg b/data/icons/Default/layout/text_size.svg index facc2b31e..b18d9a7f1 100644 --- a/data/icons/Default/layout/text_size.svg +++ b/data/icons/Default/layout/text_size.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/text_size_down.svg b/data/icons/Default/layout/text_size_down.svg index a48d4a3c6..f0ed8aed0 100644 --- a/data/icons/Default/layout/text_size_down.svg +++ b/data/icons/Default/layout/text_size_down.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/text_size_minus.svg b/data/icons/Default/layout/text_size_minus.svg index d707c1a85..9b5e5cdd9 100644 --- a/data/icons/Default/layout/text_size_minus.svg +++ b/data/icons/Default/layout/text_size_minus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/text_size_plus.svg b/data/icons/Default/layout/text_size_plus.svg index 3e7d75dc0..b1291abdf 100644 --- a/data/icons/Default/layout/text_size_plus.svg +++ b/data/icons/Default/layout/text_size_plus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/text_size_up.svg b/data/icons/Default/layout/text_size_up.svg index 026373782..f75ddb808 100644 --- a/data/icons/Default/layout/text_size_up.svg +++ b/data/icons/Default/layout/text_size_up.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/text_strikethrough.svg b/data/icons/Default/layout/text_strikethrough.svg index 096f1061d..d337f0f24 100644 --- a/data/icons/Default/layout/text_strikethrough.svg +++ b/data/icons/Default/layout/text_strikethrough.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/text_underline.svg b/data/icons/Default/layout/text_underline.svg index 30995426e..157326efa 100644 --- a/data/icons/Default/layout/text_underline.svg +++ b/data/icons/Default/layout/text_underline.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/tiles_four.svg b/data/icons/Default/layout/tiles_four.svg index 03e62fb07..38d9975a8 100644 --- a/data/icons/Default/layout/tiles_four.svg +++ b/data/icons/Default/layout/tiles_four.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/tiles_minus.svg b/data/icons/Default/layout/tiles_minus.svg index 42f983936..eedf4850c 100644 --- a/data/icons/Default/layout/tiles_minus.svg +++ b/data/icons/Default/layout/tiles_minus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/tiles_nine.svg b/data/icons/Default/layout/tiles_nine.svg index 5cb750cd6..7b0c5cef2 100644 --- a/data/icons/Default/layout/tiles_nine.svg +++ b/data/icons/Default/layout/tiles_nine.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/tiles_plus.svg b/data/icons/Default/layout/tiles_plus.svg index 30632a4f2..d5adeef71 100644 --- a/data/icons/Default/layout/tiles_plus.svg +++ b/data/icons/Default/layout/tiles_plus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/layout/tiles_sixteen.svg b/data/icons/Default/layout/tiles_sixteen.svg index e2b7ae150..fad5f2a70 100644 --- a/data/icons/Default/layout/tiles_sixteen.svg +++ b/data/icons/Default/layout/tiles_sixteen.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/mail/at.svg b/data/icons/Default/mail/at.svg index 32104b251..15e324faa 100644 --- a/data/icons/Default/mail/at.svg +++ b/data/icons/Default/mail/at.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/mail/email.svg b/data/icons/Default/mail/email.svg index 865b6b606..9febfe941 100644 --- a/data/icons/Default/mail/email.svg +++ b/data/icons/Default/mail/email.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/mail/email_minimal.svg b/data/icons/Default/mail/email_minimal.svg index 75c6dd670..aa10249a1 100644 --- a/data/icons/Default/mail/email_minimal.svg +++ b/data/icons/Default/mail/email_minimal.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/mail/inbox.svg b/data/icons/Default/mail/inbox.svg index 2c667c101..8e70fc8f3 100644 --- a/data/icons/Default/mail/inbox.svg +++ b/data/icons/Default/mail/inbox.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/mail/inbox_in.svg b/data/icons/Default/mail/inbox_in.svg index 29be74814..d3f671d19 100644 --- a/data/icons/Default/mail/inbox_in.svg +++ b/data/icons/Default/mail/inbox_in.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/mail/inbox_out.svg b/data/icons/Default/mail/inbox_out.svg index e70de90ab..d078117a8 100644 --- a/data/icons/Default/mail/inbox_out.svg +++ b/data/icons/Default/mail/inbox_out.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/mail/mail_reply.svg b/data/icons/Default/mail/mail_reply.svg index bdc6eacea..6b1947e4f 100644 --- a/data/icons/Default/mail/mail_reply.svg +++ b/data/icons/Default/mail/mail_reply.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/audio.svg b/data/icons/Default/media/audio.svg index f9bb03e1c..255cbc8b9 100644 --- a/data/icons/Default/media/audio.svg +++ b/data/icons/Default/media/audio.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/audio1.svg b/data/icons/Default/media/audio1.svg index 9add6e0c7..0111a6e9b 100644 --- a/data/icons/Default/media/audio1.svg +++ b/data/icons/Default/media/audio1.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/audio2.svg b/data/icons/Default/media/audio2.svg index bb53485f7..7ab993726 100644 --- a/data/icons/Default/media/audio2.svg +++ b/data/icons/Default/media/audio2.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/audio3.svg b/data/icons/Default/media/audio3.svg index 8adf7047f..01b1351f9 100644 --- a/data/icons/Default/media/audio3.svg +++ b/data/icons/Default/media/audio3.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/audio_left_right.svg b/data/icons/Default/media/audio_left_right.svg index 94a495825..ebe7fa1ad 100644 --- a/data/icons/Default/media/audio_left_right.svg +++ b/data/icons/Default/media/audio_left_right.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/audio_mute.svg b/data/icons/Default/media/audio_mute.svg index b63362930..9aa62f780 100644 --- a/data/icons/Default/media/audio_mute.svg +++ b/data/icons/Default/media/audio_mute.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/audio_stereo.svg b/data/icons/Default/media/audio_stereo.svg index cb9591030..65d7fdddb 100644 --- a/data/icons/Default/media/audio_stereo.svg +++ b/data/icons/Default/media/audio_stereo.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/audio_stereo_stack.svg b/data/icons/Default/media/audio_stereo_stack.svg index 6741ff1d7..cfdf03040 100644 --- a/data/icons/Default/media/audio_stereo_stack.svg +++ b/data/icons/Default/media/audio_stereo_stack.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/closedcaption.svg b/data/icons/Default/media/closedcaption.svg index 358a1e8aa..c9080ff83 100644 --- a/data/icons/Default/media/closedcaption.svg +++ b/data/icons/Default/media/closedcaption.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/closedcaption_off.svg b/data/icons/Default/media/closedcaption_off.svg index b37d78852..03b0e8709 100644 --- a/data/icons/Default/media/closedcaption_off.svg +++ b/data/icons/Default/media/closedcaption_off.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/film.svg b/data/icons/Default/media/film.svg index 2111b15df..1d94534fa 100644 --- a/data/icons/Default/media/film.svg +++ b/data/icons/Default/media/film.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/movie_clapper.svg b/data/icons/Default/media/movie_clapper.svg index 0d93aa696..aa2f220a9 100644 --- a/data/icons/Default/media/movie_clapper.svg +++ b/data/icons/Default/media/movie_clapper.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/music.svg b/data/icons/Default/media/music.svg index 6aa2ebfbc..e2a34901a 100644 --- a/data/icons/Default/media/music.svg +++ b/data/icons/Default/media/music.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/music_wifi.svg b/data/icons/Default/media/music_wifi.svg index 2612ad606..3a8f1d430 100644 --- a/data/icons/Default/media/music_wifi.svg +++ b/data/icons/Default/media/music_wifi.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/video.svg b/data/icons/Default/media/video.svg index 4569c10aa..4cae69c6a 100644 --- a/data/icons/Default/media/video.svg +++ b/data/icons/Default/media/video.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/video_gallery.svg b/data/icons/Default/media/video_gallery.svg index 3b7684828..f102bd4ab 100644 --- a/data/icons/Default/media/video_gallery.svg +++ b/data/icons/Default/media/video_gallery.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/video_highdef.svg b/data/icons/Default/media/video_highdef.svg index d3798617c..cfa04dae6 100644 --- a/data/icons/Default/media/video_highdef.svg +++ b/data/icons/Default/media/video_highdef.svg @@ -2,7 +2,7 @@ - - + + diff --git a/data/icons/Default/media/video_send.svg b/data/icons/Default/media/video_send.svg index c7b0fce38..8fbcaf0a7 100644 --- a/data/icons/Default/media/video_send.svg +++ b/data/icons/Default/media/video_send.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/media/video_standarddef.svg b/data/icons/Default/media/video_standarddef.svg index 22de71952..f2883ff1c 100644 --- a/data/icons/Default/media/video_standarddef.svg +++ b/data/icons/Default/media/video_standarddef.svg @@ -2,7 +2,7 @@ - - + + diff --git a/data/icons/Default/misc/acorn.svg b/data/icons/Default/misc/acorn.svg index c7c95f91c..b2bd0f0bc 100644 --- a/data/icons/Default/misc/acorn.svg +++ b/data/icons/Default/misc/acorn.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/ball.svg b/data/icons/Default/misc/ball.svg index 3373a9f8e..c6cce1272 100644 --- a/data/icons/Default/misc/ball.svg +++ b/data/icons/Default/misc/ball.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/barcode.svg b/data/icons/Default/misc/barcode.svg index 84d442e78..3263fb41f 100644 --- a/data/icons/Default/misc/barcode.svg +++ b/data/icons/Default/misc/barcode.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/bike.svg b/data/icons/Default/misc/bike.svg index 7ab0e7f5d..1dd79dd20 100644 --- a/data/icons/Default/misc/bike.svg +++ b/data/icons/Default/misc/bike.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/brick.svg b/data/icons/Default/misc/brick.svg index b6cc4995b..678bcc6ae 100644 --- a/data/icons/Default/misc/brick.svg +++ b/data/icons/Default/misc/brick.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/candle.svg b/data/icons/Default/misc/candle.svg index d93218e75..79e2378fe 100644 --- a/data/icons/Default/misc/candle.svg +++ b/data/icons/Default/misc/candle.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/city.svg b/data/icons/Default/misc/city.svg index ded88d4bd..005719c97 100644 --- a/data/icons/Default/misc/city.svg +++ b/data/icons/Default/misc/city.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/closedbook.svg b/data/icons/Default/misc/closedbook.svg index 1f6939bf3..92b6b6947 100644 --- a/data/icons/Default/misc/closedbook.svg +++ b/data/icons/Default/misc/closedbook.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/creativecommons.svg b/data/icons/Default/misc/creativecommons.svg index c6701da49..6d8d4943b 100644 --- a/data/icons/Default/misc/creativecommons.svg +++ b/data/icons/Default/misc/creativecommons.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/creditcard.svg b/data/icons/Default/misc/creditcard.svg index 2e4ed0a37..51ea5c158 100644 --- a/data/icons/Default/misc/creditcard.svg +++ b/data/icons/Default/misc/creditcard.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/cube.svg b/data/icons/Default/misc/cube.svg index 16c942f85..a65f8eae0 100644 --- a/data/icons/Default/misc/cube.svg +++ b/data/icons/Default/misc/cube.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/cup.svg b/data/icons/Default/misc/cup.svg index 345ee9dd6..c2e772a68 100644 --- a/data/icons/Default/misc/cup.svg +++ b/data/icons/Default/misc/cup.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/customerservice.svg b/data/icons/Default/misc/customerservice.svg index ef75f0a9a..be63b2bf0 100644 --- a/data/icons/Default/misc/customerservice.svg +++ b/data/icons/Default/misc/customerservice.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/eye.svg b/data/icons/Default/misc/eye.svg index 993c86c45..97b28bc99 100644 --- a/data/icons/Default/misc/eye.svg +++ b/data/icons/Default/misc/eye.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/fingerprint.svg b/data/icons/Default/misc/fingerprint.svg index 71433df34..f38715089 100644 --- a/data/icons/Default/misc/fingerprint.svg +++ b/data/icons/Default/misc/fingerprint.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/flag.svg b/data/icons/Default/misc/flag.svg index 28a8002c2..0e659e191 100644 --- a/data/icons/Default/misc/flag.svg +++ b/data/icons/Default/misc/flag.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/foot.svg b/data/icons/Default/misc/foot.svg index 93dce4ff8..43be018d6 100644 --- a/data/icons/Default/misc/foot.svg +++ b/data/icons/Default/misc/foot.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/gallery.svg b/data/icons/Default/misc/gallery.svg index fd52c23d4..7ae87ae3f 100644 --- a/data/icons/Default/misc/gallery.svg +++ b/data/icons/Default/misc/gallery.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/games.svg b/data/icons/Default/misc/games.svg index d95587abc..417e0d559 100644 --- a/data/icons/Default/misc/games.svg +++ b/data/icons/Default/misc/games.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/gender_both.svg b/data/icons/Default/misc/gender_both.svg index 67f02db0c..c41229cff 100644 --- a/data/icons/Default/misc/gender_both.svg +++ b/data/icons/Default/misc/gender_both.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/gender_female.svg b/data/icons/Default/misc/gender_female.svg index 4e7ac4656..189f336d3 100644 --- a/data/icons/Default/misc/gender_female.svg +++ b/data/icons/Default/misc/gender_female.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/gender_male.svg b/data/icons/Default/misc/gender_male.svg index 5c00d14a0..6b2ac15a6 100644 --- a/data/icons/Default/misc/gender_male.svg +++ b/data/icons/Default/misc/gender_male.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/heart.svg b/data/icons/Default/misc/heart.svg index 862e079b7..0661de1c2 100644 --- a/data/icons/Default/misc/heart.svg +++ b/data/icons/Default/misc/heart.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/heart_outline.svg b/data/icons/Default/misc/heart_outline.svg index 553aa1df8..de5f0877e 100644 --- a/data/icons/Default/misc/heart_outline.svg +++ b/data/icons/Default/misc/heart_outline.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/lamp.svg b/data/icons/Default/misc/lamp.svg index fb06d7052..a36b55989 100644 --- a/data/icons/Default/misc/lamp.svg +++ b/data/icons/Default/misc/lamp.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/leaderboard.svg b/data/icons/Default/misc/leaderboard.svg index ca604448d..f17a455fc 100644 --- a/data/icons/Default/misc/leaderboard.svg +++ b/data/icons/Default/misc/leaderboard.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/lifesaver.svg b/data/icons/Default/misc/lifesaver.svg index 5f7bb3d1d..bd1e98df4 100644 --- a/data/icons/Default/misc/lifesaver.svg +++ b/data/icons/Default/misc/lifesaver.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/lightning.svg b/data/icons/Default/misc/lightning.svg index 98ae3b1e9..509a65c5c 100644 --- a/data/icons/Default/misc/lightning.svg +++ b/data/icons/Default/misc/lightning.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/man_walk.svg b/data/icons/Default/misc/man_walk.svg index aa4681eae..b4e4b64bd 100644 --- a/data/icons/Default/misc/man_walk.svg +++ b/data/icons/Default/misc/man_walk.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/medical_pill.svg b/data/icons/Default/misc/medical_pill.svg index 4274d8607..633f54b17 100644 --- a/data/icons/Default/misc/medical_pill.svg +++ b/data/icons/Default/misc/medical_pill.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/medical_pulse.svg b/data/icons/Default/misc/medical_pulse.svg index fb206dcd2..cf9ad85c3 100644 --- a/data/icons/Default/misc/medical_pulse.svg +++ b/data/icons/Default/misc/medical_pulse.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/na.svg b/data/icons/Default/misc/na.svg index cdf439d08..3703217df 100644 --- a/data/icons/Default/misc/na.svg +++ b/data/icons/Default/misc/na.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/openbook.svg b/data/icons/Default/misc/openbook.svg index 48f7d7743..62c623785 100644 --- a/data/icons/Default/misc/openbook.svg +++ b/data/icons/Default/misc/openbook.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/openbook_info.svg b/data/icons/Default/misc/openbook_info.svg index 56250bcaf..6140e4de5 100644 --- a/data/icons/Default/misc/openbook_info.svg +++ b/data/icons/Default/misc/openbook_info.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/openbook_text.svg b/data/icons/Default/misc/openbook_text.svg index a65f701fb..9ef6d157c 100644 --- a/data/icons/Default/misc/openbook_text.svg +++ b/data/icons/Default/misc/openbook_text.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/openbook_textimage.svg b/data/icons/Default/misc/openbook_textimage.svg index bcd846f4d..98451c05f 100644 --- a/data/icons/Default/misc/openbook_textimage.svg +++ b/data/icons/Default/misc/openbook_textimage.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/paw.svg b/data/icons/Default/misc/paw.svg index d969aa2f7..994a6ee37 100644 --- a/data/icons/Default/misc/paw.svg +++ b/data/icons/Default/misc/paw.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/picture.svg b/data/icons/Default/misc/picture.svg index 4b53b4747..430fb0bcf 100644 --- a/data/icons/Default/misc/picture.svg +++ b/data/icons/Default/misc/picture.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/places.svg b/data/icons/Default/misc/places.svg index 509496f85..8049a5736 100644 --- a/data/icons/Default/misc/places.svg +++ b/data/icons/Default/misc/places.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/plane.svg b/data/icons/Default/misc/plane.svg index 4ac570ceb..e28ce811e 100644 --- a/data/icons/Default/misc/plane.svg +++ b/data/icons/Default/misc/plane.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/present.svg b/data/icons/Default/misc/present.svg index dc7a4988f..6e4407fb1 100644 --- a/data/icons/Default/misc/present.svg +++ b/data/icons/Default/misc/present.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/puzzle.svg b/data/icons/Default/misc/puzzle.svg index 9aadbfc23..358f3296b 100644 --- a/data/icons/Default/misc/puzzle.svg +++ b/data/icons/Default/misc/puzzle.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/rocket.svg b/data/icons/Default/misc/rocket.svg index 595ae96cf..80763758f 100644 --- a/data/icons/Default/misc/rocket.svg +++ b/data/icons/Default/misc/rocket.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/share.svg b/data/icons/Default/misc/share.svg index 707c9079b..24206a69a 100644 --- a/data/icons/Default/misc/share.svg +++ b/data/icons/Default/misc/share.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/sleep.svg b/data/icons/Default/misc/sleep.svg index 08ee7c0f8..5c03e3c18 100644 --- a/data/icons/Default/misc/sleep.svg +++ b/data/icons/Default/misc/sleep.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/thermometer.svg b/data/icons/Default/misc/thermometer.svg index 67a9d150b..6df6d315f 100644 --- a/data/icons/Default/misc/thermometer.svg +++ b/data/icons/Default/misc/thermometer.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/thermometer_celcius.svg b/data/icons/Default/misc/thermometer_celcius.svg index b586b8fad..9fa1e73a0 100644 --- a/data/icons/Default/misc/thermometer_celcius.svg +++ b/data/icons/Default/misc/thermometer_celcius.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/thermometer_fahrenheit.svg b/data/icons/Default/misc/thermometer_fahrenheit.svg index d097fce02..701195b1f 100644 --- a/data/icons/Default/misc/thermometer_fahrenheit.svg +++ b/data/icons/Default/misc/thermometer_fahrenheit.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/thermometer_signs.svg b/data/icons/Default/misc/thermometer_signs.svg index a9a8e78e3..1340c8119 100644 --- a/data/icons/Default/misc/thermometer_signs.svg +++ b/data/icons/Default/misc/thermometer_signs.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/tournament.svg b/data/icons/Default/misc/tournament.svg index f6fa51c96..6d0f80685 100644 --- a/data/icons/Default/misc/tournament.svg +++ b/data/icons/Default/misc/tournament.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/trophy.svg b/data/icons/Default/misc/trophy.svg index 3131a16f3..6c418484c 100644 --- a/data/icons/Default/misc/trophy.svg +++ b/data/icons/Default/misc/trophy.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/misc/whirl.svg b/data/icons/Default/misc/whirl.svg index 71433df34..f38715089 100644 --- a/data/icons/Default/misc/whirl.svg +++ b/data/icons/Default/misc/whirl.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/nature/leaf.svg b/data/icons/Default/nature/leaf.svg index c31854616..1eb2e0a51 100644 --- a/data/icons/Default/nature/leaf.svg +++ b/data/icons/Default/nature/leaf.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/nature/leaf_three.svg b/data/icons/Default/nature/leaf_three.svg index d43332f01..0bcb95506 100644 --- a/data/icons/Default/nature/leaf_three.svg +++ b/data/icons/Default/nature/leaf_three.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/nature/pine.svg b/data/icons/Default/nature/pine.svg index bfc51a565..c0c3154af 100644 --- a/data/icons/Default/nature/pine.svg +++ b/data/icons/Default/nature/pine.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/nature/tree.svg b/data/icons/Default/nature/tree.svg index 778fe42c0..28d07dd47 100644 --- a/data/icons/Default/nature/tree.svg +++ b/data/icons/Default/nature/tree.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/navigation/base.svg b/data/icons/Default/navigation/base.svg index b826eb0b6..10030c413 100644 --- a/data/icons/Default/navigation/base.svg +++ b/data/icons/Default/navigation/base.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/navigation/base_select.svg b/data/icons/Default/navigation/base_select.svg index ec4502b5c..987b2590e 100644 --- a/data/icons/Default/navigation/base_select.svg +++ b/data/icons/Default/navigation/base_select.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/navigation/location.svg b/data/icons/Default/navigation/location.svg index 161afb602..182fb12aa 100644 --- a/data/icons/Default/navigation/location.svg +++ b/data/icons/Default/navigation/location.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/navigation/location_add.svg b/data/icons/Default/navigation/location_add.svg index 736738c7e..f9d511183 100644 --- a/data/icons/Default/navigation/location_add.svg +++ b/data/icons/Default/navigation/location_add.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/navigation/location_checkin.svg b/data/icons/Default/navigation/location_checkin.svg index f874e9d5b..6af1f26e4 100644 --- a/data/icons/Default/navigation/location_checkin.svg +++ b/data/icons/Default/navigation/location_checkin.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/navigation/location_circle.svg b/data/icons/Default/navigation/location_circle.svg index bf8d910d5..ee2810ce4 100644 --- a/data/icons/Default/navigation/location_circle.svg +++ b/data/icons/Default/navigation/location_circle.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/navigation/location_delete.svg b/data/icons/Default/navigation/location_delete.svg index b9469fd5b..8374126f5 100644 --- a/data/icons/Default/navigation/location_delete.svg +++ b/data/icons/Default/navigation/location_delete.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/navigation/location_minus.svg b/data/icons/Default/navigation/location_minus.svg index 6b64fbedf..3543ee46a 100644 --- a/data/icons/Default/navigation/location_minus.svg +++ b/data/icons/Default/navigation/location_minus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/navigation/location_round.svg b/data/icons/Default/navigation/location_round.svg index 5dce45b95..e0628e467 100644 --- a/data/icons/Default/navigation/location_round.svg +++ b/data/icons/Default/navigation/location_round.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/navigation/map.svg b/data/icons/Default/navigation/map.svg index 420e467dc..fa9b20fd2 100644 --- a/data/icons/Default/navigation/map.svg +++ b/data/icons/Default/navigation/map.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/navigation/map_folds.svg b/data/icons/Default/navigation/map_folds.svg index f7869f315..1d9f3eb34 100644 --- a/data/icons/Default/navigation/map_folds.svg +++ b/data/icons/Default/navigation/map_folds.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/navigation/map_satellite.svg b/data/icons/Default/navigation/map_satellite.svg index 5931b2f24..76d091075 100644 --- a/data/icons/Default/navigation/map_satellite.svg +++ b/data/icons/Default/navigation/map_satellite.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/navigation/map_treasure.svg b/data/icons/Default/navigation/map_treasure.svg index 0c4a736c4..e485026c9 100644 --- a/data/icons/Default/navigation/map_treasure.svg +++ b/data/icons/Default/navigation/map_treasure.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/365.svg b/data/icons/Default/office/365.svg index efbebbf68..98c5079de 100644 --- a/data/icons/Default/office/365.svg +++ b/data/icons/Default/office/365.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/access.svg b/data/icons/Default/office/access.svg index 975cefae8..2e3b5838b 100644 --- a/data/icons/Default/office/access.svg +++ b/data/icons/Default/office/access.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/accounting.svg b/data/icons/Default/office/accounting.svg index b22265d89..df0f64600 100644 --- a/data/icons/Default/office/accounting.svg +++ b/data/icons/Default/office/accounting.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/addressbook.svg b/data/icons/Default/office/addressbook.svg index 9e4681bf9..e29f7d88f 100644 --- a/data/icons/Default/office/addressbook.svg +++ b/data/icons/Default/office/addressbook.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/cabinet.svg b/data/icons/Default/office/cabinet.svg index a277d4958..6146f1ab2 100644 --- a/data/icons/Default/office/cabinet.svg +++ b/data/icons/Default/office/cabinet.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/cabinet_closed.svg b/data/icons/Default/office/cabinet_closed.svg index dcbf4b0fa..81b480c4b 100644 --- a/data/icons/Default/office/cabinet_closed.svg +++ b/data/icons/Default/office/cabinet_closed.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/cabinet_in.svg b/data/icons/Default/office/cabinet_in.svg index 3b34f5cd7..2e33b9fc0 100644 --- a/data/icons/Default/office/cabinet_in.svg +++ b/data/icons/Default/office/cabinet_in.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/cabinet_out.svg b/data/icons/Default/office/cabinet_out.svg index ac2e13276..f551162dc 100644 --- a/data/icons/Default/office/cabinet_out.svg +++ b/data/icons/Default/office/cabinet_out.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/chart.svg b/data/icons/Default/office/chart.svg index 0b13cfff5..71cdc890a 100644 --- a/data/icons/Default/office/chart.svg +++ b/data/icons/Default/office/chart.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/circle_decline.svg b/data/icons/Default/office/circle_decline.svg index 7375f56ab..a9144a9a7 100644 --- a/data/icons/Default/office/circle_decline.svg +++ b/data/icons/Default/office/circle_decline.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/circle_growth.svg b/data/icons/Default/office/circle_growth.svg index 4b6a80cfc..b8f6f36a3 100644 --- a/data/icons/Default/office/circle_growth.svg +++ b/data/icons/Default/office/circle_growth.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/excel.svg b/data/icons/Default/office/excel.svg index 870e3200a..1aa82070e 100644 --- a/data/icons/Default/office/excel.svg +++ b/data/icons/Default/office/excel.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/graph_bar.svg b/data/icons/Default/office/graph_bar.svg index ae912f505..1424306e8 100644 --- a/data/icons/Default/office/graph_bar.svg +++ b/data/icons/Default/office/graph_bar.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/graph_boxplot.svg b/data/icons/Default/office/graph_boxplot.svg index 15e1da0e5..1811fe4c9 100644 --- a/data/icons/Default/office/graph_boxplot.svg +++ b/data/icons/Default/office/graph_boxplot.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/graph_histogram.svg b/data/icons/Default/office/graph_histogram.svg index e33cd0fc5..2937f2360 100644 --- a/data/icons/Default/office/graph_histogram.svg +++ b/data/icons/Default/office/graph_histogram.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/graph_line.svg b/data/icons/Default/office/graph_line.svg index 0b13cfff5..71cdc890a 100644 --- a/data/icons/Default/office/graph_line.svg +++ b/data/icons/Default/office/graph_line.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/graph_line_down.svg b/data/icons/Default/office/graph_line_down.svg index 2c9b8f36c..f64e063ce 100644 --- a/data/icons/Default/office/graph_line_down.svg +++ b/data/icons/Default/office/graph_line_down.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/graph_line_up.svg b/data/icons/Default/office/graph_line_up.svg index 03c7135cf..ce8190008 100644 --- a/data/icons/Default/office/graph_line_up.svg +++ b/data/icons/Default/office/graph_line_up.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/infopath.svg b/data/icons/Default/office/infopath.svg index 70ab53e44..f3de9de85 100644 --- a/data/icons/Default/office/infopath.svg +++ b/data/icons/Default/office/infopath.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/journal.svg b/data/icons/Default/office/journal.svg index d0d695bc8..961b25561 100644 --- a/data/icons/Default/office/journal.svg +++ b/data/icons/Default/office/journal.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/lync.svg b/data/icons/Default/office/lync.svg index cb3674c8c..26d5876ee 100644 --- a/data/icons/Default/office/lync.svg +++ b/data/icons/Default/office/lync.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/money.svg b/data/icons/Default/office/money.svg index 49273013c..1b324930d 100644 --- a/data/icons/Default/office/money.svg +++ b/data/icons/Default/office/money.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/onenote.svg b/data/icons/Default/office/onenote.svg index 3887e41ea..49a6f6155 100644 --- a/data/icons/Default/office/onenote.svg +++ b/data/icons/Default/office/onenote.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/outlook.svg b/data/icons/Default/office/outlook.svg index b1d52e390..aabcd08cf 100644 --- a/data/icons/Default/office/outlook.svg +++ b/data/icons/Default/office/outlook.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/paperclip.svg b/data/icons/Default/office/paperclip.svg index 472bee628..83877092e 100644 --- a/data/icons/Default/office/paperclip.svg +++ b/data/icons/Default/office/paperclip.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/pie.svg b/data/icons/Default/office/pie.svg index 352a9e099..d73870095 100644 --- a/data/icons/Default/office/pie.svg +++ b/data/icons/Default/office/pie.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/pie_quarter.svg b/data/icons/Default/office/pie_quarter.svg index 28764f2e2..1e24eee1b 100644 --- a/data/icons/Default/office/pie_quarter.svg +++ b/data/icons/Default/office/pie_quarter.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/powerpoint.svg b/data/icons/Default/office/powerpoint.svg index d41d7c67a..ea02f29f6 100644 --- a/data/icons/Default/office/powerpoint.svg +++ b/data/icons/Default/office/powerpoint.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/project.svg b/data/icons/Default/office/project.svg index 6a0f4ba30..3385c56ef 100644 --- a/data/icons/Default/office/project.svg +++ b/data/icons/Default/office/project.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/publisher.svg b/data/icons/Default/office/publisher.svg index 31db00f61..4582573ad 100644 --- a/data/icons/Default/office/publisher.svg +++ b/data/icons/Default/office/publisher.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/scale.svg b/data/icons/Default/office/scale.svg index 2f4bb242a..4251ea417 100644 --- a/data/icons/Default/office/scale.svg +++ b/data/icons/Default/office/scale.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/scale_unbalanced.svg b/data/icons/Default/office/scale_unbalanced.svg index a96241838..0190d4c0f 100644 --- a/data/icons/Default/office/scale_unbalanced.svg +++ b/data/icons/Default/office/scale_unbalanced.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/sharepoint.svg b/data/icons/Default/office/sharepoint.svg index 69733b436..e045a7fcd 100644 --- a/data/icons/Default/office/sharepoint.svg +++ b/data/icons/Default/office/sharepoint.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/stock.svg b/data/icons/Default/office/stock.svg index 1951ee045..14edfd8ee 100644 --- a/data/icons/Default/office/stock.svg +++ b/data/icons/Default/office/stock.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/stock_down.svg b/data/icons/Default/office/stock_down.svg index ad21231c4..a860c499e 100644 --- a/data/icons/Default/office/stock_down.svg +++ b/data/icons/Default/office/stock_down.svg @@ -1,6 +1,6 @@  - - + + diff --git a/data/icons/Default/office/stock_up.svg b/data/icons/Default/office/stock_up.svg index 1ca33a56b..11bc474b9 100644 --- a/data/icons/Default/office/stock_up.svg +++ b/data/icons/Default/office/stock_up.svg @@ -1,6 +1,6 @@  - - + + diff --git a/data/icons/Default/office/suitcase.svg b/data/icons/Default/office/suitcase.svg index bca5b1ee1..4268b5342 100644 --- a/data/icons/Default/office/suitcase.svg +++ b/data/icons/Default/office/suitcase.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/visio.svg b/data/icons/Default/office/visio.svg index 6bb023af0..3031cde63 100644 --- a/data/icons/Default/office/visio.svg +++ b/data/icons/Default/office/visio.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/office/word.svg b/data/icons/Default/office/word.svg index f7d0ad807..a7af5efc5 100644 --- a/data/icons/Default/office/word.svg +++ b/data/icons/Default/office/word.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/add.svg b/data/icons/Default/page/add.svg index 70fdce7cb..e9cc4892d 100644 --- a/data/icons/Default/page/add.svg +++ b/data/icons/Default/page/add.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/arrow.svg b/data/icons/Default/page/arrow.svg index 04b639612..1b62365e0 100644 --- a/data/icons/Default/page/arrow.svg +++ b/data/icons/Default/page/arrow.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/break.svg b/data/icons/Default/page/break.svg index ca25b6130..2cd1c479a 100644 --- a/data/icons/Default/page/break.svg +++ b/data/icons/Default/page/break.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/check.svg b/data/icons/Default/page/check.svg index ff75907d4..0b1309588 100644 --- a/data/icons/Default/page/check.svg +++ b/data/icons/Default/page/check.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/copy.svg b/data/icons/Default/page/copy.svg index a1f2158a0..5aea170f7 100644 --- a/data/icons/Default/page/copy.svg +++ b/data/icons/Default/page/copy.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/corner.svg b/data/icons/Default/page/corner.svg index 135ffa57c..b42f9583b 100644 --- a/data/icons/Default/page/corner.svg +++ b/data/icons/Default/page/corner.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/corner_bookmark.svg b/data/icons/Default/page/corner_bookmark.svg index 05e950965..6c6de5a6b 100644 --- a/data/icons/Default/page/corner_bookmark.svg +++ b/data/icons/Default/page/corner_bookmark.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/corner_break.svg b/data/icons/Default/page/corner_break.svg index 894285e76..4186cf410 100644 --- a/data/icons/Default/page/corner_break.svg +++ b/data/icons/Default/page/corner_break.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/corner_cells.svg b/data/icons/Default/page/corner_cells.svg index 31ff0827d..4c82f7bf7 100644 --- a/data/icons/Default/page/corner_cells.svg +++ b/data/icons/Default/page/corner_cells.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/corner_folded.svg b/data/icons/Default/page/corner_folded.svg index da23dfc69..df97b460a 100644 --- a/data/icons/Default/page/corner_folded.svg +++ b/data/icons/Default/page/corner_folded.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/corner_folded_grid.svg b/data/icons/Default/page/corner_folded_grid.svg index 1c005b75d..12f7ff70c 100644 --- a/data/icons/Default/page/corner_folded_grid.svg +++ b/data/icons/Default/page/corner_folded_grid.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/corner_folded_text.svg b/data/icons/Default/page/corner_folded_text.svg index cda277c0e..535a05bf4 100644 --- a/data/icons/Default/page/corner_folded_text.svg +++ b/data/icons/Default/page/corner_folded_text.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/corner_grid.svg b/data/icons/Default/page/corner_grid.svg index f68eef35f..d5bcb70ae 100644 --- a/data/icons/Default/page/corner_grid.svg +++ b/data/icons/Default/page/corner_grid.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/corner_text.svg b/data/icons/Default/page/corner_text.svg index 1ec61359b..6f5417aa0 100644 --- a/data/icons/Default/page/corner_text.svg +++ b/data/icons/Default/page/corner_text.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/corner_text_break.svg b/data/icons/Default/page/corner_text_break.svg index 8a398167a..d86ac885e 100644 --- a/data/icons/Default/page/corner_text_break.svg +++ b/data/icons/Default/page/corner_text_break.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/delete.svg b/data/icons/Default/page/delete.svg index 50a892c8e..e085bf8d6 100644 --- a/data/icons/Default/page/delete.svg +++ b/data/icons/Default/page/delete.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/download.svg b/data/icons/Default/page/download.svg index 02b7aee8d..391e18130 100644 --- a/data/icons/Default/page/download.svg +++ b/data/icons/Default/page/download.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/duplicate.svg b/data/icons/Default/page/duplicate.svg index 56d171be8..3625dc428 100644 --- a/data/icons/Default/page/duplicate.svg +++ b/data/icons/Default/page/duplicate.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/edit.svg b/data/icons/Default/page/edit.svg index 5f51892f3..d1afbd2f2 100644 --- a/data/icons/Default/page/edit.svg +++ b/data/icons/Default/page/edit.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/hidden.svg b/data/icons/Default/page/hidden.svg index e436c0719..3dc8f860d 100644 --- a/data/icons/Default/page/hidden.svg +++ b/data/icons/Default/page/hidden.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/location.svg b/data/icons/Default/page/location.svg index 543dcb3c2..7bd7e63d8 100644 --- a/data/icons/Default/page/location.svg +++ b/data/icons/Default/page/location.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/location_add.svg b/data/icons/Default/page/location_add.svg index b22594efc..ff5c72f18 100644 --- a/data/icons/Default/page/location_add.svg +++ b/data/icons/Default/page/location_add.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/minus.svg b/data/icons/Default/page/minus.svg index 9e73b324c..d31e45974 100644 --- a/data/icons/Default/page/minus.svg +++ b/data/icons/Default/page/minus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/multiple.svg b/data/icons/Default/page/multiple.svg index 25b52ebe1..10cd2273c 100644 --- a/data/icons/Default/page/multiple.svg +++ b/data/icons/Default/page/multiple.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/new.svg b/data/icons/Default/page/new.svg index d3b661b05..7f4e870c5 100644 --- a/data/icons/Default/page/new.svg +++ b/data/icons/Default/page/new.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/page.svg b/data/icons/Default/page/page.svg index 92d5cbfda..a5e29f88a 100644 --- a/data/icons/Default/page/page.svg +++ b/data/icons/Default/page/page.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/search.svg b/data/icons/Default/page/search.svg index 4f88ace6d..302878def 100644 --- a/data/icons/Default/page/search.svg +++ b/data/icons/Default/page/search.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/page/upload.svg b/data/icons/Default/page/upload.svg index 1fc78b5da..95b7848ef 100644 --- a/data/icons/Default/page/upload.svg +++ b/data/icons/Default/page/upload.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/acrobatreader.svg b/data/icons/Default/programs/acrobatreader.svg index a4c18bec9..84c7b2b6e 100644 --- a/data/icons/Default/programs/acrobatreader.svg +++ b/data/icons/Default/programs/acrobatreader.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/chat.svg b/data/icons/Default/programs/chat.svg index ca7041b08..fab2b639c 100644 --- a/data/icons/Default/programs/chat.svg +++ b/data/icons/Default/programs/chat.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/clipboard.svg b/data/icons/Default/programs/clipboard.svg index 189d65ff2..287d0e0e4 100644 --- a/data/icons/Default/programs/clipboard.svg +++ b/data/icons/Default/programs/clipboard.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/cloudapp.svg b/data/icons/Default/programs/cloudapp.svg index 2e497422a..a34d69a50 100644 --- a/data/icons/Default/programs/cloudapp.svg +++ b/data/icons/Default/programs/cloudapp.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/commandline.svg b/data/icons/Default/programs/commandline.svg index 0beec0565..2c46733fc 100644 --- a/data/icons/Default/programs/commandline.svg +++ b/data/icons/Default/programs/commandline.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/compress.svg b/data/icons/Default/programs/compress.svg index 042ca60cb..1a0cb42dc 100644 --- a/data/icons/Default/programs/compress.svg +++ b/data/icons/Default/programs/compress.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/decompress.svg b/data/icons/Default/programs/decompress.svg index 042ca60cb..1a0cb42dc 100644 --- a/data/icons/Default/programs/decompress.svg +++ b/data/icons/Default/programs/decompress.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/filemanager.svg b/data/icons/Default/programs/filemanager.svg index 98f66dcb2..39955bf5e 100644 --- a/data/icons/Default/programs/filemanager.svg +++ b/data/icons/Default/programs/filemanager.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/gfxeditor.svg b/data/icons/Default/programs/gfxeditor.svg index 45cf8b6b7..ffba6d365 100644 --- a/data/icons/Default/programs/gfxeditor.svg +++ b/data/icons/Default/programs/gfxeditor.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/internet.svg b/data/icons/Default/programs/internet.svg index 455d3a4bb..ed92b1619 100644 --- a/data/icons/Default/programs/internet.svg +++ b/data/icons/Default/programs/internet.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/message.svg b/data/icons/Default/programs/message.svg index 5d623e2c5..12cabfcc2 100644 --- a/data/icons/Default/programs/message.svg +++ b/data/icons/Default/programs/message.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/musicplayer.svg b/data/icons/Default/programs/musicplayer.svg index 6aa2ebfbc..e2a34901a 100644 --- a/data/icons/Default/programs/musicplayer.svg +++ b/data/icons/Default/programs/musicplayer.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/news_create.svg b/data/icons/Default/programs/news_create.svg index 34e7b9e60..5a4071b6c 100644 --- a/data/icons/Default/programs/news_create.svg +++ b/data/icons/Default/programs/news_create.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/pictureviewer.svg b/data/icons/Default/programs/pictureviewer.svg index 4b53b4747..430fb0bcf 100644 --- a/data/icons/Default/programs/pictureviewer.svg +++ b/data/icons/Default/programs/pictureviewer.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/rss.svg b/data/icons/Default/programs/rss.svg index d78b56dbc..10fe5870a 100644 --- a/data/icons/Default/programs/rss.svg +++ b/data/icons/Default/programs/rss.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/shell.svg b/data/icons/Default/programs/shell.svg index 0beec0565..2c46733fc 100644 --- a/data/icons/Default/programs/shell.svg +++ b/data/icons/Default/programs/shell.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/snapshot.svg b/data/icons/Default/programs/snapshot.svg index d2e34f0e9..05980eb5b 100644 --- a/data/icons/Default/programs/snapshot.svg +++ b/data/icons/Default/programs/snapshot.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/tool.svg b/data/icons/Default/programs/tool.svg index 11889469c..e68cd7406 100644 --- a/data/icons/Default/programs/tool.svg +++ b/data/icons/Default/programs/tool.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/programs/usermanagement.svg b/data/icons/Default/programs/usermanagement.svg index 2c04bd02f..5c6961997 100644 --- a/data/icons/Default/programs/usermanagement.svg +++ b/data/icons/Default/programs/usermanagement.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/technical/axis_three.svg b/data/icons/Default/technical/axis_three.svg index 4171fb652..a3b89ebd1 100644 --- a/data/icons/Default/technical/axis_three.svg +++ b/data/icons/Default/technical/axis_three.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/technical/axis_x.svg b/data/icons/Default/technical/axis_x.svg index 9cdb078c4..bdc69665f 100644 --- a/data/icons/Default/technical/axis_x.svg +++ b/data/icons/Default/technical/axis_x.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/technical/axis_x_letter.svg b/data/icons/Default/technical/axis_x_letter.svg index 503e71c34..33195641e 100644 --- a/data/icons/Default/technical/axis_x_letter.svg +++ b/data/icons/Default/technical/axis_x_letter.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/technical/axis_xy.svg b/data/icons/Default/technical/axis_xy.svg index 12407301d..50ceabe51 100644 --- a/data/icons/Default/technical/axis_xy.svg +++ b/data/icons/Default/technical/axis_xy.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/technical/axis_xy_parentheses.svg b/data/icons/Default/technical/axis_xy_parentheses.svg index 3b0d38b1f..acc8ea032 100644 --- a/data/icons/Default/technical/axis_xy_parentheses.svg +++ b/data/icons/Default/technical/axis_xy_parentheses.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/technical/axis_y.svg b/data/icons/Default/technical/axis_y.svg index 862a7821a..071dacc68 100644 --- a/data/icons/Default/technical/axis_y.svg +++ b/data/icons/Default/technical/axis_y.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/technical/axis_y_letter.svg b/data/icons/Default/technical/axis_y_letter.svg index d9e017ea0..32836a442 100644 --- a/data/icons/Default/technical/axis_y_letter.svg +++ b/data/icons/Default/technical/axis_y_letter.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/technical/axis_yx.svg b/data/icons/Default/technical/axis_yx.svg index 472ac0c18..ccd7d5a3a 100644 --- a/data/icons/Default/technical/axis_yx.svg +++ b/data/icons/Default/technical/axis_yx.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/technical/axis_z.svg b/data/icons/Default/technical/axis_z.svg index 61ebd3678..ba4599625 100644 --- a/data/icons/Default/technical/axis_z.svg +++ b/data/icons/Default/technical/axis_z.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/technical/axis_z_letter.svg b/data/icons/Default/technical/axis_z_letter.svg index 5f031cd5a..4d68195bb 100644 --- a/data/icons/Default/technical/axis_z_letter.svg +++ b/data/icons/Default/technical/axis_z_letter.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/technical/greek_sigma_lower.svg b/data/icons/Default/technical/greek_sigma_lower.svg index 02365106c..baa8e3ede 100644 --- a/data/icons/Default/technical/greek_sigma_lower.svg +++ b/data/icons/Default/technical/greek_sigma_lower.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/technical/greek_sigma_upper.svg b/data/icons/Default/technical/greek_sigma_upper.svg index d2f6ff9e1..5daa42baa 100644 --- a/data/icons/Default/technical/greek_sigma_upper.svg +++ b/data/icons/Default/technical/greek_sigma_upper.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/technical/infinite.svg b/data/icons/Default/technical/infinite.svg index 41ef1f63c..5930c60ed 100644 --- a/data/icons/Default/technical/infinite.svg +++ b/data/icons/Default/technical/infinite.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/technical/plus_minus.svg b/data/icons/Default/technical/plus_minus.svg index 27bcd5c7d..a1b47a71c 100644 --- a/data/icons/Default/technical/plus_minus.svg +++ b/data/icons/Default/technical/plus_minus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/alarm.svg b/data/icons/Default/time/alarm.svg index 91dcbbf4f..8bcd48bac 100644 --- a/data/icons/Default/time/alarm.svg +++ b/data/icons/Default/time/alarm.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/calendar.svg b/data/icons/Default/time/calendar.svg index c7ad2f391..5895e849a 100644 --- a/data/icons/Default/time/calendar.svg +++ b/data/icons/Default/time/calendar.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/calendar_14.svg b/data/icons/Default/time/calendar_14.svg index c8eedd62f..1148f12c0 100644 --- a/data/icons/Default/time/calendar_14.svg +++ b/data/icons/Default/time/calendar_14.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/calendar_31.svg b/data/icons/Default/time/calendar_31.svg index e6b825ed2..0af922d33 100644 --- a/data/icons/Default/time/calendar_31.svg +++ b/data/icons/Default/time/calendar_31.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/calendar_day.svg b/data/icons/Default/time/calendar_day.svg index a3ec424c5..b89f51a65 100644 --- a/data/icons/Default/time/calendar_day.svg +++ b/data/icons/Default/time/calendar_day.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/calendar_month.svg b/data/icons/Default/time/calendar_month.svg index 62589fddc..a944be5bc 100644 --- a/data/icons/Default/time/calendar_month.svg +++ b/data/icons/Default/time/calendar_month.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/calendar_range.svg b/data/icons/Default/time/calendar_range.svg index 2cd756d1f..36131ff17 100644 --- a/data/icons/Default/time/calendar_range.svg +++ b/data/icons/Default/time/calendar_range.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/calendar_reply.svg b/data/icons/Default/time/calendar_reply.svg index 6673f82bf..d6528f369 100644 --- a/data/icons/Default/time/calendar_reply.svg +++ b/data/icons/Default/time/calendar_reply.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/calendar_week.svg b/data/icons/Default/time/calendar_week.svg index 034853105..7310bdbc2 100644 --- a/data/icons/Default/time/calendar_week.svg +++ b/data/icons/Default/time/calendar_week.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/calendar_year.svg b/data/icons/Default/time/calendar_year.svg index 9e837e1e0..51644dbd1 100644 --- a/data/icons/Default/time/calendar_year.svg +++ b/data/icons/Default/time/calendar_year.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/clock.svg b/data/icons/Default/time/clock.svg index 91dcbbf4f..8bcd48bac 100644 --- a/data/icons/Default/time/clock.svg +++ b/data/icons/Default/time/clock.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/hourglass.svg b/data/icons/Default/time/hourglass.svg index 546a956fe..15792a5c8 100644 --- a/data/icons/Default/time/hourglass.svg +++ b/data/icons/Default/time/hourglass.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/timer.svg b/data/icons/Default/time/timer.svg index 207cb82a4..21537d473 100644 --- a/data/icons/Default/time/timer.svg +++ b/data/icons/Default/time/timer.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/timer_alert.svg b/data/icons/Default/time/timer_alert.svg index 43c0f214d..c377c41e1 100644 --- a/data/icons/Default/time/timer_alert.svg +++ b/data/icons/Default/time/timer_alert.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/timer_check.svg b/data/icons/Default/time/timer_check.svg index ead1cb256..873b4eee8 100644 --- a/data/icons/Default/time/timer_check.svg +++ b/data/icons/Default/time/timer_check.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/timer_forward.svg b/data/icons/Default/time/timer_forward.svg index 929b2db59..30ca70f62 100644 --- a/data/icons/Default/time/timer_forward.svg +++ b/data/icons/Default/time/timer_forward.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/timer_pause.svg b/data/icons/Default/time/timer_pause.svg index 53e8b90df..a1e562db8 100644 --- a/data/icons/Default/time/timer_pause.svg +++ b/data/icons/Default/time/timer_pause.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/timer_play.svg b/data/icons/Default/time/timer_play.svg index ad5b267ac..16290da55 100644 --- a/data/icons/Default/time/timer_play.svg +++ b/data/icons/Default/time/timer_play.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/timer_record.svg b/data/icons/Default/time/timer_record.svg index 78a07997a..36d0774cd 100644 --- a/data/icons/Default/time/timer_record.svg +++ b/data/icons/Default/time/timer_record.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/timer_rewind.svg b/data/icons/Default/time/timer_rewind.svg index 069008be5..c0585214f 100644 --- a/data/icons/Default/time/timer_rewind.svg +++ b/data/icons/Default/time/timer_rewind.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/time/timer_stop.svg b/data/icons/Default/time/timer_stop.svg index 8dff19307..efa71fdc4 100644 --- a/data/icons/Default/time/timer_stop.svg +++ b/data/icons/Default/time/timer_stop.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/brush.svg b/data/icons/Default/tools/brush.svg index fcefe3a34..be3baf081 100644 --- a/data/icons/Default/tools/brush.svg +++ b/data/icons/Default/tools/brush.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/calculator.svg b/data/icons/Default/tools/calculator.svg index b22265d89..df0f64600 100644 --- a/data/icons/Default/tools/calculator.svg +++ b/data/icons/Default/tools/calculator.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/centerline.svg b/data/icons/Default/tools/centerline.svg index eac1c3836..8cc0a321e 100644 --- a/data/icons/Default/tools/centerline.svg +++ b/data/icons/Default/tools/centerline.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/cog.svg b/data/icons/Default/tools/cog.svg index 0754b87a9..c2d87cd25 100644 --- a/data/icons/Default/tools/cog.svg +++ b/data/icons/Default/tools/cog.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/cogs.svg b/data/icons/Default/tools/cogs.svg index 7d59c8930..e2d1c65e2 100644 --- a/data/icons/Default/tools/cogs.svg +++ b/data/icons/Default/tools/cogs.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/colour_line.svg b/data/icons/Default/tools/colour_line.svg index 45a5715e8..f71318561 100644 --- a/data/icons/Default/tools/colour_line.svg +++ b/data/icons/Default/tools/colour_line.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/colourpicker.svg b/data/icons/Default/tools/colourpicker.svg index 908c6ee88..22ce3321b 100644 --- a/data/icons/Default/tools/colourpicker.svg +++ b/data/icons/Default/tools/colourpicker.svg @@ -1,6 +1,6 @@  - - + + diff --git a/data/icons/Default/tools/contrast.svg b/data/icons/Default/tools/contrast.svg index 6db0790dd..d7ed96719 100644 --- a/data/icons/Default/tools/contrast.svg +++ b/data/icons/Default/tools/contrast.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/corners.svg b/data/icons/Default/tools/corners.svg index e31ef1666..af4e4877c 100644 --- a/data/icons/Default/tools/corners.svg +++ b/data/icons/Default/tools/corners.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/crop.svg b/data/icons/Default/tools/crop.svg index 6ec224014..95aec4226 100644 --- a/data/icons/Default/tools/crop.svg +++ b/data/icons/Default/tools/crop.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/crosshair.svg b/data/icons/Default/tools/crosshair.svg index 7a81e99db..ac0aca571 100644 --- a/data/icons/Default/tools/crosshair.svg +++ b/data/icons/Default/tools/crosshair.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/cut.svg b/data/icons/Default/tools/cut.svg index d1482773c..3e86ff5fd 100644 --- a/data/icons/Default/tools/cut.svg +++ b/data/icons/Default/tools/cut.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/dial.svg b/data/icons/Default/tools/dial.svg index a27f42a81..faf3e7e47 100644 --- a/data/icons/Default/tools/dial.svg +++ b/data/icons/Default/tools/dial.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/edit.svg b/data/icons/Default/tools/edit.svg index e46849dd9..cfefccadb 100644 --- a/data/icons/Default/tools/edit.svg +++ b/data/icons/Default/tools/edit.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/edit_add.svg b/data/icons/Default/tools/edit_add.svg index 7a8155a1d..28a922ffe 100644 --- a/data/icons/Default/tools/edit_add.svg +++ b/data/icons/Default/tools/edit_add.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/edit_box.svg b/data/icons/Default/tools/edit_box.svg index 651a06abd..b495a0e9b 100644 --- a/data/icons/Default/tools/edit_box.svg +++ b/data/icons/Default/tools/edit_box.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/edit_minus.svg b/data/icons/Default/tools/edit_minus.svg index caaae2245..31fc45d11 100644 --- a/data/icons/Default/tools/edit_minus.svg +++ b/data/icons/Default/tools/edit_minus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/fill.svg b/data/icons/Default/tools/fill.svg index 4f44361d3..3a8a7ae58 100644 --- a/data/icons/Default/tools/fill.svg +++ b/data/icons/Default/tools/fill.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/filter.svg b/data/icons/Default/tools/filter.svg index b00baddfb..995ce5888 100644 --- a/data/icons/Default/tools/filter.svg +++ b/data/icons/Default/tools/filter.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/filter_alpha.svg b/data/icons/Default/tools/filter_alpha.svg index bd2a9ec12..ab8db4f52 100644 --- a/data/icons/Default/tools/filter_alpha.svg +++ b/data/icons/Default/tools/filter_alpha.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/flip_horizontal.svg b/data/icons/Default/tools/flip_horizontal.svg index 1c7b0a28e..b4af4601c 100644 --- a/data/icons/Default/tools/flip_horizontal.svg +++ b/data/icons/Default/tools/flip_horizontal.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/flip_vertical.svg b/data/icons/Default/tools/flip_vertical.svg index 00044d92d..92cce9fca 100644 --- a/data/icons/Default/tools/flip_vertical.svg +++ b/data/icons/Default/tools/flip_vertical.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/hand.svg b/data/icons/Default/tools/hand.svg index d966ebfee..f96c5a4e1 100644 --- a/data/icons/Default/tools/hand.svg +++ b/data/icons/Default/tools/hand.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/image_ants.svg b/data/icons/Default/tools/image_ants.svg index c5d7e968c..62629da1c 100644 --- a/data/icons/Default/tools/image_ants.svg +++ b/data/icons/Default/tools/image_ants.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/image_backlight.svg b/data/icons/Default/tools/image_backlight.svg index 0712bb787..d170ed4da 100644 --- a/data/icons/Default/tools/image_backlight.svg +++ b/data/icons/Default/tools/image_backlight.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/image_broken.svg b/data/icons/Default/tools/image_broken.svg index a033d00c1..45669435e 100644 --- a/data/icons/Default/tools/image_broken.svg +++ b/data/icons/Default/tools/image_broken.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/image_export.svg b/data/icons/Default/tools/image_export.svg index 28d2844e5..edc74c72f 100644 --- a/data/icons/Default/tools/image_export.svg +++ b/data/icons/Default/tools/image_export.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/image_focus.svg b/data/icons/Default/tools/image_focus.svg index ae5582846..f39c9c75a 100644 --- a/data/icons/Default/tools/image_focus.svg +++ b/data/icons/Default/tools/image_focus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/image_gallery.svg b/data/icons/Default/tools/image_gallery.svg index 0d4061222..e633c694f 100644 --- a/data/icons/Default/tools/image_gallery.svg +++ b/data/icons/Default/tools/image_gallery.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/image_landscape.svg b/data/icons/Default/tools/image_landscape.svg index b05e5349d..4eaaadc59 100644 --- a/data/icons/Default/tools/image_landscape.svg +++ b/data/icons/Default/tools/image_landscape.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/image_macro.svg b/data/icons/Default/tools/image_macro.svg index 8ebf9fbdd..81410cb15 100644 --- a/data/icons/Default/tools/image_macro.svg +++ b/data/icons/Default/tools/image_macro.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/image_multiple.svg b/data/icons/Default/tools/image_multiple.svg index 5fdb93779..9a2f7ffef 100644 --- a/data/icons/Default/tools/image_multiple.svg +++ b/data/icons/Default/tools/image_multiple.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/image_portrait.svg b/data/icons/Default/tools/image_portrait.svg index 2a994053b..c9bf5e3b9 100644 --- a/data/icons/Default/tools/image_portrait.svg +++ b/data/icons/Default/tools/image_portrait.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/image_redeye.svg b/data/icons/Default/tools/image_redeye.svg index 35ad8b021..7c0862543 100644 --- a/data/icons/Default/tools/image_redeye.svg +++ b/data/icons/Default/tools/image_redeye.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/key.svg b/data/icons/Default/tools/key.svg index a0d03075a..28686fe94 100644 --- a/data/icons/Default/tools/key.svg +++ b/data/icons/Default/tools/key.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/lightbulb.svg b/data/icons/Default/tools/lightbulb.svg index 0fa024a68..b0cb8ace3 100644 --- a/data/icons/Default/tools/lightbulb.svg +++ b/data/icons/Default/tools/lightbulb.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/magnifier.svg b/data/icons/Default/tools/magnifier.svg index 32acace37..8ce46c694 100644 --- a/data/icons/Default/tools/magnifier.svg +++ b/data/icons/Default/tools/magnifier.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/magnifier_11.svg b/data/icons/Default/tools/magnifier_11.svg index d0af21129..33438d25a 100644 --- a/data/icons/Default/tools/magnifier_11.svg +++ b/data/icons/Default/tools/magnifier_11.svg @@ -2,5 +2,5 @@ - + diff --git a/data/icons/Default/tools/magnifier_minus.svg b/data/icons/Default/tools/magnifier_minus.svg index 7edcef7f6..11c3be3d3 100644 --- a/data/icons/Default/tools/magnifier_minus.svg +++ b/data/icons/Default/tools/magnifier_minus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/magnifier_plus.svg b/data/icons/Default/tools/magnifier_plus.svg index 94fb2b1f3..edb5ca3a2 100644 --- a/data/icons/Default/tools/magnifier_plus.svg +++ b/data/icons/Default/tools/magnifier_plus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/move.svg b/data/icons/Default/tools/move.svg index ea638cf06..0fa750920 100644 --- a/data/icons/Default/tools/move.svg +++ b/data/icons/Default/tools/move.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/paintbrush.svg b/data/icons/Default/tools/paintbrush.svg index 45cf8b6b7..ffba6d365 100644 --- a/data/icons/Default/tools/paintbrush.svg +++ b/data/icons/Default/tools/paintbrush.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/pen.svg b/data/icons/Default/tools/pen.svg index 55cf6d17e..f1d992f5e 100644 --- a/data/icons/Default/tools/pen.svg +++ b/data/icons/Default/tools/pen.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/pen_add.svg b/data/icons/Default/tools/pen_add.svg index 2b974a35c..cef74c083 100644 --- a/data/icons/Default/tools/pen_add.svg +++ b/data/icons/Default/tools/pen_add.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/pen_minus.svg b/data/icons/Default/tools/pen_minus.svg index 2e6d0dea3..aeb422659 100644 --- a/data/icons/Default/tools/pen_minus.svg +++ b/data/icons/Default/tools/pen_minus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/pencil.svg b/data/icons/Default/tools/pencil.svg index 3b620cc65..9ce1470e7 100644 --- a/data/icons/Default/tools/pencil.svg +++ b/data/icons/Default/tools/pencil.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/pin.svg b/data/icons/Default/tools/pin.svg index f6d1c8c19..748a42c21 100644 --- a/data/icons/Default/tools/pin.svg +++ b/data/icons/Default/tools/pin.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/pointer.svg b/data/icons/Default/tools/pointer.svg index 2b340f85f..6386978f9 100644 --- a/data/icons/Default/tools/pointer.svg +++ b/data/icons/Default/tools/pointer.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/protractor.svg b/data/icons/Default/tools/protractor.svg index 03728ab5d..6cb308be4 100644 --- a/data/icons/Default/tools/protractor.svg +++ b/data/icons/Default/tools/protractor.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/quill.svg b/data/icons/Default/tools/quill.svg index 4a49fb663..4bb0d312a 100644 --- a/data/icons/Default/tools/quill.svg +++ b/data/icons/Default/tools/quill.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/rotate_clockwise.svg b/data/icons/Default/tools/rotate_clockwise.svg index 177d47ec2..6c0aed43e 100644 --- a/data/icons/Default/tools/rotate_clockwise.svg +++ b/data/icons/Default/tools/rotate_clockwise.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/rotate_counterclockwise.svg b/data/icons/Default/tools/rotate_counterclockwise.svg index 38ae212eb..b577483ee 100644 --- a/data/icons/Default/tools/rotate_counterclockwise.svg +++ b/data/icons/Default/tools/rotate_counterclockwise.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/rotate_left.svg b/data/icons/Default/tools/rotate_left.svg index 5c16c05e1..b5ca71680 100644 --- a/data/icons/Default/tools/rotate_left.svg +++ b/data/icons/Default/tools/rotate_left.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/rotate_right.svg b/data/icons/Default/tools/rotate_right.svg index aec936fd3..ae6e168a3 100644 --- a/data/icons/Default/tools/rotate_right.svg +++ b/data/icons/Default/tools/rotate_right.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/ruler.svg b/data/icons/Default/tools/ruler.svg index f1a7aff0c..b7389476d 100644 --- a/data/icons/Default/tools/ruler.svg +++ b/data/icons/Default/tools/ruler.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/slice.svg b/data/icons/Default/tools/slice.svg index ad7e9a2b7..1b1fee74e 100644 --- a/data/icons/Default/tools/slice.svg +++ b/data/icons/Default/tools/slice.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/vector_circle.svg b/data/icons/Default/tools/vector_circle.svg index 52f2c4a3f..3bdedf29a 100644 --- a/data/icons/Default/tools/vector_circle.svg +++ b/data/icons/Default/tools/vector_circle.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/vector_curve.svg b/data/icons/Default/tools/vector_curve.svg index 504cae87d..dc06a1f6b 100644 --- a/data/icons/Default/tools/vector_curve.svg +++ b/data/icons/Default/tools/vector_curve.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/vector_group.svg b/data/icons/Default/tools/vector_group.svg index a7c0ad312..e3c91e8ea 100644 --- a/data/icons/Default/tools/vector_group.svg +++ b/data/icons/Default/tools/vector_group.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/vector_group_removed.svg b/data/icons/Default/tools/vector_group_removed.svg index de085e75d..f11df16be 100644 --- a/data/icons/Default/tools/vector_group_removed.svg +++ b/data/icons/Default/tools/vector_group_removed.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/vector_line.svg b/data/icons/Default/tools/vector_line.svg index 7f987bcc3..71869c7a5 100644 --- a/data/icons/Default/tools/vector_line.svg +++ b/data/icons/Default/tools/vector_line.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/vector_polygon.svg b/data/icons/Default/tools/vector_polygon.svg index d19aed50e..ca73f5910 100644 --- a/data/icons/Default/tools/vector_polygon.svg +++ b/data/icons/Default/tools/vector_polygon.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/vector_rectangle.svg b/data/icons/Default/tools/vector_rectangle.svg index 55eaeec7e..3c66a4cd5 100644 --- a/data/icons/Default/tools/vector_rectangle.svg +++ b/data/icons/Default/tools/vector_rectangle.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/vector_shape.svg b/data/icons/Default/tools/vector_shape.svg index 21bf46df0..8d7173a9c 100644 --- a/data/icons/Default/tools/vector_shape.svg +++ b/data/icons/Default/tools/vector_shape.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/vector_spline.svg b/data/icons/Default/tools/vector_spline.svg index 8865663bf..20c89cfa7 100644 --- a/data/icons/Default/tools/vector_spline.svg +++ b/data/icons/Default/tools/vector_spline.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/tools/volume.svg b/data/icons/Default/tools/volume.svg index 8adf7047f..01b1351f9 100644 --- a/data/icons/Default/tools/volume.svg +++ b/data/icons/Default/tools/volume.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/users/group.svg b/data/icons/Default/users/group.svg index 9a690905d..8ead9aca1 100644 --- a/data/icons/Default/users/group.svg +++ b/data/icons/Default/users/group.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/users/group_add.svg b/data/icons/Default/users/group_add.svg index 975e8048a..61bb03f42 100644 --- a/data/icons/Default/users/group_add.svg +++ b/data/icons/Default/users/group_add.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/users/group_delete.svg b/data/icons/Default/users/group_delete.svg index eb0eadfba..2b9b44e5d 100644 --- a/data/icons/Default/users/group_delete.svg +++ b/data/icons/Default/users/group_delete.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/users/group_magnify.svg b/data/icons/Default/users/group_magnify.svg index 4d88f0dc1..c541e400b 100644 --- a/data/icons/Default/users/group_magnify.svg +++ b/data/icons/Default/users/group_magnify.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/users/group_minus.svg b/data/icons/Default/users/group_minus.svg index 4b2805354..4b9f5a5f7 100644 --- a/data/icons/Default/users/group_minus.svg +++ b/data/icons/Default/users/group_minus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/users/user_add.svg b/data/icons/Default/users/user_add.svg index a5d67954e..5a3722ef0 100644 --- a/data/icons/Default/users/user_add.svg +++ b/data/icons/Default/users/user_add.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/users/user_delete.svg b/data/icons/Default/users/user_delete.svg index f894fa9de..daf6bc6a1 100644 --- a/data/icons/Default/users/user_delete.svg +++ b/data/icons/Default/users/user_delete.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/users/user_magnify.svg b/data/icons/Default/users/user_magnify.svg index 9d1a85782..559c8eba9 100644 --- a/data/icons/Default/users/user_magnify.svg +++ b/data/icons/Default/users/user_magnify.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/users/user_minus.svg b/data/icons/Default/users/user_minus.svg index 8417ec6bb..80e974a50 100644 --- a/data/icons/Default/users/user_minus.svg +++ b/data/icons/Default/users/user_minus.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/users/user_profile.svg b/data/icons/Default/users/user_profile.svg index 83119c6c5..e91ed5b37 100644 --- a/data/icons/Default/users/user_profile.svg +++ b/data/icons/Default/users/user_profile.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/chance.svg b/data/icons/Default/weather/chance.svg index 517f26173..3beb5d7e2 100644 --- a/data/icons/Default/weather/chance.svg +++ b/data/icons/Default/weather/chance.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/dropleft.svg b/data/icons/Default/weather/dropleft.svg index 3bc4f9b9d..bed2269d1 100644 --- a/data/icons/Default/weather/dropleft.svg +++ b/data/icons/Default/weather/dropleft.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/moon.svg b/data/icons/Default/weather/moon.svg index 126bc500f..f79dbefe5 100644 --- a/data/icons/Default/weather/moon.svg +++ b/data/icons/Default/weather/moon.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/moon_first_quarter.svg b/data/icons/Default/weather/moon_first_quarter.svg index 1048566fa..c023d2399 100644 --- a/data/icons/Default/weather/moon_first_quarter.svg +++ b/data/icons/Default/weather/moon_first_quarter.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/moon_full.svg b/data/icons/Default/weather/moon_full.svg index 772064f16..5a7889b88 100644 --- a/data/icons/Default/weather/moon_full.svg +++ b/data/icons/Default/weather/moon_full.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/moon_new.svg b/data/icons/Default/weather/moon_new.svg index 1db36b8b9..450738cbd 100644 --- a/data/icons/Default/weather/moon_new.svg +++ b/data/icons/Default/weather/moon_new.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/moon_sleep.svg b/data/icons/Default/weather/moon_sleep.svg index fc94b4b57..77c18ea2e 100644 --- a/data/icons/Default/weather/moon_sleep.svg +++ b/data/icons/Default/weather/moon_sleep.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/moon_third_quarter.svg b/data/icons/Default/weather/moon_third_quarter.svg index 27dd21dce..be877a6de 100644 --- a/data/icons/Default/weather/moon_third_quarter.svg +++ b/data/icons/Default/weather/moon_third_quarter.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/moon_waning_crescent.svg b/data/icons/Default/weather/moon_waning_crescent.svg index ceacf2b72..afc1cb8b5 100644 --- a/data/icons/Default/weather/moon_waning_crescent.svg +++ b/data/icons/Default/weather/moon_waning_crescent.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/moon_waxing_crescent.svg b/data/icons/Default/weather/moon_waxing_crescent.svg index 2452d058c..0791e4d9f 100644 --- a/data/icons/Default/weather/moon_waxing_crescent.svg +++ b/data/icons/Default/weather/moon_waxing_crescent.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/overcast.svg b/data/icons/Default/weather/overcast.svg index 24a12b1b0..24e1d1823 100644 --- a/data/icons/Default/weather/overcast.svg +++ b/data/icons/Default/weather/overcast.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/rain.svg b/data/icons/Default/weather/rain.svg index 83211a204..c0127af8b 100644 --- a/data/icons/Default/weather/rain.svg +++ b/data/icons/Default/weather/rain.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/snow.svg b/data/icons/Default/weather/snow.svg index 01f5619cc..4cff3a314 100644 --- a/data/icons/Default/weather/snow.svg +++ b/data/icons/Default/weather/snow.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/snowflake.svg b/data/icons/Default/weather/snowflake.svg index fb0371ebe..7bee6bc64 100644 --- a/data/icons/Default/weather/snowflake.svg +++ b/data/icons/Default/weather/snowflake.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/snowman.svg b/data/icons/Default/weather/snowman.svg index 7f0abe82f..569fbd116 100644 --- a/data/icons/Default/weather/snowman.svg +++ b/data/icons/Default/weather/snowman.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/sun.svg b/data/icons/Default/weather/sun.svg index 9bca7ad04..35828bf48 100644 --- a/data/icons/Default/weather/sun.svg +++ b/data/icons/Default/weather/sun.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/sunrise.svg b/data/icons/Default/weather/sunrise.svg index ddb1ede73..17b058104 100644 --- a/data/icons/Default/weather/sunrise.svg +++ b/data/icons/Default/weather/sunrise.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/sunset.svg b/data/icons/Default/weather/sunset.svg index ff78e9633..b9e6bba19 100644 --- a/data/icons/Default/weather/sunset.svg +++ b/data/icons/Default/weather/sunset.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/thunder.svg b/data/icons/Default/weather/thunder.svg index cb2cb1f2b..aeee77cbe 100644 --- a/data/icons/Default/weather/thunder.svg +++ b/data/icons/Default/weather/thunder.svg @@ -1,5 +1,5 @@  - + diff --git a/data/icons/Default/weather/weather_station.svg b/data/icons/Default/weather/weather_station.svg index 1a70a8d73..8c303ace8 100644 --- a/data/icons/Default/weather/weather_station.svg +++ b/data/icons/Default/weather/weather_station.svg @@ -1,5 +1,5 @@  - + diff --git a/data/logos/clover.svg b/data/logos/clover.svg index 5e1251985..dff4ec88b 100644 --- a/data/logos/clover.svg +++ b/data/logos/clover.svg @@ -10,21 +10,29 @@ .st5{fill:#4BB7D8;} .st6{fill:#8CCFE4;} .st7{fill:#A1D18C;} + .st8{fill:#F2C7E3;} + .st9{fill:#B4E59C;} + .st10{fill:#F4E98C;} + .st11{fill:#95DEEF;} - - + + - + - + - - - + + + - + + + + + diff --git a/data/logos/parasol.svg b/data/logos/parasol.svg index cb97af831..a4661840b 100644 --- a/data/logos/parasol.svg +++ b/data/logos/parasol.svg @@ -1,72 +1,78 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/data/styles/default/values.xml b/data/styles/default/values.xml index 0a4acb0c0..eeaeda784 100644 --- a/data/styles/default/values.xml +++ b/data/styles/default/values.xml @@ -4,16 +4,16 @@ - - - - - - + + + + + + - - - + + + - - - - + - diff --git a/docs/html/images/clover.svg b/docs/html/images/clover.svg index 5e1251985..dff4ec88b 100644 --- a/docs/html/images/clover.svg +++ b/docs/html/images/clover.svg @@ -10,21 +10,29 @@ .st5{fill:#4BB7D8;} .st6{fill:#8CCFE4;} .st7{fill:#A1D18C;} + .st8{fill:#F2C7E3;} + .st9{fill:#B4E59C;} + .st10{fill:#F4E98C;} + .st11{fill:#95DEEF;} - - + + - + - + - - - + + + - + + + + + diff --git a/docs/html/images/parasol.svg b/docs/html/images/parasol.svg index cb97af831..a4661840b 100644 --- a/docs/html/images/parasol.svg +++ b/docs/html/images/parasol.svg @@ -1,72 +1,78 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/docs/xml/modules/audio.xml b/docs/xml/modules/audio.xml index 515c00e61..81c00678c 100644 --- a/docs/xml/modules/audio.xml +++ b/docs/xml/modules/audio.xml @@ -6,7 +6,7 @@ Audio module 1 - Paul Manias © 2002-2023 + Paul Manias © 2002-2024 Audio Sound @@ -16,7 +16,7 @@ MixContinue Continue playing a stopped channel. - ERROR sndMixContinue(objAudio * Audio, LONG Handle) + ERR sndMixContinue(objAudio * Audio, LONG Handle) The target Audio object. The target channel. @@ -24,7 +24,7 @@

This function will continue playback on a channel that has previously been stopped.

- + Operation successful. Function call missing argument value(s) @@ -33,7 +33,7 @@ MixEndSequence Ends the buffering of mix commands. - ERROR sndMixEndSequence(objAudio * Audio, LONG Handle) + ERR sndMixEndSequence(objAudio * Audio, LONG Handle) The target Audio object. The target channel. @@ -41,7 +41,7 @@

Use this function to end a buffered command sequence that was started by MixStartSequence.

- + Operation successful. Function call missing argument value(s) @@ -50,7 +50,7 @@ MixFrequency Sets a channel's playback rate. - ERROR sndMixFrequency(objAudio * Audio, LONG Handle, LONG Frequency) + ERR sndMixFrequency(objAudio * Audio, LONG Handle, LONG Frequency) The target Audio object. The target channel. @@ -59,7 +59,7 @@

Use this function to set the playback rate of a mixer channel.

- + Operation successful. Function call missing argument value(s) @@ -68,7 +68,7 @@ MixMute Mutes the audio of a channel. - ERROR sndMixMute(objAudio * Audio, LONG Handle, LONG Mute) + ERR sndMixMute(objAudio * Audio, LONG Handle, LONG Mute) The target Audio object. The target channel. @@ -77,7 +77,7 @@

Use this function to mute the audio of a mixer channel.

- + Operation successful. Function call missing argument value(s) @@ -86,7 +86,7 @@ MixPan Sets a channel's panning value. - ERROR sndMixPan(objAudio * Audio, LONG Handle, DOUBLE Pan) + ERR sndMixPan(objAudio * Audio, LONG Handle, DOUBLE Pan) The target Audio object. The target channel. @@ -95,7 +95,7 @@

Use this function to set a mixer channel's panning value. Accepted values are between -1.0 (left) and 1.0 (right).

- + Operation successful. Function call missing argument value(s) @@ -104,7 +104,7 @@ MixPlay Commences channel playback at a set frequency.. - ERROR sndMixPlay(objAudio * Audio, LONG Handle, LONG Position) + ERR sndMixPlay(objAudio * Audio, LONG Handle, LONG Position) The target Audio object. The target channel. @@ -113,7 +113,7 @@

This function will start playback of the sound sample associated with the target mixer channel. If the channel is already in playback mode, it will be stopped to facilitate the new playback request.

- + Operation successful. Function call missing argument value(s) @@ -122,7 +122,7 @@ MixRate Sets a new update rate for a channel. - ERROR sndMixRate(objAudio * Audio, LONG Handle, LONG Rate) + ERR sndMixRate(objAudio * Audio, LONG Handle, LONG Rate) The target Audio object. The channel set allocated from OpenChannels(). @@ -131,7 +131,7 @@

This function will set a new update rate for all channels, measured in milliseconds. The default update rate is 125, which is equivalent to 5000Hz.

- + Operation successful. Function call missing argument value(s) @@ -140,7 +140,7 @@ MixSample Associate a sound sample with a mixer channel. - ERROR sndMixSample(objAudio * Audio, LONG Handle, LONG Sample) + ERR sndMixSample(objAudio * Audio, LONG Handle, LONG Sample) The target Audio object. The target channel. @@ -150,7 +150,7 @@

This function will associate a sound sample with the channel identified by Handle. The client should follow this by setting configuration details (e.g. volume and pan values).

The referenced Sample must have been added to the audio server via the Audio:AddSample() or Audio:AddStream() methods.

- + Operation successful. Function call missing argument value(s) @@ -159,7 +159,7 @@ MixStartSequence Initiates buffering of mix commands. - ERROR sndMixStartSequence(objAudio * Audio, LONG Handle) + ERR sndMixStartSequence(objAudio * Audio, LONG Handle) The target Audio object. The target channel. @@ -168,7 +168,7 @@

Use this function to initiate the buffering of mix commands, up until a call to MixEndSequence is made. The buffering of mix commands makes it possible to create batches of commands that are executed at timed intervals as determined by MixRate.

This feature can be used to implement complex sound mixes and digital music players.

- + Operation successful. Function call missing argument value(s) @@ -177,7 +177,7 @@ MixStop Stops all playback on a channel. - ERROR sndMixStop(objAudio * Audio, LONG Handle) + ERR sndMixStop(objAudio * Audio, LONG Handle) The target Audio object. The target channel. @@ -185,7 +185,7 @@

This function will stop a channel that is currently playing.

- + Operation successful. Function call missing argument value(s) @@ -194,7 +194,7 @@ MixStopLoop Cancels any playback loop configured for a channel. - ERROR sndMixStopLoop(objAudio * Audio, LONG Handle) + ERR sndMixStopLoop(objAudio * Audio, LONG Handle) The target Audio object. The target channel. @@ -202,7 +202,7 @@

This function will cancel the loop that is associated with the channel identified by Handle if in playback mode. The existing loop configuration will remain intact if playback is restarted.

- + Operation successful. Function call missing argument value(s) @@ -211,7 +211,7 @@ MixVolume Changes the volume of a channel. - ERROR sndMixVolume(objAudio * Audio, LONG Handle, DOUBLE Volume) + ERR sndMixVolume(objAudio * Audio, LONG Handle, DOUBLE Volume) The target Audio object. The target channel. @@ -220,7 +220,7 @@

This function will change the volume of the mixer channel identified by Handle. Valid values are from 0 (silent) to 1.0 (maximum).

- + Operation successful. Function call missing argument value(s) diff --git a/docs/xml/modules/classes/audio.xml b/docs/xml/modules/classes/audio.xml index 46f09c763..a7e21b597 100644 --- a/docs/xml/modules/classes/audio.xml +++ b/docs/xml/modules/classes/audio.xml @@ -12,7 +12,7 @@ ID_AUDIO Audio modules/audio.h - Paul Manias © 2002-2023 + Paul Manias © 2002-2024

The Audio class provides a common audio service that works across multiple platforms and follows a client-server design model.

Supported features include 8/16/32 bit output in stereo or mono, oversampling, streaming, multiple audio channels and command sequencing. Audio functionality is simplified in the Sound class interface, which we recommend when straight-forward audio playback is sufficient.

@@ -56,7 +56,7 @@ AddSample Adds a new sample to an audio object for channel-based playback. - ERROR sndAddSample(OBJECTPTR Object, FUNCTION OnStop, SFM SampleFormat, APTR Data, LONG DataSize, struct AudioLoop * Loop, LONG LoopSize, LONG * Result) + ERR sndAddSample(OBJECTPTR Object, FUNCTION OnStop, SFM SampleFormat, APTR Data, LONG DataSize, struct AudioLoop * Loop, LONG LoopSize, LONG * Result) This optional callback function will be called when the stream stops playing. Indicates the format of the sample data that you are adding. @@ -89,7 +89,7 @@ AddStream Adds a new sample-stream to an Audio object for channel-based playback. - ERROR sndAddStream(OBJECTPTR Object, FUNCTION Callback, FUNCTION OnStop, SFM SampleFormat, LONG SampleLength, LONG PlayOffset, struct AudioLoop * Loop, LONG LoopSize, LONG * Result) + ERR sndAddStream(OBJECTPTR Object, FUNCTION Callback, FUNCTION OnStop, SFM SampleFormat, LONG SampleLength, LONG PlayOffset, struct AudioLoop * Loop, LONG LoopSize, LONG * Result) This callback function must be able to return raw audio data for streaming. This optional callback function will be called when the stream stops playing. @@ -124,7 +124,7 @@ Beep Beeps the PC audio speaker. - ERROR sndBeep(OBJECTPTR Object, LONG Pitch, LONG Duration, LONG Volume) + ERR sndBeep(OBJECTPTR Object, LONG Pitch, LONG Duration, LONG Volume) The pitch of the beep in HZ. The duration of the beep in milliseconds. @@ -143,7 +143,7 @@ CloseChannels Frees audio channels that have been allocated for sample playback. - ERROR sndCloseChannels(OBJECTPTR Object, LONG Handle) + ERR sndCloseChannels(OBJECTPTR Object, LONG Handle) Must refer to a channel handle returned from the OpenChannels method. @@ -160,7 +160,7 @@ OpenChannels Allocates audio channels that can be used for sample playback. - ERROR sndOpenChannels(OBJECTPTR Object, LONG Total, LONG * Result) + ERR sndOpenChannels(OBJECTPTR Object, LONG Total, LONG * Result) Total of channels to allocate. The resulting channel handle is returned in this parameter. @@ -181,7 +181,7 @@ RemoveSample Removes a sample from the global sample list and deallocates its resources. - ERROR sndRemoveSample(OBJECTPTR Object, LONG Handle) + ERR sndRemoveSample(OBJECTPTR Object, LONG Handle) The handle of the sample that requires removal. @@ -199,7 +199,7 @@ SetSampleLength Sets the byte length of a streaming sample. - ERROR sndSetSampleLength(OBJECTPTR Object, LONG Sample, LARGE Length) + ERR sndSetSampleLength(OBJECTPTR Object, LONG Sample, LARGE Length) A sample handle from AddStream(). Byte length of the sample stream. @@ -219,7 +219,7 @@ SetVolume Sets the volume for input and output mixers. - ERROR sndSetVolume(OBJECTPTR Object, LONG Index, CSTRING Name, SVF Flags, LONG Channel, DOUBLE Volume) + ERR sndSetVolume(OBJECTPTR Object, LONG Index, CSTRING Name, SVF Flags, LONG Channel, DOUBLE Volume) The index of the mixer that you want to set. If the correct index number is unknown, the name of the mixer may be set here. diff --git a/docs/xml/modules/classes/bitmap.xml b/docs/xml/modules/classes/bitmap.xml index e0b1b9600..f9935dc61 100644 --- a/docs/xml/modules/classes/bitmap.xml +++ b/docs/xml/modules/classes/bitmap.xml @@ -12,7 +12,7 @@ ID_BITMAP Graphics modules/bitmap.h - Paul Manias 2003-2023 + Paul Manias 2003-2024

The Bitmap class provides a way of describing an area of memory that an application can draw to, and/or display if the data is held in video memory. Bitmaps are used in the handling of Display and Picture objects, and form the backbone of Parasol's graphics functionality. The Bitmap class supports everything from basic graphics primitives to masking and alpha blending features.

To create a new bitmap object, you need to specify its Width and Height at a minimum. Preferably, you should also know how many colours you want to use and whether the bitmap data should be held in standard memory (for CPU based reading and writing) or video memory (for hardware based drawing). After creating a bitmap you can use a number of available drawing methods for the purpose of image management. Please note that these methods are designed to be called under exclusive conditions, and it is not recommended that you call methods on a bitmap using the message system.

@@ -89,8 +89,8 @@ Resize Resizes a bitmap object's dimensions. -

Resizing a bitmap will change its width, height and optionally bit depth. Existing image data is not retained after this process.

-

The image data is cleared with BkgdRGB if the CLEAR flag is defined in Flags.

+

Resizing a bitmap will change its width, height and optionally bit depth. Existing image data is not retained by this process.

+

The image data is cleared with BkgdRGB if the CLEAR flag is defined in Flags.

Operation successful. @@ -126,7 +126,7 @@ Compress Compresses bitmap data to save memory. - ERROR bmpCompress(OBJECTPTR Object, LONG Level) + ERR bmpCompress(OBJECTPTR Object, LONG Level) Level of compression. Zero uses a default setting (recommended), the maximum is 10. @@ -147,7 +147,7 @@ ConvertToLinear Convert a bitmap's colour space to linear RGB. - ERROR bmpConvertToLinear(OBJECTPTR Object) + ERR bmpConvertToLinear(OBJECTPTR Object)

Use ConvertToLinear to convert the colour space of a bitmap from sRGB to linear RGB. If the BMF::ALPHA_CHANNEL flag is enabled on the bitmap, pixels with an alpha value of 0 are ignored.

The ColourSpace will be set to LINEAR_RGB on completion. This method returns immediately if the ColourSpace is already set to LINEAR_RGB.

@@ -164,7 +164,7 @@ ConvertToRGB Convert a bitmap's colour space to standard RGB. - ERROR bmpConvertToRGB(OBJECTPTR Object) + ERR bmpConvertToRGB(OBJECTPTR Object)

Use ConvertToRGB to convert the colour space of a bitmap from linear RGB to sRGB. If the BMF::ALPHA_CHANNEL flag is enabled on the bitmap, pixels with an alpha value of 0 are ignored.

The ColourSpace will be set to SRGB on completion. This method returns immediately if the ColourSpace is already set to SRGB.

@@ -181,7 +181,7 @@ CopyArea Copies a rectangular area from one bitmap to another. - ERROR bmpCopyArea(OBJECTPTR Object, objBitmap * DestBitmap, BAF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) + ERR bmpCopyArea(OBJECTPTR Object, objBitmap * DestBitmap, BAF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) The target bitmap. Optional flags. @@ -205,7 +205,7 @@ Decompress Decompresses a compressed bitmap. - ERROR bmpDecompress(OBJECTPTR Object, LONG RetainData) + ERR bmpDecompress(OBJECTPTR Object, LONG RetainData) Retains the compression data if TRUE. @@ -222,9 +222,9 @@ Demultiply Reverses the conversion process performed by Premultiply(). - ERROR bmpDemultiply(OBJECTPTR Object) + ERR bmpDemultiply(OBJECTPTR Object) -

Use Demultiply to normalise RGB values that have previously been converted by Premultiply. This method will return immediately if the bitmap values are already normalised.

+

Use Demultiply to normalise RGB values that have previously been converted by Premultiply. This method will return immediately if the bitmap values are already normalised, as determined by the presence of the PREMUL value in Flags.

Operation successful. @@ -237,7 +237,7 @@ DrawRectangle Draws rectangles, both filled and unfilled. - ERROR bmpDrawRectangle(OBJECTPTR Object, LONG X, LONG Y, LONG Width, LONG Height, ULONG Colour, BAF Flags) + ERR bmpDrawRectangle(OBJECTPTR Object, LONG X, LONG Y, LONG Width, LONG Height, ULONG Colour, BAF Flags) The left-most coordinate of the rectangle. The top-most coordinate of the rectangle. @@ -258,7 +258,7 @@ Flip Flips a bitmap around the horizontal or vertical axis. - ERROR bmpFlip(OBJECTPTR Object, FLIP Orientation) + ERR bmpFlip(OBJECTPTR Object, FLIP Orientation) Set to either FLIP_HORIZONTAL or FLIP_VERTICAL. @@ -275,7 +275,7 @@ GetColour Converts Red, Green, Blue components into a single colour value. - ERROR bmpGetColour(OBJECTPTR Object, LONG Red, LONG Green, LONG Blue, LONG Alpha, ULONG * Colour) + ERR bmpGetColour(OBJECTPTR Object, LONG Red, LONG Green, LONG Blue, LONG Alpha, ULONG * Colour) Red component from 0 - 255. Green component from 0 - 255. @@ -295,7 +295,7 @@ Premultiply Premultiplies RGB channel values by the alpha channel. - ERROR bmpPremultiply(OBJECTPTR Object) + ERR bmpPremultiply(OBJECTPTR Object)

Use Premultiply to convert all RGB values in the bitmap's clipping region to pre-multiplied values. The exact formula applied per channel is (Colour * Alpha + 0xff)>>8. The alpha channel is not affected.

This method will only operate on 32 bit bitmaps, and an alpha channel must be present. If the RGB values are already pre-multiplied, the method returns immediately.

@@ -312,7 +312,7 @@ SetClipRegion Sets a clipping region for a bitmap object. - ERROR bmpSetClipRegion(OBJECTPTR Object, LONG Number, LONG Left, LONG Top, LONG Right, LONG Bottom, LONG Terminate) + ERR bmpSetClipRegion(OBJECTPTR Object, LONG Number, LONG Left, LONG Top, LONG Right, LONG Bottom, LONG Terminate) The number of the clip region to set. The horizontal start of the clip region. diff --git a/docs/xml/modules/classes/blurfx.xml b/docs/xml/modules/classes/blurfx.xml index 15c1ef216..90b0e53ff 100644 --- a/docs/xml/modules/classes/blurfx.xml +++ b/docs/xml/modules/classes/blurfx.xml @@ -12,9 +12,9 @@ ID_BLURFX Graphics modules/blurfx.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024 -

The BlurFX class performs a Gaussian blur on the input source. The Gaussian blur kernel is an approximation of the normalized convolution G(x,y) = H(x)I(y) where H(x) = exp(-x2/ (2s2)) / sqrt(2* pi*s2) and I(y) = exp(-y2/ (2t2)) / sqrt(2* pi*t2) with 's' being the standard deviation in the x direction and 't' being the standard deviation in the y direction, as specified by SX and SY.

+

The BlurFX class performs a Gaussian blur, or approximation thereof, on the input source. The Gaussian blur kernel is an approximation of the normalized convolution G(x,y) = H(x)I(y) where H(x) = exp(-x2/ (2s2)) / sqrt(2* pi*s2) and I(y) = exp(-y2/ (2t2)) / sqrt(2* pi*t2) with 's' being the standard deviation in the x direction and 't' being the standard deviation in the y direction, as specified by SX and SY.

At least one of SX or SY should be greater than 0, otherwise no rendering is performed.

filter_blur.cpp diff --git a/docs/xml/modules/classes/clientsocket.xml b/docs/xml/modules/classes/clientsocket.xml index 420c2e7aa..fd49b8fea 100644 --- a/docs/xml/modules/classes/clientsocket.xml +++ b/docs/xml/modules/classes/clientsocket.xml @@ -12,7 +12,7 @@ ID_CLIENTSOCKET Network modules/clientsocket.h - Paul Manias © 2005-2023 + Paul Manias © 2005-2024

If a Netsocket is running in server mode then it will create a new ClientSocket object every time that a new connection is opened by a client. This is a very simple class that assists in the management of I/O between the client and server.

@@ -49,7 +49,7 @@ ReadClientMsg Read a message from the socket. - ERROR csReadClientMsg(OBJECTPTR Object, APTR * Message, LONG * Length, LONG * Progress, LONG * CRC) + ERR csReadClientMsg(OBJECTPTR Object, APTR * Message, LONG * Length, LONG * Progress, LONG * CRC) A pointer to the message buffer will be placed here if a message has been received. The length of the message is returned here. @@ -74,7 +74,7 @@ WriteClientMsg Writes a message to the socket. - ERROR csWriteClientMsg(OBJECTPTR Object, APTR Message, LONG Length) + ERR csWriteClientMsg(OBJECTPTR Object, APTR Message, LONG Length) Pointer to the message to send. The length of the message. diff --git a/docs/xml/modules/classes/clipboard.xml b/docs/xml/modules/classes/clipboard.xml index 30dffe0da..55bea94e9 100644 --- a/docs/xml/modules/classes/clipboard.xml +++ b/docs/xml/modules/classes/clipboard.xml @@ -12,7 +12,7 @@ ID_CLIPBOARD IO modules/clipboard.h - Paul Manias 2003-2023 + Paul Manias 2003-2024

The Clipboard class manages data transfer between applications on behalf of the user. Depending on the host system, behaviour between platforms can vary.

On Windows the clipboard is tightly integrated by default, allowing it to support native Windows applications. This reduces the default feature set, but ensures that the clipboard behaves in a way that the user would expect it to. If historical buffering is enabled with the CPF::HISTORY_BUFFER option then the clipboard API will actively monitor the clipboard and store copied data in the local clipboard: file cache. This results in additional overhead to clipboard management.

@@ -44,7 +44,7 @@ AddFile Add files to the clipboard. - ERROR clipAddFile(OBJECTPTR Object, CLIPTYPE Datatype, CSTRING Path, CEF Flags) + ERR clipAddFile(OBJECTPTR Object, CLIPTYPE Datatype, CSTRING Path, CEF Flags) Set this argument to indicate the type of data you are copying to the clipboard. The path of the file to add. @@ -67,7 +67,7 @@ AddObjects Extract data from objects and add it all to the clipboard. - ERROR clipAddObjects(OBJECTPTR Object, CLIPTYPE Datatype, OBJECTID * Objects, CEF Flags) + ERR clipAddObjects(OBJECTPTR Object, CLIPTYPE Datatype, OBJECTID * Objects, CEF Flags) The type of data representing the objects, or NULL for automatic recognition. Array of object ID's to add to the clipboard. @@ -88,7 +88,7 @@ AddText Adds a block of text to the clipboard. - ERROR clipAddText(OBJECTPTR Object, CSTRING String) + ERR clipAddText(OBJECTPTR Object, CSTRING String) The text to add to the clipboard. @@ -105,7 +105,7 @@ GetFiles Retrieve the most recently clipped data as a list of files. - ERROR clipGetFiles(OBJECTPTR Object, CLIPTYPE * Datatype, LONG Index, CSTRING ** Files, CEF * Flags) + ERR clipGetFiles(OBJECTPTR Object, CLIPTYPE * Datatype, LONG Index, CSTRING ** Files, CEF * Flags) Filter down to the specified data types. This parameter will be updated to reflect the retrieved data type when the method returns. Set to zero to disable. If the Datatype parameter is zero, this parameter may be set to the index of the desired clip item. @@ -114,7 +114,7 @@

This method returns a list of items that are on the clipboard. The caller must declare the types of data that it supports (or zero if all datatypes are recognised).

-

The most recently clipped datatype is always returned. To scan for all available clip items, set the Datatype parameter to zero and repeatedly call this method with incremented Index numbers until the error code ERR_OutOfRange is returned.

+

The most recently clipped datatype is always returned. To scan for all available clip items, set the Datatype parameter to zero and repeatedly call this method with incremented Index numbers until the error code ERR::OutOfRange is returned.

On success this method will return a list of files (terminated with a NULL entry) in the Files parameter. Each file is a readable clipboard entry - how the client reads it depends on the resulting Datatype. Additionally, the IdentifyFile function could be used to find a class that supports the data. The resulting Files array is a memory allocation that must be freed with a call to FreeResource.

If this method returns the CEF::DELETE flag in the Flags parameter, the client must delete the source files after successfully copying the data. When cutting and pasting files within the file system, using MoveFile is recommended as the most efficient method.

@@ -129,7 +129,7 @@ Remove Remove items from the clipboard. - ERROR clipRemove(OBJECTPTR Object, CLIPTYPE Datatype) + ERR clipRemove(OBJECTPTR Object, CLIPTYPE Datatype) The datatype(s) that will be deleted (datatypes may be logically-or'd together). @@ -164,8 +164,8 @@

Applications can request data from a clipboard if it is in drag-and-drop mode by sending a DATA::REQUEST to the Clipboard's DataFeed action. Doing so will result in a callback to the function that is referenced in the RequestHandler, which must be defined by the source application. The RequestHandler function must follow this template:

-ERROR RequestHandler(*Clipboard, OBJECTPTR Requester, LONG Item, BYTE Datatypes[4])

-

The function will be expected to send a DATA::RECEIPT to the object referenced in the Requester paramter. The receipt must provide coverage for the referenced Item and use one of the indicated Datatypes as the data format. If this cannot be achieved then ERR_NoSupport should be returned by the function.

+ERR RequestHandler(*Clipboard, OBJECTPTR Requester, LONG Item, BYTE Datatypes[4])

+

The function will be expected to send a DATA::RECEIPT to the object referenced in the Requester paramter. The receipt must provide coverage for the referenced Item and use one of the indicated Datatypes as the data format. If this cannot be achieved then ERR::NoSupport should be returned by the function.

diff --git a/docs/xml/modules/classes/colourfx.xml b/docs/xml/modules/classes/colourfx.xml index a232de46f..63696804f 100644 --- a/docs/xml/modules/classes/colourfx.xml +++ b/docs/xml/modules/classes/colourfx.xml @@ -12,7 +12,7 @@ ID_COLOURFX Graphics modules/colourfx.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

Use ColourFX to perform colour transformations on an input source. A Mode must be selected and any required Values defined prior to rendering.

SVG requires that the calculations are performed on non-premultiplied colour values. If the input graphics consists of premultiplied colour values, those values are automatically converted into non-premultiplied colour values for this operation.

diff --git a/docs/xml/modules/classes/compositefx.xml b/docs/xml/modules/classes/compositefx.xml index c5e8f1aad..1d22a4255 100644 --- a/docs/xml/modules/classes/compositefx.xml +++ b/docs/xml/modules/classes/compositefx.xml @@ -12,7 +12,7 @@ ID_COMPOSITEFX Graphics modules/compositefx.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

This filter combines the Input and Mix sources using either one of the Porter-Duff compositing operations, or a colour blending algorithm. The Input has priority and will be placed in the foreground for ordered operations such as Atop and Over.

diff --git a/docs/xml/modules/classes/compressedstream.xml b/docs/xml/modules/classes/compressedstream.xml index 1156b6dbf..2bb3ac090 100644 --- a/docs/xml/modules/classes/compressedstream.xml +++ b/docs/xml/modules/classes/compressedstream.xml @@ -13,7 +13,7 @@ ID_COMPRESSEDSTREAM Data modules/compressedstream.h - Paul Manias 1996-2023 + Paul Manias 1996-2024

Use the CompressedStream class to compress and decompress data on the fly without the need for a temporary storage area. The default compression algorithm is DEFLATE with gzip header data. It is compatible with common command-line tools such as gzip.

To decompress data, set the Input field with a source object that supports the Read action, such as a File. Repeatedly reading from the CompressedStream will automatically handle the decompression process for you. If the decompressed size of the incoming data is defined in the source header, it will be reflected in the Size field.

@@ -165,7 +165,7 @@ - Limits the routine to checking the file cache for the existence of the file. If found, the relevant cache entry is returned. The open count is not incremented by this action (it is therefore unnecessary to follow-up with a call to UnloadFile()). If no up-to-date cache entry is available, ERR_Search is returned. + Limits the routine to checking the file cache for the existence of the file. If found, the relevant cache entry is returned. The open count is not incremented by this action (it is therefore unnecessary to follow-up with a call to UnloadFile()). If no up-to-date cache entry is available, ERR::Search is returned. @@ -199,7 +199,7 @@ The default behaviour - this will add the message to the end of the queue. The Type parameter refers to a unique message ID rather than a message type for this call. - If the Type parameter matches a message already inside the queue, the new message will not be added and the function will immediately return with ERR_Okay. + If the Type parameter matches a message already inside the queue, the new message will not be added and the function will immediately return with ERR::Okay. If the Type parameter matches a message already inside the queue, the data for that message will be deleted, then the new message will be added to the end of the queue. Wait before inserting the message if the queue is at maximum capacity. @@ -231,7 +231,7 @@ The object switched from the base-class to a sub-class during initialisation. The object has been signalled and is awaiting processing. The object is subscribed to a timer interval. - Use to allocate an object that has a guaranteed unique name. This will prevent code from shadowing any object that exists with the same name, which can be imperative when creating shared objects. If it is discovered that an identically named object exists, NewObject() will return ERR_ObjectExists. This flag works in conjunction with the Name argument. + Use to allocate an object that has a guaranteed unique name. This will prevent code from shadowing any object that exists with the same name, which can be imperative when creating shared objects. If it is discovered that an identically named object exists, NewObject() will return ERR::ObjectExists. This flag works in conjunction with the Name argument. An object created with this flag will not be tracked back to the object that created it. @@ -340,7 +340,7 @@ Ignores file extensions for the purpose of file name matching. For use on host systems that use case-insensitive file systems such as Windows; this option checks that the discovered file is a case-sensitive match to the Path. - If the volume referenced by Path is traced to another volume that is reserved by a virtual file system driver, ERR_VirtualVolume is returned. The volume is still resolved as far as possible and the resulting path will be returned by this function. + If the volume referenced by Path is traced to another volume that is reserved by a virtual file system driver, ERR::VirtualVolume is returned. The volume is still resolved as far as possible and the resulting path will be returned by this function. Do not perform more than one iteration when resolving the source file path. Do not test for the existence of the targeted file or folder during the resolution process. Use the PATH environment variable to resolve the file name in the Path parameter. @@ -364,9 +364,8 @@ - + - @@ -400,9 +399,9 @@ An option to complement the field type. Can be a pointer or an integer value - A virtual function that will retrieve the value for this field. + A virtual function that will retrieve the value for this field. A virtual function that will set the value for this field. - An internal function for writing to this field. + An internal function for writing to this field. The English name for the field, e.g. "Width" Provides a fast way of finding fields, e.g. FID_WIDTH Field offset within the object diff --git a/docs/xml/modules/classes/compression.xml b/docs/xml/modules/classes/compression.xml index 9c5e6b5b0..267d03426 100644 --- a/docs/xml/modules/classes/compression.xml +++ b/docs/xml/modules/classes/compression.xml @@ -14,7 +14,7 @@ ID_COMPRESSION Data modules/compression.h - Paul Manias 1996-2023 + Paul Manias 1996-2024

The Compression class provides the necessary means to compress and decompress data. It provides support for file based compression as well as memory based compression routines. The base class uses zip algorithms to support pkzip files, while other forms of compressed data can be supported by installing additional compression sub-classes.

The following examples demonstrate basic usage of compression objects in Fluid:

@@ -52,7 +52,7 @@ err = cmp.mtDecompressFile('*.def', 'temp:') CompressBuffer Compresses a plain memory area into an empty buffer. - ERROR cmpCompressBuffer(OBJECTPTR Object, APTR Input, LONG InputSize, APTR Output, LONG OutputSize, LONG * Result) + ERR cmpCompressBuffer(OBJECTPTR Object, APTR Input, LONG InputSize, APTR Output, LONG OutputSize, LONG * Result) Pointer to the source data. Byte length of the source data. @@ -61,7 +61,7 @@ err = cmp.mtDecompressFile('*.def', 'temp:') The size of the compressed data will be returned in this parameter. -

This method provides a simple way of compressing a memory area into a buffer. It requires a reference to the source data and a buffer large enough to accept the compressed information. Generally the destination buffer should be no smaller than 75% of the size of the source data. If the destination buffer is not large enough, an error of ERR_BufferOverflow will be returned. The size of the compressed data will be returned in the Result parameter.

+

This method provides a simple way of compressing a memory area into a buffer. It requires a reference to the source data and a buffer large enough to accept the compressed information. Generally the destination buffer should be no smaller than 75% of the size of the source data. If the destination buffer is not large enough, an error of ERR::BufferOverflow will be returned. The size of the compressed data will be returned in the Result parameter.

To decompress the data that is output by this function, use the DecompressBuffer method.

The compression method used to compress the data will be identified in the first 32 bits of output, for example, ZLIB. The following 32 bits will indicate the length of the compressed data section, followed by the data itself.

@@ -77,7 +77,7 @@ err = cmp.mtDecompressFile('*.def', 'temp:') CompressFile Add files to a compression object. - ERROR cmpCompressFile(OBJECTPTR Object, CSTRING Location, CSTRING Path) + ERR cmpCompressFile(OBJECTPTR Object, CSTRING Location, CSTRING Path) The location of the file(s) to add. The path that is prefixed to the file name when added to the compression object. May be NULL for no path. @@ -99,7 +99,7 @@ err = cmp.mtDecompressFile('*.def', 'temp:') CompressStream Compresses streamed data into a buffer. - ERROR cmpCompressStream(OBJECTPTR Object, APTR Input, LONG Length, FUNCTION * Callback, APTR Output, LONG OutputSize) + ERR cmpCompressStream(OBJECTPTR Object, APTR Input, LONG Length, FUNCTION * Callback, APTR Output, LONG OutputSize) Pointer to the source data. Amount of data to compress, in bytes. @@ -112,7 +112,7 @@ err = cmp.mtDecompressFile('*.def', 'temp:')

A compression object can manage only one compression stream at any given time. If it is necessary to compress multiple streams at once, create a compression object for each individual stream.

No meta-information is written to the stream, so the client will need a way to record the total number of bytes that have been output during the compression process. This value must be stored somewhere in order to decompress the stream correctly. There is also no header information recorded to identify the type of algorithm used to compress the stream. We recommend that the compression object's sub-class ID is stored for future reference.

The following C code illustrates a simple means of compressing a file to another file using a stream:

-
ERROR error = mtCompressStreamStart(compress);
+
ERR error = mtCompressStreamStart(compress);
 
 if (!error) {
    LONG len;
@@ -153,7 +153,7 @@ if (!error) {
     
       CompressStreamEnd
       Ends the compression of an open stream.
-      ERROR cmpCompressStreamEnd(OBJECTPTR Object, FUNCTION * Callback, APTR Output, LONG OutputSize)
+      ERR cmpCompressStreamEnd(OBJECTPTR Object, FUNCTION * Callback, APTR Output, LONG OutputSize)
       
         Refers to a function that will be called for each compressed block of data.
         Optional pointer to a buffer that will receive the compressed data.  If not set, the compression object will use its own buffer.
@@ -173,7 +173,7 @@ if (!error) {
     
       CompressStreamStart
       Initialises a new compression stream.
-      ERROR cmpCompressStreamStart(OBJECTPTR Object)
+      ERR cmpCompressStreamStart(OBJECTPTR Object)
       
 

The level of compression is determined by the CompressionLevel field value.

@@ -186,7 +186,7 @@ if (!error) { DecompressBuffer Decompresses data originating from the CompressBuffer method. - ERROR cmpDecompressBuffer(OBJECTPTR Object, APTR Input, APTR Output, LONG OutputSize, LONG * Result) + ERR cmpDecompressBuffer(OBJECTPTR Object, APTR Input, APTR Output, LONG OutputSize, LONG * Result) Pointer to the compressed data. Pointer to the decompression buffer. @@ -194,7 +194,7 @@ if (!error) { The amount of bytes decompressed will be returned in this parameter. -

This method is used to decompress data that has been packed using the CompressBuffer method. A pointer to the compressed data and an output buffer large enough to contain the decompressed data are required. If the output buffer is not large enough to contain the data, the method will write out as much information as it can and then return with an error code of ERR_BufferOverflow.

+

This method is used to decompress data that has been packed using the CompressBuffer method. A pointer to the compressed data and an output buffer large enough to contain the decompressed data are required. If the output buffer is not large enough to contain the data, the method will write out as much information as it can and then return with an error code of ERR::BufferOverflow.

Operation successful. @@ -206,7 +206,7 @@ if (!error) { DecompressFile Extracts one or more files from a compression object. - ERROR cmpDecompressFile(OBJECTPTR Object, CSTRING Path, CSTRING Dest, LONG Flags) + ERR cmpDecompressFile(OBJECTPTR Object, CSTRING Path, CSTRING Dest, LONG Flags) The full path name of the file to extract from the archive. The destination to extract the file to. @@ -234,7 +234,7 @@ if (!error) { DecompressObject Decompresses one file to a target object. - ERROR cmpDecompressObject(OBJECTPTR Object, CSTRING Path, OBJECTPTR Object) + ERR cmpDecompressObject(OBJECTPTR Object, CSTRING Path, OBJECTPTR Object) The location of the source file within the archive. If a wildcard is used, the first matching file is extracted. The target object for the decompressed source data. @@ -257,7 +257,7 @@ if (!error) { DecompressStream Decompresses streamed data to an output buffer. - ERROR cmpDecompressStream(OBJECTPTR Object, APTR Input, LONG Length, FUNCTION * Callback, APTR Output, LONG OutputSize) + ERR cmpDecompressStream(OBJECTPTR Object, APTR Input, LONG Length, FUNCTION * Callback, APTR Output, LONG OutputSize) Pointer to data to decompress. Amount of data to decompress from the Input parameter. @@ -267,7 +267,7 @@ if (!error) {

Call DecompressStream repeatedly to decompress a data stream and process the results in a callback routine. The client will need to provide a pointer to the data in the Input parameter and indicate its size in Length. The decompression routine will call the routine that was specified in Callback for each block that is decompressed.

-

The format of the Callback routine is ERROR Function(*Compression, APTR Buffer, LONG Length)

+

The format of the Callback routine is ERR Function(*Compression, APTR Buffer, LONG Length)

The Buffer will refer to the start of the decompressed data and its size will be indicated in Length. If the Callback routine returns an error of any kind, the decompression process will be stopped and the error code will be immediately returned by the method.

Optionally, the client can specify an output buffer in the Output parameter. This can be a valuable optimisation technique, as it will eliminate the need to copy data out of the compression object's internal buffer.

When there is no more data in the decompression stream or if an error has occurred, the client must call DecompressStreamEnd.

@@ -283,7 +283,7 @@ if (!error) { DecompressStreamEnd Must be called at the end of the decompression process. - ERROR cmpDecompressStreamEnd(OBJECTPTR Object, FUNCTION * Callback) + ERR cmpDecompressStreamEnd(OBJECTPTR Object, FUNCTION * Callback) Refers to a function that will be called for each decompressed block of information. @@ -299,7 +299,7 @@ if (!error) { DecompressStreamStart Initialises a new decompression stream. - ERROR cmpDecompressStreamStart(OBJECTPTR Object) + ERR cmpDecompressStreamStart(OBJECTPTR Object)

Use the DecompressStreamStart method to initialise a new decompression stream. No parameters are required.

If a decompression stream is already active at the time that this method is called, all resources associated with that stream will be deallocated so that the new stream can be initiated.

@@ -314,7 +314,7 @@ if (!error) { Find Find the first item that matches a given filter. - ERROR cmpFind(OBJECTPTR Object, CSTRING Path, STR Flags, struct CompressedItem ** Item) + ERR cmpFind(OBJECTPTR Object, CSTRING Path, STR Flags, struct CompressedItem ** Item) Search for a specific item or items, using wildcards. String comparison flags used by StrCompare(). @@ -335,7 +335,7 @@ if (!error) { RemoveFile Deletes one or more files from a compression object. - ERROR cmpRemoveFile(OBJECTPTR Object, CSTRING Path) + ERR cmpRemoveFile(OBJECTPTR Object, CSTRING Path) The full path name of the file to delete from the archive. @@ -353,14 +353,14 @@ if (!error) { Scan Scan the archive's index of compressed data. - ERROR cmpScan(OBJECTPTR Object, CSTRING Folder, CSTRING Filter, FUNCTION * Callback) + ERR cmpScan(OBJECTPTR Object, CSTRING Folder, CSTRING Filter, FUNCTION * Callback) If defined, only items within the specified folder are returned. Use an empty string for files in the root folder. Search for a specific item or items by name, using wildcards. If NULL or an empty string, all items will be scanned. This callback function will be called with a pointer to a CompressedItem structure. -

Use the Scan method to search an archive's list of items. Optional filtering can be applied using the Folder parameter to limit results to those within a folder, and Filter parameter to apply wildcard matching to item names. Each item that is discovered during the scan will be passed to the function referenced in the Callback parameter. If the Callback function returns ERR_Terminate, the scan will stop immediately. The synopsis of the callback function is ERROR Function(*Compression, *CompressedItem).

+

Use the Scan method to search an archive's list of items. Optional filtering can be applied using the Folder parameter to limit results to those within a folder, and Filter parameter to apply wildcard matching to item names. Each item that is discovered during the scan will be passed to the function referenced in the Callback parameter. If the Callback function returns ERR::Terminate, the scan will stop immediately. The synopsis of the callback function is ERR Function(*Compression, *CompressedItem).

The CompressedItem structure consists of the following fields:

To search for a single item with a path and name already known, please use the Find method instead.

@@ -401,9 +401,9 @@ if (!error) { Get/Set FUNCTION -

To receive feedback during any de/compression process, set a callback routine in this field. The format for the callback routine is ERROR Function(*Compression, *CompressionFeedback).

+

To receive feedback during any de/compression process, set a callback routine in this field. The format for the callback routine is ERR Function(*Compression, *CompressionFeedback).

For object classes, the object that initiated the de/compression process can be learned by calling the Core's CurrentContext function.

-

During the processing of multiple files, any individual file can be skipped by returning ERR_Skip and the entire process can be cancelled by returning ERR_Terminate. All other error codes are ignored.

+

During the processing of multiple files, any individual file can be skipped by returning ERR::Skip and the entire process can be cancelled by returning ERR::Terminate. All other error codes are ignored.

The CompressionFeedback structure consists of the following fields:

diff --git a/docs/xml/modules/classes/config.xml b/docs/xml/modules/classes/config.xml index ebe5d13a7..b8ecf2afc 100644 --- a/docs/xml/modules/classes/config.xml +++ b/docs/xml/modules/classes/config.xml @@ -14,7 +14,7 @@ ID_CONFIG Data modules/config.h - Paul Manias 1996-2023 + Paul Manias 1996-2024

The Config class is provided for reading text based key-values in a simple structured format. Although basic and lacking support for trees and types, they are reliable, easy to support and use minimal resources.

The following segment of a config file illustrates:

@@ -85,7 +85,7 @@ print('The Action class is located at ' .. str) DeleteGroup Deletes entire groups of configuration data. - ERROR cfgDeleteGroup(OBJECTPTR Object, CSTRING Group) + ERR cfgDeleteGroup(OBJECTPTR Object, CSTRING Group) The name of the group that will be deleted. @@ -101,7 +101,7 @@ print('The Action class is located at ' .. str) DeleteKey Deletes single key entries. - ERROR cfgDeleteKey(OBJECTPTR Object, CSTRING Group, CSTRING Key) + ERR cfgDeleteKey(OBJECTPTR Object, CSTRING Group, CSTRING Key) The name of the targeted group. The name of the targeted key. @@ -119,7 +119,7 @@ print('The Action class is located at ' .. str) GetGroupFromIndex Converts an index number into its matching group string. - ERROR cfgGetGroupFromIndex(OBJECTPTR Object, LONG Index, CSTRING * Group) + ERR cfgGetGroupFromIndex(OBJECTPTR Object, LONG Index, CSTRING * Group) The group index that you want to identify. Points to the group string that matches the index number. @@ -138,9 +138,9 @@ print('The Action class is located at ' .. str) Merge Merges two config objects together. - ERROR cfgMerge(OBJECTPTR Object, OBJECTPTR Source) + ERR cfgMerge(OBJECTPTR Object, OBJECTPTR Source) - The ID of the config object to be merged. + The config object to be merged.

The Merge method is used to merge configuration data from one config object provided as a source, into the target object. Existing data in the target will be overwritten by the source in cases where there matching set of group keys.

@@ -154,8 +154,8 @@ print('The Action class is located at ' .. str) MergeFile - Merges a foreign configuration file into existing configuration data. - ERROR cfgMergeFile(OBJECTPTR Object, CSTRING Path) + Merges a configuration file into existing configuration data. + ERR cfgMergeFile(OBJECTPTR Object, CSTRING Path) The location of the configuration file that you want to merge. @@ -172,7 +172,7 @@ print('The Action class is located at ' .. str) ReadValue Reads a key-value string. - ERROR cfgReadValue(OBJECTPTR Object, CSTRING Group, CSTRING Key, CSTRING * Data) + ERR cfgReadValue(OBJECTPTR Object, CSTRING Group, CSTRING Key, CSTRING * Data) The name of a group to examine for a key. If NULL, all groups are scanned. The name of a key to retrieve (case sensitive). @@ -192,14 +192,14 @@ print('The Action class is located at ' .. str) Set Sets keys in existing config groups (aborts if the group does not exist). - ERROR cfgSet(OBJECTPTR Object, CSTRING Group, CSTRING Key, CSTRING Data) + ERR cfgSet(OBJECTPTR Object, CSTRING Group, CSTRING Key, CSTRING Data) The name of the group. Wildcards are supported. The name of the key. The data that will be added to the given group/key. -

This method is identical to WriteValue except it will abort if the name of the referred group does not exist in the config object. The error code ERR_Search is returned if this is the case. Please refer to WriteValue for further information on the behaviour of this function.

+

This method is identical to WriteValue except it will abort if the name of the referred group does not exist in the config object. The error code ERR::Search is returned if this is the case. Please refer to WriteValue for further information on the behaviour of this function.

Operation successful. @@ -213,7 +213,7 @@ print('The Action class is located at ' .. str) SortByKey Sorts config data using a sequence of sort instructions. - ERROR cfgSortByKey(OBJECTPTR Object, CSTRING Key, LONG Descending) + ERR cfgSortByKey(OBJECTPTR Object, CSTRING Key, LONG Descending) The name of the key to sort on. Set to TRUE if a descending sort is required. @@ -230,7 +230,7 @@ print('The Action class is located at ' .. str) WriteValue Adds new entries to config objects. - ERROR cfgWriteValue(OBJECTPTR Object, CSTRING Group, CSTRING Key, CSTRING Data) + ERR cfgWriteValue(OBJECTPTR Object, CSTRING Group, CSTRING Key, CSTRING Data) The name of the group. The name of the key. diff --git a/docs/xml/modules/classes/convolvefx.xml b/docs/xml/modules/classes/convolvefx.xml index 4ec5c2fa3..804f3894c 100644 --- a/docs/xml/modules/classes/convolvefx.xml +++ b/docs/xml/modules/classes/convolvefx.xml @@ -12,7 +12,7 @@ ID_CONVOLVEFX Graphics modules/convolvefx.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

Convolve applies a matrix convolution filter effect to an input source. A convolution combines pixels in the input image with neighbouring pixels to produce a resulting image. A wide variety of imaging operations can be achieved through convolutions, including blurring, edge detection, sharpening, embossing and beveling.

A matrix convolution is based on an n-by-m matrix (the convolution kernel) which describes how a given pixel value in the input image is combined with its neighbouring pixel values to produce a resulting pixel value. Each result pixel is determined by applying the kernel matrix to the corresponding source pixel and its neighbouring pixels. The basic convolution formula which is applied to each colour value for a given pixel is:

diff --git a/docs/xml/modules/classes/displacementfx.xml b/docs/xml/modules/classes/displacementfx.xml index a53265c09..9ea04ccb1 100644 --- a/docs/xml/modules/classes/displacementfx.xml +++ b/docs/xml/modules/classes/displacementfx.xml @@ -12,7 +12,7 @@ ID_DISPLACEMENTFX Graphics modules/displacementfx.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

This filter effect uses the pixel values from the image from Mix to spatially displace the image from Input. This is the transformation to be performed:

P'(x,y) <- P(x + Scale * (XC(x,y) - 0.5), y + Scale * (YC(x,y) - 0.5))
diff --git a/docs/xml/modules/classes/display.xml b/docs/xml/modules/classes/display.xml
index bad3da259..5cb502544 100644
--- a/docs/xml/modules/classes/display.xml
+++ b/docs/xml/modules/classes/display.xml
@@ -12,7 +12,7 @@
     ID_DISPLAY
     Graphics
     modules/display.h
-    Paul Manias 2003-2023
+    Paul Manias 2003-2024
     
 

A Display object represents an area of displayable video memory. Although it is a very complex structure, it is fairly simple to initialise. In fact it is possible to initialise a display using an empty structure and accept all the user defaults (which we recommended if possible). For more demanding applications however you may often need to specify a few fields. Before doing so, make sure that you understand how each field operates and what implications setting them may bring. Where possible try to avoid setting field values, as the user default should always be considered as acceptable.

It is perfectly acceptable to initialise multiple display objects and add them to the viewport, but due to memory restrictions, chances of failure could be high when doing this in certain environments. When programming for Parasol, it is recommended that the utilisation of display objects is avoided in favour of using the Surface class. which is much lighter on memory usage.

@@ -100,7 +100,7 @@

The MoveToPoint action moves the display to a new position.

In a hosted environment, the supplied coordinates are treated as being indicative of the absolute position of the host window (not the client area).

-

For full-screen displays, MoveToPoint can alter the screen position for the hardware device managing the display output. This is a rare feature that requires hardware support. ERR_NoSupport is returned if this feature is unavailable.

+

For full-screen displays, MoveToPoint can alter the screen position for the hardware device managing the display output. This is a rare feature that requires hardware support. ERR::NoSupport is returned if this feature is unavailable.

@@ -145,7 +145,7 @@ Minimise Minimise the desktop window hosting the display. - ERROR gfxMinimise(OBJECTPTR Object) + ERR gfxMinimise(OBJECTPTR Object)

If a display is hosted in a desktop window, calling the Minimise method will perform the default minimise action on that window. On a platform such as Microsoft Windows, this would normally result in the window being minimised to the task bar.

Calling Minimise on a display that is already in the minimised state may result in the host window being restored to the desktop. This behaviour is platform dependent and should be manually tested to confirm its reliability on the host platform.

@@ -158,7 +158,7 @@ SetDisplay Changes the current display mode. - ERROR gfxSetDisplay(OBJECTPTR Object, LONG X, LONG Y, LONG Width, LONG Height, LONG InsideWidth, LONG InsideHeight, LONG BitsPerPixel, DOUBLE RefreshRate, LONG Flags) + ERR gfxSetDisplay(OBJECTPTR Object, LONG X, LONG Y, LONG Width, LONG Height, LONG InsideWidth, LONG InsideHeight, LONG BitsPerPixel, DOUBLE RefreshRate, LONG Flags) Horizontal offset of the display, relative to its default position. Vertical offset of the display, relative to its default position. @@ -186,7 +186,7 @@ SetGamma Sets the display gamma levels. - ERROR gfxSetGamma(OBJECTPTR Object, DOUBLE Red, DOUBLE Green, DOUBLE Blue, GMF Flags) + ERR gfxSetGamma(OBJECTPTR Object, DOUBLE Red, DOUBLE Green, DOUBLE Blue, GMF Flags) Gamma correction for the red gun. Gamma correction for the green gun. @@ -208,7 +208,7 @@ SetGammaLinear Sets the display gamma level using a linear algorithm. - ERROR gfxSetGammaLinear(OBJECTPTR Object, DOUBLE Red, DOUBLE Green, DOUBLE Blue, GMF Flags) + ERR gfxSetGammaLinear(OBJECTPTR Object, DOUBLE Red, DOUBLE Green, DOUBLE Blue, GMF Flags) New red gamma value. New green gamma value. @@ -227,7 +227,7 @@ SetMonitor Changes the default monitor settings. - ERROR gfxSetMonitor(OBJECTPTR Object, CSTRING Name, LONG MinH, LONG MaxH, LONG MinV, LONG MaxV, MON Flags) + ERR gfxSetMonitor(OBJECTPTR Object, CSTRING Name, LONG MinH, LONG MaxH, LONG MinV, LONG MaxV, MON Flags) The name of the display. The minimum horizontal scan rate. Usually set to 31. @@ -250,7 +250,7 @@ SizeHints Sets the width and height restrictions for the host window (hosted environments only). - ERROR gfxSizeHints(OBJECTPTR Object, LONG MinWidth, LONG MinHeight, LONG MaxWidth, LONG MaxHeight, LONG EnforceAspect) + ERR gfxSizeHints(OBJECTPTR Object, LONG MinWidth, LONG MinHeight, LONG MaxWidth, LONG MaxHeight, LONG EnforceAspect) The minimum width of the window. The minimum height of the window. @@ -259,7 +259,7 @@ Set to true to enforce an aspect ratio that is scaled by MinHeight / MinWidth. -

If a display is hosted in a desktop window, it may be possible to enforce size restrictions that prevent the window from being shrunk or expanded beyond a certain size. This feature is platform dependent and ERR_NoSupport will be returned if it is not implemented.

+

If a display is hosted in a desktop window, it may be possible to enforce size restrictions that prevent the window from being shrunk or expanded beyond a certain size. This feature is platform dependent and ERR::NoSupport will be returned if it is not implemented.

Operation successful. @@ -270,7 +270,7 @@ UpdatePalette Updates the video display palette to new colour values if in 256 colour mode. - ERROR gfxUpdatePalette(OBJECTPTR Object, struct RGBPalette * NewPalette) + ERR gfxUpdatePalette(OBJECTPTR Object, struct RGBPalette * NewPalette) The new palette to apply to the display bitmap. @@ -287,9 +287,9 @@ WaitVBL Waits for a vertical blank. - ERROR gfxWaitVBL(OBJECTPTR Object) + ERR gfxWaitVBL(OBJECTPTR Object) -

This method waits for the strobe to reach the vertical blank area at the bottom of the display. Not all graphics hardware will support this method. If this is the case, WaitVBL() will return immediately with ERR_NoSupport.

+

This method waits for the strobe to reach the vertical blank area at the bottom of the display. Not all graphics hardware will support this method. If this is the case, WaitVBL() will return immediately with ERR::NoSupport.

Operation successful. @@ -564,7 +564,7 @@ OBJECTID

The PopOver field can be used when a display is hosted as a window. Setting the PopOver field to refer to the object ID of another display will ensure that the host window is always in front of the other display's window (assuming both windows are visible on the desktop).

-

The ERR_NoSupport error code is returned if the host does not support this functionality or if the display owns the output device.

+

The ERR::NoSupport error code is returned if the host does not support this functionality or if the display owns the output device.

diff --git a/docs/xml/modules/classes/document.xml b/docs/xml/modules/classes/document.xml index 18ee02117..6c24ae9bc 100644 --- a/docs/xml/modules/classes/document.xml +++ b/docs/xml/modules/classes/document.xml @@ -7,18 +7,22 @@ class Document Provides document display and editing facilities. - *.rpl|*.ripple|*.rple + *.rpl|*.ripple|*.ripl 1 155c3464 ID_DOCUMENT GUI modules/document.h - Paul Manias © 2005-2023 + Paul Manias © 2005-2024 -

The Document class is a complete Page Layout Engine, providing rich text display features for creating complex documents and manuals.

+

The Document class offers a complete page layout engine, providing rich text display features for creating complex documents and text-based interfaces. Internally, document data is maintained as a serial byte stream and all object model information from the source is discarded. This simplification of the data makes it possible to edit the document in-place, much the same as any word processor. Alternatively it can be used for presentation purposes only, similarly to PDF or HTML formats. Presentation is achieved by building a vector scene graph in conjunction with the Vector module. This means that the output is compatible with SVG and can be manipulated in detail with our existing vector API. Consequently, document formatting is closely integrated with SVG concepts and seamlessly inherits SVG functionality such as filling and stroking commands.

+
Safety
+

The Document class is intended to be safe to use when loading content from an unknown source. Processing will be aborted if a problem is found or the document appears to be unrenderable. It is however, not guaranteed that exploits are impossible. Consideration should also be given to the possibility of exploits that target third party libraries such as libpng and libjpeg for instance.

+

By default, script execution is not enabled when parsing a document source. If support for scripts is enabled, there is no meaningful level of safety on offer when the document is processed. This feature should not be used unless the source document has been written by the client, or has otherwise been received from a trusted source.

+

To mitigate security problems, we recommend that the application is built with some form of sandbox that will stop the system being compromised by bad actors. Utilising a project such as Win32 App Isolation https://github.com/microsoft/win32-app-isolation is one potential way of doing this.

- document_class.cpp - fields.cpp + document_class.cpp + fields.cpp @@ -35,7 +39,7 @@ Clear Clears all content from the object. -

You can delete all of the document information from a document object by calling the Clear action. All of the document data will be deleted from the object and the graphics will be automatically updated as a result of calling this action.

+

Using the Clear() action will delete all of the document's content. The UI will be updated to reflect a clear document.

@@ -48,8 +52,7 @@ DataFeed Document data can be sent and consumed via feeds. -

Appending content to an active document can be achieved via the data feed feature. The Document class currently supports the DATA_DOCUMENT and DATA_XML types for this purpose.

-

The surface that is associated with the Document object will be redrawn as a result of calling this action.

+

Appending content to an active document can be achieved via the data feed feature. The Document class currently supports the DATA::TEXT and DATA::XML types for this purpose.

Operation successful. @@ -61,12 +64,12 @@ Disable - Disables object functionality. + Disables user interactivity. Draw - Draws object graphics to drawable areas. + Force a page layout update (if changes are pending) and redraw to the display. @@ -110,9 +113,9 @@ AddListener Adds a listener to a document trigger for receiving special callbacks. - ERROR docAddListener(OBJECTPTR Object, LONG Trigger, FUNCTION * Function) + ERR docAddListener(OBJECTPTR Object, DRT Trigger, FUNCTION * Function) - The unique identifier for the trigger. + The unique identifier for the trigger. The function to call when the trigger activates. @@ -138,27 +141,10 @@
- - ApplyFontStyle - Applies DocStyle information to a font. - ERROR docApplyFontStyle(OBJECTPTR Object, struct DocStyleV1 * Style, objFont * Font) - - Pointer to a DocStyle structure. - Pointer to a Font object that the style information will be applied to. - - -

This method applies font information from DocStyle structures to new Font objects. The Font object should be uninitialised as it is not possible to apply changes to the font face, style or size after initialisation.

-
- - Operation successful. - Function call missing argument value(s) - -
- CallFunction Executes any registered function in the currently open document. - ERROR docCallFunction(OBJECTPTR Object, CSTRING Function, struct ScriptArg * Args, LONG TotalArgs) + ERR docCallFunction(OBJECTPTR Object, CSTRING Function, struct ScriptArg * Args, LONG TotalArgs) The name of the function that will be called. Pointer to an optional list of arguments to pass to the procedure. @@ -177,7 +163,7 @@ Edit Activates a user editing section within a document. - ERROR docEdit(OBJECTPTR Object, CSTRING Name, LONG Flags) + ERR docEdit(OBJECTPTR Object, CSTRING Name, LONG Flags) The name of the edit cell that will be activated. Optional flags. @@ -196,7 +182,7 @@ FindIndex Searches the document stream for an index, returning the start and end points if found. - ERROR docFindIndex(OBJECTPTR Object, CSTRING Name, LONG * Start, LONG * End) + ERR docFindIndex(OBJECTPTR Object, CSTRING Name, LONG * Start, LONG * End) The name of the index to search for. The byte position of the index is returned in this parameter. @@ -204,7 +190,7 @@

Use the FindIndex method to search for indexes that have been declared in a loaded document. Indexes are declared using the <index/> tag and must be given a unique name. They are useful for marking areas of interest - such as a section of content that may change during run-time viewing, or as place-markers for rapid scrolling to an exact document position.

-

If the named index exists, then the start and end points (as determined by the opening and closing of the index tag) will be returned as byte indexes in the document stream. The starting byte will refer to an ESC_INDEX_START code and the end byte will refer to an ESC_INDEX_END code.

+

If the named index exists, then the start and end points (as determined by the opening and closing of the index tag) will be returned as byte indexes in the document stream. The starting byte will refer to an SCODE::INDEX_START code and the end byte will refer to an SCODE::INDEX_END code.

The index was found and the Start and End parameters reflect its position. @@ -216,7 +202,7 @@ HideIndex Hides the content held within a named index. - ERROR docHideIndex(OBJECTPTR Object, CSTRING Name) + ERR docHideIndex(OBJECTPTR Object, CSTRING Name) The name of the index. @@ -234,10 +220,11 @@ InsertText Inserts new content into a loaded document (raw text format). - ERROR docInsertText(OBJECTPTR Object, CSTRING Text, LONG Index, LONG Preformat) + ERR docInsertText(OBJECTPTR Object, CSTRING Text, LONG Index, LONG Char, LONG Preformat) A UTF-8 text string. - The byte position at which to insert the new content. If -1, the text will be inserted at the end of the document stream. + Reference to a TEXT control code that will receive the content. If -1, the text will be inserted at the end of the document stream. + A character offset within the TEXT control code that will be injected with content. If -1, the text will be injected at the end of the target string. If TRUE, the text will be treated as pre-formatted (all whitespace, including consecutive whitespace will be recognised). @@ -247,6 +234,8 @@ Operation successful. + General failure. + A specified number is outside of the valid range. Function call missing argument value(s) @@ -254,7 +243,7 @@ InsertXML Inserts new content into a loaded document (XML format). - ERROR docInsertXML(OBJECTPTR Object, CSTRING XML, LONG Index) + ERR docInsertXML(OBJECTPTR Object, CSTRING XML, LONG Index) An XML string in RIPL format. The byte position at which to insert the new content. @@ -266,6 +255,9 @@
Operation successful. + No data is available for use. + A specified number is outside of the valid range. + A call to CreateObject() failed. Function call missing argument value(s) @@ -273,15 +265,15 @@ ReadContent Returns selected content from the document, either as plain text or original byte code. - ERROR docReadContent(OBJECTPTR Object, LONG Format, LONG Start, LONG End, STRING * Result) + ERR docReadContent(OBJECTPTR Object, DATA Format, LONG Start, LONG End, STRING * Result) - Set to DATA_TEXT to receive plain-text, or DATA_RAW to receive the original byte-code. + Set to TEXT to receive plain-text, or RAW to receive the original byte-code. An index in the document stream from which data will be extracted. An index in the document stream at which extraction will stop. The data is returned in this parameter as an allocated string. -

The ReadContent method extracts content from the document stream, covering a specific area. It can return the data in its original RIPPLE based format or translate the content into plain-text (control codes are removed).

+

The ReadContent method extracts content from the document stream, covering a specific area. It can return the data as a RIPL binary stream, or translate the content into plain-text (control codes are removed).

If data is extracted in its original format, no post-processing is performed to fix validity errors that may arise from an invalid data range. For instance, if an opening paragraph code is not closed with a matching paragraph end point, this will remain the case in the resulting data.

@@ -296,7 +288,7 @@ RemoveContent Removes content from a loaded document. - ERROR docRemoveContent(OBJECTPTR Object, LONG Start, LONG End) + ERR docRemoveContent(OBJECTPTR Object, LONG Start, LONG End) The byte position at which to start the removal. The byte position at which the removal ends. @@ -315,7 +307,7 @@ RemoveListener Removes a previously configured listener from the document. - ERROR docRemoveListener(OBJECTPTR Object, LONG Trigger, FUNCTION * Function) + ERR docRemoveListener(OBJECTPTR Object, LONG Trigger, FUNCTION * Function) The unique identifier for the trigger. The function that is called when the trigger activates. @@ -332,7 +324,7 @@ SelectLink Selects links in the document. - ERROR docSelectLink(OBJECTPTR Object, LONG Index, CSTRING Name) + ERR docSelectLink(OBJECTPTR Object, LONG Index, CSTRING Name) Index to a link (links are in the order in which they are created in the document, zero being the first link). Ignored if the Name parameter is set. The name of the link to select (set to NULL if an Index is defined). @@ -352,7 +344,7 @@ ShowIndex Shows the content held within a named index. - ERROR docShowIndex(OBJECTPTR Object, CSTRING Name) + ERR docShowIndex(OBJECTPTR Object, CSTRING Name) The name of the index. @@ -373,7 +365,7 @@ Author The author(s) of the document. - Read/Set + Read STRING

If a document declares the names of its author(s) under a head tag, the author string will be readable from this field. This field is always NULL if a document does not declare an author string.

@@ -381,78 +373,26 @@
- Background - Optional background colour for the document. - Read/Write - RGB8 - -

Set the Background field to clear the document background to the colour specified.

-
-
- - - Border - Border colour around the document's surface. - Read/Write - RGB8 - -

This field enables the drawing of a 1-pixel border around the document's surface. The edges that are drawn are controlled by the BorderEdge field.

-
-
- - - BorderEdge - Border edge flags. - Read/Init - INT - -

This field controls the border edge that is drawn around the document's surface. The colour of the border is defined in the Border field.

- -
-
- - - BottomMargin - Defines the amount of whitespace to leave at the bottom of the document page. - Read/Init - INT + ClientScript + Allows an external script object to be used by a document file. + Set + OBJECTPTR -

The BottomMargin value determines the amount of whitespace at the bottom of the page. The default margin can be altered prior to initialisation of a document object, however the loaded content may declare its own margins and overwrite this value during processing.

-

This value can be set as a fixed pixel coordinate only.

+

Set ClientScript with a Script object to allow document content to 'breach the firewall' and access functionality outside of its namespace. This feature is primarily intended for applications that need to interact with their own embedded documents.

+

If a document defines a default script in its content, it will have priority over the one referenced here.

Copyright Copyright information for the document. - Read/Set + Read STRING

If a document declares copyright information under a head tag, the copyright string will be readable from this field. This field is always NULL if a document does not declare a copyright string.

- - CursorColour - The colour used for the document cursor. - Read/Write - RGB8 - -

The colour used for the document cursor may be changed by setting this field. This is relevant only when a document is in edit mode.

-
-
- - - DefaultScript - Allows an external script object to be used by a document file. - Set - OBJECTPTR - -

Setting the DefaultScript field with a reference to a Script object will allow a document file to have access to functionality outside of its namespace. This feature is primarily intended for applications that need to embed custom documents.

-

If a loaded document defines its own custom script, it will have priority over the script referenced here.

-
-
- Description A description of the document, provided by its author. @@ -467,7 +407,7 @@ Error The most recently generated error code. Read - ERROR + ERR

The most recently generated error code is stored in this field.

@@ -480,9 +420,9 @@ FUNCTION

Set this field with a function reference to receive event notifications. It must be set in conjunction with EventMask so that notifications are limited to those of interest.

-

The callback function prototype is ERROR Function(*Document, LARGE EventFlag).

+

The callback function prototype is ERR Function(*Document, DEF EventFlag, KEYVALUE *EventData).

The EventFlag value will indicate the event that occurred. Please see the EventMask field for a list of supported events and additional details.

-

Error codes returned from the callback will normally be discarded, however in some cases ERR_Skip can be returned in order to prevent the event from being processed any further.

+

Error codes returned from the callback will normally be discarded, however in some cases ERR::Skip can be returned in order to prevent the event from being processed any further.

@@ -490,7 +430,7 @@ EventMask Specifies events that need to be reported from the Document object. Read/Write - BIGINT + DEF

To receive event notifications, set EventCallback with a function reference and the EventMask field with a mask that indicates the events that need to be received.

@@ -501,7 +441,7 @@ Flags Optional flags that affect object behaviour. Read/Set - INT + DCF @@ -511,90 +451,22 @@ Focus Refers to the object that will be monitored for user focusing. Read/Init - OBJECTID + *VectorViewport

By default, a document object will become active (i.e. capable of receiving keyboard input) when its surface container receives the focus. If you would like to change this so that a document becomes active when some other object receives the focus, refer to that object by writing its ID to this field.

- - FontColour - Default font colour. - Read/Write - RGB8 - -

This field defines the default font colour if the source document does not specify one.

-
-
- - - FontFace - Defines the default font face. - Read/Set - STRING - -

The default font face to use when processing a document is defined in this field. A document may override the default font face by declaring a body tag containing a face attribute. If this occurs, the FontFace field will reflect the default font face chosen by that document.

-
-
- - - FontSize - The point-size of the default font. - Read/Set - INT - -

The point size of the default font is defined here. Valid values range between 6 and 128.

-
-
- - - Highlight - Defines the colour used to highlight document. - Read/Write - RGB8 - -

The Highlight field determines the colour that is used when highlighting selected document areas.

-
-
- Keywords Includes keywords declared by the source document. - Read/Set + Read STRING

If a document declares keywords under a head tag, the keywords string will be readable from this field. This field is always NULL if a document does not declare any keywords. It is recommended that keywords are separated with spaces or commas. It should not be assumed that the author of the document has adhered to the accepted standard for keyword separation.

- - LeftMargin - Defines the amount of whitespace to leave at the left of the page. - Read/Init - INT - -

The LeftMargin value determines the amount of whitespace at the left of the page. The default margin can be altered prior to initialisation of a document object, however the loaded content may declare its own margins and overwrite this value during processing.

-

This value can be set as a fixed pixel coordinate only.

-
-
- - - LineHeight - Default line height (taken as an average) for all text on the page. - Read - INT - - - - LinkColour - Default font colour for hyperlinks. - Read/Write - RGB8 - -

The default font colour for hyperlinks is defined here. If the alpha component is zero, this feature is disabled.

-
-
- Origin Similar to the Path field, but does not automatically load content if set. @@ -605,6 +477,13 @@
+ + Page + The Page contains the document content and is hosted by the View + Read + *VectorViewport + + PageHeight Measures the page height of the document, in pixels. @@ -631,45 +510,28 @@ Get/Set STRING -

To load a document file into a document object, set the Path field. If this field is set after initialisation, the object will automatically clear its content and reload data from the location that you specify. It is also possible to change the current page and parameters by setting the Path.

-

The string format for setting the path is volume:folder/filename.rpl#Page?param1&param2=value.

-

This example changes the current document by loading from a new file source: documents:index.rpl.

-

This example changes the current page if a document is already loaded (note: if the page does not exist in the currently loaded document, a message is displayed to bring the error to the user's attention): #introduction.

-

This example changes the page and passes it new parameters: #introduction?username=Paul.

+

To load a document file into a document object, set the Path field. Valid string formats for setting the path are:

+

+volume:folder/filename.rpl

+

+#page_name?param1&param2=value

+

+volume:folder/filename.rpl#page_name?param1&param2=value

+

Setting this field post-initialisation will cause a complete reload unless the path begins with a hash to signal a change to the current page and parameters. Note: if a requested page does not exist in the currently loaded document, a dialog is displayed to bring the error to the user's attention).

To leap to a bookmark in the page that has been specified with the <index> element, use the colon as a separator after the pagename, i.e. #pagename:bookmark.

-

Other means of opening a document include loading the data manually and feeding it through with the DataFeed action.

-

The new document layout will be displayed when incoming messages are next processed by the running task.

+

Other means of opening a document include loading the data manually and passing it via the DataFeed action.

- RightMargin - Defines the amount of white-space to leave at the right side of the document page. - Read/Init - INT - -

The RightMargin value determines the amount of white-space at the right of the page. The default margin can be altered prior to initialisation of a document object, however the loaded content may declare its own margins and overwrite this value during processing.

-

This value can be set as a fixed pixel coordinate only.

-
-
- - - SelectColour - Default font colour to use when hyperlinks are selected. - Read/Write - RGB8 - -

This field defines the font colour for hyperlinks that are selected - for instance, when the user tabs to a link or hovers over it. If the alpha component is zero, this field has no effect.

-
-
- - - Surface - Defines the surface area for document graphics. - Read/Set - OBJECTID + Pretext + Execute the XML defined here prior to loading new pages. + Set + STRING -

The Surface field refers to the object ID of the surface that will contain the document graphics. This field must be set prior to initialisation to target the graphics correctly - if left unset then the document object will attempt to determine the correct surface object based on object ownership.

+

Use the Pretext field to execute document code prior to the loading of a new document. This feature is commonly used to set configure a document in advance, such as setting default font values and background graphics. It is functionally equivalent to embedding an + statement at the top of a document, but with the benefit of guaranteeing continued execution if the user navigates away from the first page.

+

A Pretext will always survive document unloading and resets. It can be removed only by setting this field with NULL.

@@ -686,7 +548,7 @@ Title The title of the document. - Read/Set + Read STRING

If a document declares a title under a head tag, the title string will be readable from this field. This field is always NULL if a document does not declare a title.

@@ -694,34 +556,19 @@
- TopMargin - Defines the amount of white-space to leave at the top of the document page. - Read/Init - INT - -

The TopMargin value determines the amount of white-space at the top of the page. The default margin can be altered prior to initialisation of a document object, however the loaded content may declare its own margins and overwrite this value during processing.

-

This value can be set as a fixed pixel coordinate only.

-
-
- - - UpdateLayout - When TRUE, forces the layout to update on the next redraw. - Set - INT - -

To force the document layout to be updated on the next redraw, set this field to TRUE. Redrawing can then be achieved by calling the Draw action on the document.

-

Forcing the document to recompute its layout is rarely necessary as this is automatically managed when inserting and removing content. However, an action such as adjusting the size of graphical objects from a script would require this field to be manually set.

-
+ View + An internally created viewport that hosts the Page + Read + *VectorViewport
- VLinkColour - Default font colour for visited hyperlinks. - Read/Write - RGB8 + Viewport + A client-specific viewport that will host the document graphics. + Read/Set + *VectorViewport -

The default font colour for visited hyperlinks is stored in this field. The source document can specify its own colour for visited links if the author desires.

+

The Viewport field must refer to a VectorViewport that will host the document graphics. If undefined by the client, the nearest viewport container will be determined based on object ownership.

@@ -739,25 +586,37 @@ - - Bottom border edge. - Left border edge. - Right border edge. - Top border edge. + + Audio file data, recognised by the Sound class + Document content (between XML tags) - sent by document objects only + Device activity + File location (the data will reflect the complete file path) + Image file data, recognised by the Image class + Device input that has been transformed into user input + Raw unprocessed data + Receipt for item data, in response to an earlier request + Database record + Make a request for item data + Standard ASCII text + Markup based text data. NOTE - For clipboard data, the top-level encapsulating tag must declare the type of XML, e.g. 'html', 'ripple'. For plain XML, use 'xml' - This read-only flag is set if the object has been disabled through the Disable action. + This read-only flag is set if the UI has been disabled through the Disable action. Allow direct keyboard input and document editing. Turn off debug output produced during document layout and processing - useful on refresh for example. - Do not display scrollbars if the page exceeds the size of the view. System-keys provide standard key support for Ctrl-C, Ctrl-X etc. Set this flag to turn them off. This flag forces overwrite mode when the user enters information through the keyboard. If the flag is not set, then insert mode is used. Turn off all security measures - may only be set prior to initialisation. - The user has interacted with a hyperlink. This event can be cancelled by returning ERR_Skip. + The user has interacted with a hyperlink. This event can be cancelled by returning ERR::Skip. + The user has interacted with an element that has an on-click definition. + Synonym for ON_CROSSING_IN | ON_CROSSING_OUT + The mouse pointer has crossed into an element. + The mouse pointer has crossed out of an element. + The user has triggered a motion event in an element that supports motion monitoring. The source file path has changed. Useful for detecting when the user has left the page. @@ -777,14 +636,5 @@ - - Version of this DocStyle structure - The document object that this style originates from - Pointer to the current font object. Indicates face, style etc, but not simple attributes like colour - Foreground colour (colour of the font) - Underline colour for the font, if active - Font style flags (FSO) - - diff --git a/docs/xml/modules/classes/file.xml b/docs/xml/modules/classes/file.xml index 0819b267c..57d283b2f 100644 --- a/docs/xml/modules/classes/file.xml +++ b/docs/xml/modules/classes/file.xml @@ -12,7 +12,7 @@ ID_FILE System modules/file.h - Paul Manias 1996-2023 + Paul Manias 1996-2024

The File class provides extensive support for file management and I/O. The class supports the notion of individual file compression and file finding capabilities. Since all File objects are tracked, there is no chance of the system leaving locked files behind after a program exits. Folder management is also integrated into this class to ease the management of both file types.

To read or write to a file, set the Path of the file as well as the correct I/O file flags before initialisation. See the Flags field for information on the available I/O flags. Functionality for read and write operations is provided through the Read and Write actions. The Seek action can be used to change the read/write position in a file.

@@ -120,7 +120,7 @@ BufferContent Reads all file content into a local memory buffer. - ERROR flBufferContent(OBJECTPTR Object) + ERR flBufferContent(OBJECTPTR Object)

File content may be buffered at any time by calling the BufferContent method. This will allocate a buffer that matches the current file size and the file's content will be read into that buffer. The BUFFER flag is set in the file object and a pointer to the content is referenced in the file's Buffer field. Standard file operations such as read, write and seek have the same effect when a file is in buffer mode.

Once a file has been buffered, the original file handle and any locks on that file are returned to the system. Physical operations on the file object such as delete, rename and attribute settings no longer have meaning when applied to a buffered file. It is not possible to drop the buffer and return the file object to its original state once buffering has been enabled.

@@ -135,7 +135,7 @@ Copy Copies the data of a file to another location. - ERROR flCopy(OBJECTPTR Object, CSTRING Dest, FUNCTION * Callback) + ERR flCopy(OBJECTPTR Object, CSTRING Dest, FUNCTION * Callback) The destination file path for the copy operation. Optional callback for receiving feedback during the operation. @@ -162,7 +162,7 @@ Delete Deletes a file from its source location. - ERROR flDelete(OBJECTPTR Object, FUNCTION * Callback) + ERR flDelete(OBJECTPTR Object, FUNCTION * Callback) Optional callback for receiving feedback during the operation. @@ -184,7 +184,7 @@ Move Moves a file to a new location. - ERROR flMove(OBJECTPTR Object, CSTRING Dest, FUNCTION * Callback) + ERR flMove(OBJECTPTR Object, CSTRING Dest, FUNCTION * Callback) The desired path for the file. Optional callback for receiving feedback during the operation. @@ -205,7 +205,7 @@ Next Retrieve meta information describing the next indexed file in the folder list. - ERROR flNext(OBJECTPTR Object, objFile ** File) + ERR flNext(OBJECTPTR Object, objFile ** File) A pointer to a new File object will be returned in this parameter if the call is successful. @@ -226,13 +226,13 @@ ReadLine Reads the next line from the file. - ERROR flReadLine(OBJECTPTR Object, STRING * Result) + ERR flReadLine(OBJECTPTR Object, STRING * Result) The resulting string is returned in this parameter.

Reads one line from the file into an internal buffer, which is returned in the Result argument. Reading a line will increase the Position field by the amount of bytes read from the file. You must have set the FL::READ bit in the Flags field when you initialised the file, or the call will fail.

-

The line buffer is managed internally, so there is no need for you to free the result string. This method returns ERR_NoData when it runs out of information to read from the file.

+

The line buffer is managed internally, so there is no need for you to free the result string. This method returns ERR::NoData when it runs out of information to read from the file.

The file information was read into the buffer. @@ -248,7 +248,7 @@ SetDate Sets the date on a file. - ERROR flSetDate(OBJECTPTR Object, LONG Year, LONG Month, LONG Day, LONG Hour, LONG Minute, LONG Second, FDT Type) + ERR flSetDate(OBJECTPTR Object, LONG Year, LONG Month, LONG Day, LONG Hour, LONG Minute, LONG Second, FDT Type) Year (-ve for BC, +ve for AD). Month (1 - 12) @@ -262,7 +262,7 @@

The SetDate method provides a convenient way to set the date and time information for a file object. Date information is set in a human readable year, month, day, hour, minute and second format for your convenience.

Depending on the filesystem type, multiple forms of datestamp may be supported. The default datestamp, FDT_MODIFIED defines the time at which the file data was last altered. Other types include the date on which the file was created and the date it was last archived (backed up). The following types are supported by the Type argument:

-

If the specified datestamp is not supported by the filesystem, ERR_NoSupport is returned by this method.

+

If the specified datestamp is not supported by the filesystem, ERR::NoSupport is returned by this method.

Operation successful. @@ -276,7 +276,7 @@ StartStream Starts streaming data from a file source. - ERROR flStartStream(OBJECTPTR Object, OBJECTID Subscriber, FL Flags, LONG Length) + ERR flStartStream(OBJECTPTR Object, OBJECTID Subscriber, FL Flags, LONG Length) Reference to an object that will receive streamed data notifications. Use READ for incoming data, WRITE for outgoing data. @@ -300,7 +300,7 @@ StopStream Stops streaming data from a file source. - ERROR flStopStream(OBJECTPTR Object) + ERR flStopStream(OBJECTPTR Object)

This method terminates data streaming from a file (instantiated by the StartStream method). Any resources related to the streaming process will be deallocated.

@@ -314,7 +314,7 @@ Watch Monitors files and folders for file system events. - ERROR flWatch(OBJECTPTR Object, FUNCTION * Callback, LARGE Custom, MFF Flags) + ERR flWatch(OBJECTPTR Object, FUNCTION * Callback, LARGE Custom, MFF Flags) The routine that will be called when a file change is triggered by the system. A custom 64-bit value that will passed to the Callback routine as a parameter. @@ -324,9 +324,9 @@

The WatchFile() function configures event based reporting for changes to any file or folder in the file system. The capabilities of this method are dependent on the host platform, with Windows and Linux systems being able to support most of the current feature set.

The path that will be monitored is determined by the File object's Path field. Both files and folders are supported as targets.

The optional MFF Flags are used to filter events to those that are desired for monitoring.

-

The client must provide a Callback that will be triggered when a monitored event is triggered. The Callback must follow the format ERROR Routine(*File, STRING Path, LARGE Custom, LONG Flags)

+

The client must provide a Callback that will be triggered when a monitored event is triggered. The Callback must follow the format ERR Routine(*File, STRING Path, LARGE Custom, LONG Flags)

Each event will be delivered in the sequence that they are originally raised. The Flags parameter will reflect the specific event that has occurred. The Custom parameter is identical to the Custom argument originally passed to this method. The Path is a string that is relative to the File's Path field.

-

If the callback routine returns ERR_Terminate, the watch will be disabled. It is also possible to disable an existing watch by calling this method with no parameters, or by setting the Flags parameter to 0.

+

If the callback routine returns ERR::Terminate, the watch will be disabled. It is also possible to disable an existing watch by calling this method with no parameters, or by setting the Flags parameter to 0.

Operation successful. @@ -388,7 +388,7 @@

The group ID assigned to a file can be read from this field. The ID is retrieved from the file system in real time in case the ID has been changed after initialisation of the file object.

You can also change the group ID of a file by writing an integer value to this field.

-

If the file system does not support group ID's, ERR_NoSupport is returned.

+

If the file system does not support group ID's, ERR::NoSupport is returned.

@@ -516,7 +516,7 @@

The user ID assigned to a file can be read from this field. The ID is retrieved from the file system in real time in case the ID has been changed after initialisation of the file object.

You can also change the user ID of a file by writing an integer value to this field. This can only be done post-initialisation or an error code will be returned.

-

If the filesystem does not support user ID's, ERR_NoSupport is returned.

+

If the filesystem does not support user ID's, ERR::NoSupport is returned.

@@ -607,13 +607,13 @@ - Year - Month 1 to 12 - Day 1 to 31 - Hour 0 to 23 - Minute 0 to 59 - Second 0 to 59 - TimeZone -13 to +13 + Year + Month 1 to 12 + Day 1 to 31 + Hour 0 to 23 + Minute 0 to 59 + Second 0 to 59 + TimeZone -13 to +13 diff --git a/docs/xml/modules/classes/filtereffect.xml b/docs/xml/modules/classes/filtereffect.xml index 48ead01c7..3bdbd7a0b 100644 --- a/docs/xml/modules/classes/filtereffect.xml +++ b/docs/xml/modules/classes/filtereffect.xml @@ -12,7 +12,7 @@ ID_FILTEREFFECT Graphics modules/filtereffect.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

The FilterEffect class provides base-class functionality for effect classes. FilterEffect objects mut not be instantiated directly by the client.

The documented fields and actions here are integral to all effects that utilise this class.

diff --git a/docs/xml/modules/classes/floodfx.xml b/docs/xml/modules/classes/floodfx.xml index f7a3479a3..fc7e38f03 100644 --- a/docs/xml/modules/classes/floodfx.xml +++ b/docs/xml/modules/classes/floodfx.xml @@ -12,7 +12,7 @@ ID_FLOODFX Graphics modules/floodfx.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

The FloodFX class is an output-only effect that fills its target area with a single colour value.

diff --git a/docs/xml/modules/classes/font.xml b/docs/xml/modules/classes/font.xml index d41834111..3ac8ee479 100644 --- a/docs/xml/modules/classes/font.xml +++ b/docs/xml/modules/classes/font.xml @@ -6,7 +6,7 @@ Font class Font - Draws text in different type faces and styles. + Draws bitmap fonts and manages font meta information. *.font|*.fnt|*.tty|*.fon Font 1 @@ -14,22 +14,22 @@ ID_FONT Graphics modules/font.h - Paul Manias © 1998-2023 + Paul Manias © 1998-2024 -

The Font class is provided for the purpose of rendering strings to Bitmap graphics. It supports standard effects such as bold, italic and underlined text, along with extra features such as adjustable spacing, word alignment and outlining. Fixed-point bitmap fonts are supported through the Windows .fon file format and TrueType font files are supported for scaled font rendering.

-

Fonts must be stored in the fonts: directory in order to be recognised and either in the "fixed" or "truetype" sub-directories as appropriate. The process of font installation and file management is managed by functions supplied in the Font module.

+

The Font class is provided for the purpose of bitmap font rendering and querying font meta information. It supports styles such as bold, italic and underlined text, along with extra features such as adjustable spacing and word alignment. Fixed-point bitmap fonts are supported through the Windows .fon file format. Truetype fonts are not supported (refer to the VectorText class for this feature).

+

Bitmap fonts must be stored in the fonts:fixed/ directory in order to be recognised. The process of font installation and file management is managed by functions supplied in the Font module.

The Font class includes full support for the unicode character set through its support for UTF-8. This gives you the added benefit of being able to support international character sets with ease, but you must be careful not to use character codes above #127 without being sure that they follow UTF-8 guidelines. Find out more about UTF-8 at this web page.

-

Initialisation of a new font object can be as simple as declaring its Point size and Face name. Font objects can be difficult to alter post-initialisation, so all style and graphical selections must be defined on creation. For example, it is not possible to change styling from regular to bold format dynamically. To support multiple styles of the same font, you need to create a font object for every style that you need to support. Basic settings such as colour, the font string and text positioning are not affected by these limitations.

+

Initialisation of a new font object can be as simple as declaring its Point size and Face name. Font objects can be difficult to alter post-initialisation, so all style and graphical selections must be defined on creation. For example, it is not possible to change styling from regular to bold format dynamically. To support multiple styles of the same font, create a font object for every style that requires support. Basic settings such as colour, the font string and text positioning are not affected by these limitations.

To draw a font string to a Bitmap object, start by setting the Bitmap and String fields. The X and Y fields determine string positioning and you can also use the Align field to position a string to the right or center of the surface area.

To clarify the terminology used in this documentation, please note the definitions for the following terms:

  • 'Point' determines the size of a font. The value is relative only to other point sizes of the same font face, i.e. two faces at the same point size are not necessarily the same height.
  • 'Height' represents the 'vertical bearing' or point of the font, expressed as a pixel value. The height does not cover for any leading at the top of the font, or the gutter space used for the tails on characters like 'g' and 'y'.
  • -
  • 'Gutter' is the amount of space that a character can descend below the base line. Characters like 'g' and 'y' are examples of characters that utilise the gutter space. The gutter is also sometimes known as the "external leading" of a character.
  • +
  • 'Gutter' is the amount of space that a character can descend below the base line. Characters like 'g' and 'y' are examples of characters that utilise the gutter space. The gutter is also sometimes known as the 'external leading' or 'descent' of a character.
  • 'LineSpacing' is the recommended pixel distance between each line that is printed with the font.
  • 'Glyph' refers to a single font character.
  • -

    Please note that if special effects and transforms are desired then use the VectorText class for this purpose.

    +

    Please note that in the majority of cases the VectorText class should be used for drawing strings because the Font class is not integrated with the display's vector scene graph.

    class_font.cpp @@ -82,16 +82,6 @@ - - Angle - A rotation angle to use when drawing scalable fonts. - Read/Write - DOUBLE - -

    If the Angle field is set to any value other than zero, the font string will be rotated around (0,0) when it is drawn.

    -
    -
    - Ascent The total number of pixels above the baseline. @@ -146,44 +136,20 @@ - - EscapeCallback - The routine defined here will be called when escape characters are encountered. - Read/Write - APTR - -

    Escape characters can be embedded into font strings and a callback routine can be customised to respond to escape characters during the drawing process. By setting the EscapeCallback field to a valid routine, the support for escape characters will be enabled. The EscapeChar field defines the character that will be used to detect escape sequences (the default is 0x1b, the ASCII character set standard).

    -

    The routine defined in the EscapeCallback field must follow this synopsis ERROR EscapeCallback(*Font, STRING String, LONG *Advance, LONG *X, LONG *Y)

    -

    The String parameter refers to the character position just after the escape code was encountered. The string position can optionally be advanced to a new position by setting a value in the Advance parameter before the function returns. The X and Y indicate the next character drawing position and can also be adjusted before the function returns. A result of ERR_Okay will continue the character drawing process. ERR_Terminate will abort the drawing process early. All other error codes will abort the process and the given error code will be returned as the draw action's result.

    -

    During the escape callback routine, legal activities performed on the font object are limited to the following: Adjusting the outline, underline and base colours; adjusting the translucency level. Performing actions not on the list may have a negative impact on the font drawing process.

    -
    -
    - - - EscapeChar - The routine defined here will be called when escape characters are encountered. - Get/Set - STRING - -

    If the EscapeCallback field has been set, EscapeChar will define the character used to detect escape sequences. The default value is 0x1b in the ASCII character set.

    -
    -
    - Face The name of a font face that is to be loaded on initialisation. Read/Set STRING -

    The name of an installed font face must be specified here for initialisation. If this field is not set then the initialisation process will use the user's preferred face. A list of available faces can be obtained from the Font module's GetList function.

    +

    The name of an installed font face must be specified here for initialisation. If this field is undefined then the initialisation process will use the user's preferred face. A list of available faces can be obtained from the GetList function.

    For convenience, the face string can also be extended with extra parameters so that the point size and style are defined at the same time. Extra parameters are delimited with the colon character and must follow a set order defined as face:pointsize:style:colour.

    Here are some examples:

    -
    Open Sans:12:Bold Italic:#ff0000
    +
    Noto Sans:12:Bold Italic:#ff0000
     Courier:10.6
     Charter:120%::255,128,255
     
    -

    To load a font file that is not installed by default, replace the face parameter with the SRC command, followed by the font location: SRC:volumename:data/images/shine:14:Italic

    -

    Multiple font faces can be specified in CSV format, e.g. Sans Serif,Open Sans, which allows the closest matching font to be selected if the first face is unavailable or unable to match the requested point size. This feature can be very useful for pairing bitmap fonts with a scalable equivalent.

    +

    Multiple font faces can be specified in CSV format, e.g. Sans Serif,Noto Sans, which allows the closest matching font to be selected if the first face is unavailable or unable to match the requested point size.

    @@ -207,25 +173,14 @@ Charter:120%::255,128,255 - - FreeTypeFace - Internal field used for exposing FreeType font handles. - Get - APTR - -

    This internal field is intended for use by code published in the standard distribution only. It exposes the handle for a font that has been loaded by the FreeType library (FT_Face).

    -
    -
    - GlyphSpacing - The amount of spacing between each character. + Adjusts the amount of spacing between each character. Read/Write - INT + DOUBLE -

    This field represents the horizontal spacing between each glyph, technically known as kerning between each font character. Fonts that have a high GlyphSpacing value will typically print out like this:

    -
    H e l l o   W o r l d !
    -

    On the other hand, using negative values in this field can cause text to be printed backwards. The GlyphSpacing value is typically set to zero or one by default, depending on the font type that has been loaded.

    +

    This field adjusts the horizontal spacing between each glyph, technically known as kerning between each font character. The value is expressed as a multiplier of the width of each character, and defaults to 1.0.

    +

    Using negative values is valid, and can lead to text being printed backwards.

    @@ -235,19 +190,7 @@ Charter:120%::255,128,255 Read/Init INT -

    This field reflects the 'external leading' value (also known as the 'gutter'), measured in pixels. It applies to fixed fonts only.

    -
    - - - - HDPI - Defines the horizontal dots-per-inch of the target device. - Read/Init - INT - -

    The HDPI defines the horizontal dots-per-inch of the target device. It is commonly set to a custom value when a font needs to target the DPI of a device such as a printer.

    -

    By default the HDPI and VDPI values will reflect the DPI of the primary display.

    -

    In the majority of cases the HDPI and VDPI should share the same value.

    +

    This field reflects the 'external leading' value (also known as the 'gutter'), measured in pixels.

    @@ -348,10 +291,8 @@ Charter:120%::255,128,255 Get/Set DOUBLE -

    The point size of a font defines the size of a font, relative to other point sizes for a particular font face. For example, Arial point 8 is half the size of Arial point 16. The point size between font families cannot be compared accurately due to designer discretion when it comes to determining font size. For accurate point size in terms of pixels, please refer to the Height field.

    -

    The unit of measure for point size is dependent on the target display. For video displays, the point size translates directly into pixels. When printing however, point size will translate to a certain number of dots on the page (the exact number of dots will depend on the printer device and final DPI).

    -

    The Point field also supports proportional sizing based on the default value set by the system or user. For instance if a Point value of 150% is specified and the default font size is 10, the final point size for the font will be 15. This feature is very important in order to support multiple devices at varying DPI's - i.e. mobile devices. You can change the global point size for your application by calling SetDefaultSize in the Font module.

    -

    When setting the point size of a bitmap font, the system will try and find the closest matching value for the requested point size. For instance, if you request a fixed font at point 11 and the closest size is point 8, the system will drop the font to point 8. This does not impact upon scalable fonts, which can be measured to any point size.

    +

    The point size defines the size of a font in point units, at a ratio of 1:72 DPI.

    +

    When setting the point size of a bitmap font, the system will try and find the closest matching value for the requested point size. For instance, if you request a fixed font at point 11 and the closest size is point 8, the system will drop the font to point 8.

    @@ -366,18 +307,6 @@ Charter:120%::255,128,255 - - StrokeSize - The strength of stroked outlines is defined here. - Read/Write - DOUBLE - -

    Set the StrokeSize field to define the strength of the border surrounding an outlined font. The default value is 1.0, which equates to about 1 or 2 pixels at 96 DPI. The value acts as a multiplier, so 3.0 would be triple the default strength.

    -

    This field affects scalable fonts only. Bitmap fonts will always have a stroke size of 1 regardless of the value set here.

    -

    This field does not activate font stroking on its own - the Outline field needs to be set in order for stroking to be activated.

    -
    -
    - Style Determines font styling. @@ -386,7 +315,7 @@ Charter:120%::255,128,255

    The style of a font can be selected by setting the Style field. This comes into effect only if the font actually supports the specified style as part of its graphics set. If the style is unsupported, the regular styling of the face will be used on initialisation.

    Bitmap fonts are a special case if a bold or italic style is selected. In this situation the system can automatically convert the font to that style even if the correct graphics set does not exist.

    -

    Conventional font styles are Bold, Bold Italic, Italic and Regular (the default). TrueType fonts can consist of any style that the designer chooses, such as Narrow or Wide, so use GetList to retrieve available style names.

    +

    Conventional font styles are Bold, Bold Italic, Italic and Regular (the default).

    @@ -396,21 +325,11 @@ Charter:120%::255,128,255 Read/Write INT -

    The TabSize value controls the interval between tabs, measured in characters. If the font is scalable, the character width of 'o' is used for character measurement.

    +

    The TabSize value controls the interval between tabs, measured in characters.

    The default tab size is 8 and the TabSize only comes into effect when tab characters are used in the font String.

    - - TotalChars - Reflects the total number of character glyphs that are available by the font object. - Read - INT - -

    The total number of character glyphs that are available is reflected in this field. The font must have been initialised before the count is known.

    -
    -
    - Underline Enables font underlining when set. @@ -421,25 +340,6 @@ Charter:120%::255,128,255 - - UserData - Optional storage variable for user data; ignored by the Font class. - Read/Write - APTR - - - - VDPI - Defines the vertical dots-per-inch of the target device. - Read/Init - INT - -

    The VDPI defines the vertical dots-per-inch of the target device. It is commonly set to a custom value when a font needs to target the DPI of a device such as a printer.

    -

    By default the HDPI and VDPI values will reflect the DPI of the primary display.

    -

    In the majority of cases the HDPI and VDPI should share the same value.

    -
    -
    - Width Returns the pixel width of a string. @@ -450,18 +350,6 @@ Charter:120%::255,128,255 - - WrapCallback - The routine defined here will be called when the wordwrap boundary is encountered. - Read/Write - FUNCTION * - -

    Customisation of a font's word-wrap behaviour can be achieved by defining a word-wrap callback routine. If word-wrapping has been enabled via the WORDWRAP flag, the WrapCallback routine will be called when the word-wrap boundary is encountered. The routine defined in the WrapCallback field must follow this synopsis: ERROR WrapCallback(*Font, STRING String, LONG *X, LONG *Y).

    -

    The String value reflects the current position within the font string. The X and Y indicate the coordinates at which the wordwrap has occurred. It is assumed that the routine will update the coordinates to reflect the position at which the font should continue drawing. If this is undesirable, returning ERR_NothingDone will cause the the font object to automatically update the coordinates for you. Returning a value of ERR_Terminate will abort the drawing process early. All other error codes will abort the process and the given error code will be returned as the draw action's result.

    -

    During the callback routine, legal activities against the font object are limited to the following: Adjusting the outline, underline and base colours; adjusting the translucency level; adjusting the WrapEdge field. Other types of activity may have a negative impact on the font drawing process.

    -
    -
    - WrapEdge Enables word wrapping at a given boundary. @@ -504,28 +392,20 @@ Charter:120%::255,128,255 - - Process all characters. - Terminate operation at the first line feed or word-wrap. + + The font should not appear in any named list shown to the user. + The Freetype hinter should be used. + The light version of the Freetype hinter should be used. + The hinting information provided by the font should be given preference. + The font is scalable (assume fixed otherwise). + This is a scalable font featuring variable metrics. - Allows switching to a suitable scalable font if a fixed point size is unavailable. Equivalent to ending a font face with the '*' wildcard. - Smooth the edges of scalable fonts. The Font's Y coordinate is the base line. Font is described as having a bold weight (read only). - Clip words by adding dots to the end of the string. Underline the font with a double-sized line, using the colour defined in UnderlineRGB. Font is described as using italics (read only). - The loaded font is embedded with kerning information (read only). - Glyphs are drawn directly to the target bitmap unblended. - A fixed size font (monochrome, no transforms) is preferred to the equivalent scalable font. - A scaled font is preferred over the equivalent fixed size font. - Quick anti-aliasing is useful for games and can be enabled if the background is black. - A fixed size font is required and not a scalable font. - A scaled font is required and not a fixed size font. - This is set if the font is scalable, otherwise assume fixed. - Smooth the edges of scalable fonts. @@ -533,11 +413,14 @@ Charter:120%::255,128,255 Pointer to the next entry in the list. The name of the font face. + Reference to another font Name if this is an alias. Pointer to an array of fixed point sizes supported by the font. Supported styles are listed here in CSV format. + For variable fonts, lists all supported axis codes in CSV format TRUE if the font is scalable. - Do not use. - Do not use. + TRUE if the font has variable metrics. + Hinting options + TRUE if the font should be hidden from user font lists. diff --git a/docs/xml/modules/classes/http.xml b/docs/xml/modules/classes/http.xml index 823a5f2c6..e953783af 100644 --- a/docs/xml/modules/classes/http.xml +++ b/docs/xml/modules/classes/http.xml @@ -12,7 +12,7 @@ ID_HTTP Network modules/http.h - Paul Manias © 2005-2023 + Paul Manias © 2005-2024

    The HTTP class provides a way of interacting with servers that support the HTTP protocol. Supported HTTP methods include GET, POST, PUT, DELETE, COPY, MOVE, MKCOL and more. The following features are included:

    @@ -127,7 +127,7 @@ http.acActivate() Read/Write DOUBLE -

    The timeout for connect operations is specified here. In the event of a timeout, the HTTP object will be deactivated and the Error field will be updated to a value of ERR_TimeOut.

    +

    The timeout for connect operations is specified here. In the event of a timeout, the HTTP object will be deactivated and the Error field will be updated to a value of ERR::TimeOut.

    The timeout value is measured in seconds.

    @@ -172,7 +172,7 @@ http.acActivate() DOUBLE

    A timeout for send and receive operations is required to prevent prolonged waiting during data transfer operations. This is essential when interacting with servers that stream data with indeterminate content lengths. It should be noted that a timeout does not necessarily indicate failure if the content is being streamed from the server (ContentLength is set to -1).

    -

    In the event of a timeout, the HTTP object will be deactivated and the Error field will be updated to a value of ERR_TimeOut.

    +

    In the event of a timeout, the HTTP object will be deactivated and the Error field will be updated to a value of ERR::TimeOut.

    The timeout value is measured in seconds.

    @@ -193,9 +193,9 @@ http.acActivate() Error The error code received for the most recently executed HTTP command. Read/Write - ERROR + ERR -

    On completion of an HTTP request, the most appropriate error code will be stored here. If the request was successful then the value will be zero (ERR_Okay). It should be noted that certain error codes may not necessarily indicate failure - for instance, an ERR_TimeOut error may be received on termination of streamed content. For genuine HTML error codes, see the Status field.

    +

    On completion of an HTTP request, the most appropriate error code will be stored here. If the request was successful then the value will be zero (ERR::Okay). It should be noted that certain error codes may not necessarily indicate failure - for instance, an ERR::TimeOut error may be received on termination of streamed content. For genuine HTML error codes, see the Status field.

    @@ -225,8 +225,8 @@ http.acActivate() Get/Set FUNCTION -

    Data can be received from an HTTP request by setting a callback routine in the Incoming field. The format for the callback routine is ERROR Function(*HTTP, APTR Data, LONG Length).

    -

    If an error code of ERR_Terminate is returned by the callback routine, the currently executing HTTP request will be cancelled.

    +

    Data can be received from an HTTP request by setting a callback routine in the Incoming field. The format for the callback routine is ERR Function(*HTTP, APTR Data, LONG Length).

    +

    If an error code of ERR::Terminate is returned by the callback routine, the currently executing HTTP request will be cancelled.

    @@ -301,9 +301,9 @@ http.acActivate() Get/Set FUNCTION -

    Outgoing data can be managed manually by providing the HTTP object with an outgoing callback routine. The C prototype for the callback routine is ERROR Function(*HTTP, APTR Buffer, LONG BufferSize, LONG *Result). For Fluid use function(HTTP, Buffer, BufferSize).

    +

    Outgoing data can be managed manually by providing the HTTP object with an outgoing callback routine. The C prototype for the callback routine is ERR Function(*HTTP, APTR Buffer, LONG BufferSize, LONG *Result). For Fluid use function(HTTP, Buffer, BufferSize).

    Outgoing content is placed in the Buffer address and must not exceed the indicated BufferSize. The total number of bytes placed in the Buffer must be indicated in the Result parameter before the callback routine returns.

    -

    If an error code of ERR_Terminate is returned by the callback routine, any remaining data will be sent and the transfer will be treated as having completed successfully. Use ERR_TimeOut if data cannot be returned in a reasonable time frame. All other error codes apart from ERR_Okay indicate failure.

    +

    If an error code of ERR::Terminate is returned by the callback routine, any remaining data will be sent and the transfer will be treated as having completed successfully. Use ERR::TimeOut if data cannot be returned in a reasonable time frame. All other error codes apart from ERR::Okay indicate failure.

    @@ -417,8 +417,8 @@ http.acActivate() Get/Set FUNCTION -

    Define a callback routine in StateChanged in order to receive notifications of any change to the #State of an HTTP object. The format for the routine is ERROR Function(*HTTP, HGS State).

    -

    If an error code of ERR_Terminate is returned by the callback routine, the currently executing HTTP request will be cancelled.

    +

    Define a callback routine in StateChanged in order to receive notifications of any change to the #State of an HTTP object. The format for the routine is ERR Function(*HTTP, HGS State).

    +

    If an error code of ERR::Terminate is returned by the callback routine, the currently executing HTTP request will be cancelled.

    @@ -469,7 +469,7 @@ http.acActivate() The client will remain in this state when the server is sending data to the client. The default state - this value will be indicated when no data is being written to the server and the client is waiting for a complete header from the server. During the uploading of data to the server (e.g. POST), the HTTP object will remain in this state. - On successful completion of the send phase, the state changes to SEND_COMPLETE. Successful completion requires either that the number of bytes indicated in ContentLength have been sent, or ERR_Terminate has been returned by the callback functions. + On successful completion of the send phase, the state changes to SEND_COMPLETE. Successful completion requires either that the number of bytes indicated in ContentLength have been sent, or ERR::Terminate has been returned by the callback functions. If an HTTP command failes to complete normally - for instance if the connection is broken before completion - then the state is set to TERMINATED. diff --git a/docs/xml/modules/classes/imagefx.xml b/docs/xml/modules/classes/imagefx.xml index 8a52a8d39..071a2ca14 100644 --- a/docs/xml/modules/classes/imagefx.xml +++ b/docs/xml/modules/classes/imagefx.xml @@ -12,7 +12,7 @@ ID_IMAGEFX Graphics modules/imagefx.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    The ImageFX class will render a source image into a given rectangle within the current user coordinate system. The client has the option of providing a pre-allocated Bitmap or the path to a Picture file as the source.

    If a pre-allocated Bitmap is to be used, it must be created under the ownership of the ImageFX object, and this must be done prior to initialisation. It is required that the bitmap uses 32 bits per pixel and that the alpha channel is enabled.

    diff --git a/docs/xml/modules/classes/lightingfx.xml b/docs/xml/modules/classes/lightingfx.xml index 52ea2367f..9ea399a52 100644 --- a/docs/xml/modules/classes/lightingfx.xml +++ b/docs/xml/modules/classes/lightingfx.xml @@ -12,7 +12,7 @@ ID_LIGHTINGFX Graphics modules/lightingfx.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    The lighting effect class applies a diffuse or specular lighting effect to the alpha channel of an input bitmap, which functions as a bump map. The output is an RGBA representation of the light effect. If no light Colour is specified by the client then the output will be in grey scale.

    For diffuse lighting, the resulting RGBA image is computed as follows:

    @@ -61,7 +61,7 @@ Lr,Lg,Lb = RGB components of light SetDistantLight Configure lighting with a distant light source. - ERROR ltSetDistantLight(OBJECTPTR Object, DOUBLE Azimuth, DOUBLE Elevation) + ERR ltSetDistantLight(OBJECTPTR Object, DOUBLE Azimuth, DOUBLE Elevation) Direction angle for the light source on the XY plane (clockwise), in degrees from the X axis. Direction angle for the light source from the XY plane towards the Z axis, in degrees. A positive value points towards the viewer of the content. @@ -75,7 +75,7 @@ Lr,Lg,Lb = RGB components of light SetPointLight Configure lighting with a pointed light source. - ERROR ltSetPointLight(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z) + ERR ltSetPointLight(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z) X location for the light source. Y location for the light source. @@ -90,7 +90,7 @@ Lr,Lg,Lb = RGB components of light SetSpotLight Configure lighting with a spot light source. - ERROR ltSetSpotLight(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE PX, DOUBLE PY, DOUBLE PZ, DOUBLE Exponent, DOUBLE ConeAngle) + ERR ltSetSpotLight(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE PX, DOUBLE PY, DOUBLE PZ, DOUBLE Exponent, DOUBLE ConeAngle) X location for the light source. Y location for the light source. diff --git a/docs/xml/modules/classes/mergefx.xml b/docs/xml/modules/classes/mergefx.xml index 537ebcdfb..1e2b6fcab 100644 --- a/docs/xml/modules/classes/mergefx.xml +++ b/docs/xml/modules/classes/mergefx.xml @@ -12,7 +12,7 @@ ID_MERGEFX Graphics modules/mergefx.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    Use MergeFX to composite multiple input sources so that they are rendered on top of each other in a predefined sequence.

    Many effects produce a number of intermediate layers in order to create the final output image. This filter allows us to collapse those into a single image. Although this could be done by using n-1 Composite-filters, it is more convenient to have this common operation available in this form, and offers the implementation some additional flexibility.

    diff --git a/docs/xml/modules/classes/metaclass.xml b/docs/xml/modules/classes/metaclass.xml index aa235a0b9..1f05747bb 100644 --- a/docs/xml/modules/classes/metaclass.xml +++ b/docs/xml/modules/classes/metaclass.xml @@ -12,7 +12,7 @@ ID_METACLASS System modules/metaclass.h - Paul Manias 1996-2023 + Paul Manias 1996-2024

    The MetaClass is at the root of the Core's object oriented design and is responsible for managing the construction of new classes. All classes that are created within the system at run-time are represented by a MetaClass object. Each MetaClass object can be inspected to discover detailed information about the class that has been declared. Most of the interesting structural data can be gleaned from the Fields array.

    A number of functions are available in the Core for the purpose of class management. The Core maintains its own list of MetaClass objects, which you can search by calling the FindClass function. The CheckAction function provides a way of checking if a particular pre-defined action is supported by a class.

    @@ -26,7 +26,7 @@ FindField Search a class definition for a specific field. - ERROR mcFindField(OBJECTPTR Object, LONG ID, struct Field ** Field, objMetaClass ** Source) + ERR mcFindField(OBJECTPTR Object, LONG ID, struct Field ** Field, objMetaClass ** Source) The field ID to search for. Field names can be converted to ID's by using the StrHash function. Pointer to the field if discovered, otherwise NULL. @@ -299,9 +299,9 @@ An option to complement the field type. Can be a pointer or an integer value - A virtual function that will retrieve the value for this field. + A virtual function that will retrieve the value for this field. A virtual function that will set the value for this field. - An internal function for writing to this field. + An internal function for writing to this field. The English name for the field, e.g. "Width" Provides a fast way of finding fields, e.g. FID_WIDTH Field offset within the object @@ -312,7 +312,7 @@ The name of the field, e.g. "Width" void GetField(*Object, APTR Result); - ERROR SetField(*Object, APTR Value); + ERR SetField(*Object, APTR Value); Can be a pointer or an integer value Special flags that describe the field diff --git a/docs/xml/modules/classes/module.xml b/docs/xml/modules/classes/module.xml index 76eb56bc6..a5bd31ceb 100644 --- a/docs/xml/modules/classes/module.xml +++ b/docs/xml/modules/classes/module.xml @@ -14,7 +14,7 @@ ID_MODULE System modules/module.h - Paul Manias 1996-2023 + Paul Manias 1996-2024

    The Module class is used to load and maintain the modules that are installed on the user's system. A number of modules are available in the core platform as standard, which you can use in the development of your programs. Examples of existing modules can be found in both the modules: folder.

    To load a module and interact with its API, create a module object and initialise it. The following code segment illustrates in C++:

    @@ -38,13 +38,13 @@ if (modDisplay) modDisplay->getPtr(FID_ModBase, &DisplayBase); ResolveSymbol Resolves the symbol names in loaded link libraries to address pointers. - ERROR modResolveSymbol(OBJECTPTR Object, CSTRING Name, APTR * Address) + ERR modResolveSymbol(OBJECTPTR Object, CSTRING Name, APTR * Address) The name of the symbol to resolve. The address of the symbol will be returned in this parameter. -

    This method will convert symbol names to their respective address pointers. The module code must have been successfully loaded into memory or an ERR_FieldNotSet error will be returned. If the symbol was not found then ERR_NotFound is returned.

    +

    This method will convert symbol names to their respective address pointers. The module code must have been successfully loaded into memory or an ERR::FieldNotSet error will be returned. If the symbol was not found then ERR::NotFound is returned.

    Operation successful. diff --git a/docs/xml/modules/classes/morphologyfx.xml b/docs/xml/modules/classes/morphologyfx.xml index 858f2ce88..96b63136c 100644 --- a/docs/xml/modules/classes/morphologyfx.xml +++ b/docs/xml/modules/classes/morphologyfx.xml @@ -12,7 +12,7 @@ ID_MORPHOLOGYFX Graphics modules/morphologyfx.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    The MorphologyFX class performs "fattening" or "thinning" of artwork. It is particularly useful for fattening or thinning an alpha channel.

    The dilation (or erosion) kernel is a rectangle with a width of 2 * RadiusX and a height of 2 * RadiusY. In dilation, the output pixel is the individual component-wise maximum of the corresponding R,G,B,A values in the input image's kernel rectangle. In erosion, the output pixel is the individual component-wise minimum of the corresponding R,G,B,A values in the input image's kernel rectangle.

    diff --git a/docs/xml/modules/classes/netlookup.xml b/docs/xml/modules/classes/netlookup.xml index be7b23cfb..34c1b5b20 100644 --- a/docs/xml/modules/classes/netlookup.xml +++ b/docs/xml/modules/classes/netlookup.xml @@ -12,7 +12,7 @@ ID_NETLOOKUP Network modules/netlookup.h - Paul Manias © 2005-2023 + Paul Manias © 2005-2024

    Use the NetLookup class for resolving network names to IP addresses and vice versa.

    @@ -35,7 +35,7 @@ BlockingResolveAddress Resolves an IP address to a host name. - ERROR nlBlockingResolveAddress(OBJECTPTR Object, CSTRING Address) + ERR nlBlockingResolveAddress(OBJECTPTR Object, CSTRING Address) IP address to be resolved, e.g. 123.111.94.82. @@ -54,7 +54,7 @@ BlockingResolveName Resolves a domain name to an official host name and a list of IP addresses. - ERROR nlBlockingResolveName(OBJECTPTR Object, CSTRING HostName) + ERR nlBlockingResolveName(OBJECTPTR Object, CSTRING HostName) The host name to be resolved. @@ -73,7 +73,7 @@ ResolveAddress Resolves an IP address to a host name. - ERROR nlResolveAddress(OBJECTPTR Object, CSTRING Address) + ERR nlResolveAddress(OBJECTPTR Object, CSTRING Address) IP address to be resolved, e.g. "123.111.94.82". @@ -92,7 +92,7 @@ ResolveName Resolves a domain name to an official host name and a list of IP addresses. - ERROR nlResolveName(OBJECTPTR Object, CSTRING HostName) + ERR nlResolveName(OBJECTPTR Object, CSTRING HostName) The host name to be resolved. @@ -127,7 +127,7 @@ Get/Set FUNCTION -

    The function referenced here will receive the results of the most recently resolved name or address. The C/C++ prototype is Function(*NetLookup, ERROR Error, const std::string &HostName, const std::vector<IPAddress> &Addresses).

    +

    The function referenced here will receive the results of the most recently resolved name or address. The C/C++ prototype is Function(*NetLookup, ERR Error, const std::string &HostName, const std::vector<IPAddress> &Addresses).

    The Fluid prototype is as follows, with results readable from the HostName and Addresses fields: function(NetLookup, Error).

    diff --git a/docs/xml/modules/classes/netsocket.xml b/docs/xml/modules/classes/netsocket.xml index b906ab3a5..f12cf1169 100644 --- a/docs/xml/modules/classes/netsocket.xml +++ b/docs/xml/modules/classes/netsocket.xml @@ -12,7 +12,7 @@ ID_NETSOCKET Network modules/netsocket.h - Paul Manias © 2005-2023 + Paul Manias © 2005-2024

    The NetSocket class provides a simple way of managing TCP/IP socket communications. Connections from a single client to the server and from the server to multiple clients are supported. SSL functionality is also integrated.

    The design of the NetSocket class caters to asynchronous (non-blocking) communication. This is achieved primarily through callback fields - connection alerts are managed by Feedback, incoming data is received through Incoming and readiness for outgoing data is supported by Outgoing.

    @@ -79,7 +79,7 @@ initially fill the internal write buffer, thereafter it will be called whenever Connect Connects a NetSocket to an address. - ERROR nsConnect(OBJECTPTR Object, CSTRING Address, LONG Port) + ERR nsConnect(OBJECTPTR Object, CSTRING Address, LONG Port) String containing either a domain name (e.g. "www.google.com") or an IP address (e.g. "123.123.123.123") Remote port to connect to. @@ -88,7 +88,7 @@ initially fill the internal write buffer, thereafter it will be called whenever

    This method initiates the connection process with a target IP address. The address to connect to can be specified either as a domain name, in which case the domain name is first resolved to an IP address, or the address can be specified in standard IP notation.

    This method is non-blocking. It will return immediately and the connection will be resolved once the server responds to the connection request or an error occurs. Client code should subscribe to the State field to respond to changes to the connection state.

    Pre-Condition: Must be in a connection state of NTC::DISCONNECTED

    -

    Post-Condition: If this method returns ERR_Okay, will be in state NTC::CONNECTING.

    +

    Post-Condition: If this method returns ERR::Okay, will be in state NTC::CONNECTING.

    The NetSocket connecting process was successfully started. @@ -102,7 +102,7 @@ initially fill the internal write buffer, thereafter it will be called whenever DisconnectClient Disconnects all sockets connected to a specific client IP. - ERROR nsDisconnectClient(OBJECTPTR Object, struct NetClient * Client) + ERR nsDisconnectClient(OBJECTPTR Object, struct NetClient * Client) The client to be disconnected. @@ -119,7 +119,7 @@ initially fill the internal write buffer, thereafter it will be called whenever DisconnectSocket Disconnects a single socket that is connected to a client IP address. - ERROR nsDisconnectSocket(OBJECTPTR Object, objClientSocket * Socket) + ERR nsDisconnectSocket(OBJECTPTR Object, objClientSocket * Socket) The client socket to be disconnected. @@ -135,7 +135,7 @@ initially fill the internal write buffer, thereafter it will be called whenever GetLocalIPAddress Returns the IP address that the socket is locally bound to. - ERROR nsGetLocalIPAddress(OBJECTPTR Object, struct IPAddress * Address) + ERR nsGetLocalIPAddress(OBJECTPTR Object, struct IPAddress * Address) Pointer to an IPAddress structure which will be set to the result of the query if successful. @@ -152,7 +152,7 @@ initially fill the internal write buffer, thereafter it will be called whenever ReadMsg Read a message from the socket. - ERROR nsReadMsg(OBJECTPTR Object, APTR * Message, LONG * Length, LONG * Progress, LONG * CRC) + ERR nsReadMsg(OBJECTPTR Object, APTR * Message, LONG * Length, LONG * Progress, LONG * CRC) A pointer to the message buffer will be placed here if a message has been received. The length of the message is returned here. @@ -177,7 +177,7 @@ initially fill the internal write buffer, thereafter it will be called whenever WriteMsg Writes a message to the socket. - ERROR nsWriteMsg(OBJECTPTR Object, APTR Message, LONG Length) + ERR nsWriteMsg(OBJECTPTR Object, APTR Message, LONG Length) Pointer to the message to send. The length of the message. @@ -234,18 +234,18 @@ initially fill the internal write buffer, thereafter it will be called whenever Error Information about the last error that occurred during a NetSocket operation Read - ERROR + ERR

    This field describes the last error that occurred during a NetSocket operation:

    In the case where a NetSocket object enters the NTC::DISCONNECTED state from the NTC::CONNECTED state, this field can be used to determine how a TCP connection was closed.

    -The connection was closed gracefully. All data sent by the peer has been received. -The connection was broken in a non-graceful fashion. Data may be lost. -The connect operation timed out. -The connection was refused by the remote host. Note: This error will not occur on Windows, and instead the Error field will be set to ERR_Failed. -The network was unreachable. Note: This error will not occur on Windows, and instead the Error field will be set to ERR_Failed. -No path to host was found. Note: This error will not occur on Windows, and instead the Error field will be set to ERR_Failed. -An unspecified error occurred. +The connection was closed gracefully. All data sent by the peer has been received. +The connection was broken in a non-graceful fashion. Data may be lost. +The connect operation timed out. +The connection was refused by the remote host. Note: This error will not occur on Windows, and instead the Error field will be set to ERR::Failed. +The network was unreachable. Note: This error will not occur on Windows, and instead the Error field will be set to ERR::Failed. +No path to host was found. Note: This error will not occur on Windows, and instead the Error field will be set to ERR::Failed. +An unspecified error occurred.
    @@ -278,9 +278,9 @@ initially fill the internal write buffer, thereafter it will be called whenever Get/Set FUNCTION -

    The Incoming field can be set with a custom function that will be called whenever the socket receives data. The function must follow this definition: ERROR Incoming(*NetSocket, OBJECTPTR Context)

    +

    The Incoming field can be set with a custom function that will be called whenever the socket receives data. The function must follow this definition: ERR Incoming(*NetSocket, OBJECTPTR Context)

    The NetSocket parameter refers to the NetSocket object. The Context refers to the object that set the Incoming field.

    -

    Retrieve data from the socket with the Read action. Reading at least some of the data from the socket is compulsory - if the function does not do this then the data will be cleared from the socket when the function returns. If the callback function returns ERR_Terminate then the Incoming field will be cleared and the function will no longer be called. All other error codes are ignored.

    +

    Retrieve data from the socket with the Read action. Reading at least some of the data from the socket is compulsory - if the function does not do this then the data will be cleared from the socket when the function returns. If the callback function returns ERR::Terminate then the Incoming field will be cleared and the function will no longer be called. All other error codes are ignored.

    @@ -308,9 +308,9 @@ initially fill the internal write buffer, thereafter it will be called whenever Get/Set FUNCTION -

    The Outgoing field can be set with a custom function that will be called whenever the socket is ready to send data. The function must be in the format ERROR Outgoing(*NetSocket, OBJECTPTR Context)

    +

    The Outgoing field can be set with a custom function that will be called whenever the socket is ready to send data. The function must be in the format ERR Outgoing(*NetSocket, OBJECTPTR Context)

    The NetSocket parameter refers to the NetSocket object. The Context refers to the object that set the Outgoing field.

    -

    To send data to the NetSocket object, call the Write action. If the callback function returns ERR_Terminate then the Outgoing field will be cleared and the function will no longer be called. All other error codes are ignored.

    +

    To send data to the NetSocket object, call the Write action. If the callback function returns ERR::Terminate then the Outgoing field will be cleared and the function will no longer be called. All other error codes are ignored.

    The Outgoing field is ineffective if the NetSocket is in server mode (target a connected client socket instead).

    @@ -367,7 +367,7 @@ initially fill the internal write buffer, thereafter it will be called whenever INT

    After an encrypted connection has been made to a server, the ValidCert field can be used to determine the validity of the server's certificate.

    -

    If encrypted communication is not supported, ERR_NoSupport is returned. If the certificate is valid or the connection is not encrypted, a value of zero is returned to indicate that the connection is valid.

    +

    If encrypted communication is not supported, ERR::NoSupport is returned. If the certificate is valid or the connection is not encrypted, a value of zero is returned to indicate that the connection is valid.

    diff --git a/docs/xml/modules/classes/offsetfx.xml b/docs/xml/modules/classes/offsetfx.xml index 4ba592319..f586de6a4 100644 --- a/docs/xml/modules/classes/offsetfx.xml +++ b/docs/xml/modules/classes/offsetfx.xml @@ -12,7 +12,7 @@ ID_OFFSETFX Graphics modules/offsetfx.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    This filter offsets the input image relative to its current position in the image space by the specified vector of (XOffset,YOffset).

    diff --git a/docs/xml/modules/classes/picture.xml b/docs/xml/modules/classes/picture.xml index 9e87e6a22..48fd0c858 100644 --- a/docs/xml/modules/classes/picture.xml +++ b/docs/xml/modules/classes/picture.xml @@ -14,13 +14,14 @@ ID_PICTURE Graphics modules/picture.h - Paul Manias © 2001-2023 + Paul Manias © 2001-2024

    The Picture class provides a standard API for programs to load picture files of any supported data type. It is future proof in that future data formats can be supported by installing class drivers on the user's system.

    The default file format for loading and saving pictures is PNG. Other formats such as JPEG are supported via sub-classes, which can be loaded into the system at boot time or on demand. Some rare formats such as TIFF are also supported, but user preference may dictate whether or not the necessary driver is installed.

    Technical Notes
    -

    The Picture class will clip any loaded picture so that it fits the size given in the Bitmap's Width and Height. If you specify the RESIZE flag, the picture will be shrunk or enlarged to fit the given dimensions. If the Width and Height are zero, the picture will be loaded at its default dimensions. To find out general information about a picture before initialising it, Query it first so that the picture object can load initial details on the file format.

    -

    Images are also remapped automatically if the source palette and destination palettes do not match, or if there are significant differences between the source and destination bitmap types.

    +

    To find out general information about a picture before initialising it, Query it first so that the picture object can load initial details on the file format.

    +

    Images are also remapped automatically if the source palette and destination palettes do not match, or if there are significant differences between the source and destination bitmap types.

    +

    Dynamically sized image formats like SVG will use the DisplayWidth and DisplayHeight values to determine the rendered image size.

    picture.cpp @@ -41,8 +42,8 @@ Init Prepares the object for use. -

    Objects that belong to the Picture class can be initialised in two possible ways. If you have not set the Path field or have chosen to use the NEW flag, the initialisation routine will create a Bitmap area that contains no image data. This allows you to fill the picture with your own image data and save it using the SaveImage or SaveToObject actions. You must set the bitmap width, height and colour specifications at a minimum, or the initialisation process will fail.

    -

    If you have set the Path field and avoided the NEW flag, the initialisation process will analyse the file location to determine whether or not the data is in fact a valid image file. If the file does not match up with a registered data format, an error code of ERR_NoSupport is returned. You will need to use the Activate or Query actions to load or find out more information about the image format.

    +

    Objects that belong to the Picture class can be initialised in two possible ways. If you have not set the Path field or have chosen to use the NEW flag, the initialisation routine will create a Bitmap area that contains no image data. This allows you to fill the picture with your own image data and save it using the SaveImage or SaveToObject actions. You must set the bitmap width, height and colour specifications at a minimum, or the initialisation process will fail.

    +

    If you have set the Path field and avoided the NEW flag, the initialisation process will analyse the file location to determine whether or not the data is in fact a valid image file. If the file does not match up with a registered data format, an error code of ERR::NoSupport is returned. You will need to use the Activate or Query actions to load or find out more information about the image format.

    @@ -100,7 +101,7 @@ Read *Bitmap -

    The details of a picture's graphical image and data are defined in its associated bitmap object. It contains information on the image dimensions and palette for example. When loading a picture, you can place certain constraints on the image by presetting Bitmap fields such as the Width and Height (this will have the effect of clipping or resizing the source image). The Palette can also be preset if you want to remap the source image to a specific set of colour values.

    +

    The details of a picture's graphical image and data are defined in its associated bitmap object. It contains information on the image dimensions and palette for example. The Palette can be preset if you want to remap the source image to a specific set of colour values.

    Please refer to the Bitmap class for more details on the structure of bitmap objects.

    @@ -230,9 +231,6 @@ A mask has been generated for the image. Indicates that the picture image will be created from scratch. Automatically upgrade palette based images to 32 bit colour. - Synonym for RESIZE_X | RESIZE_Y - Resizes the image on the horizontal axis if the Bitmap Width is preset and does not match the width of the image source. - Resizes the image on the vertical axis if the Bitmap Height is preset and does not match the height of the image source. This read-only flag is automatically set if the image source is scalable (such as SVG). diff --git a/docs/xml/modules/classes/pointer.xml b/docs/xml/modules/classes/pointer.xml index 03d6bd088..d30196623 100644 --- a/docs/xml/modules/classes/pointer.xml +++ b/docs/xml/modules/classes/pointer.xml @@ -12,7 +12,7 @@ ID_POINTER Graphics modules/pointer.h - Paul Manias 2003-2023 + Paul Manias 2003-2024

    The Pointer class provides the user with a means of interacting with the graphical interface. On a host system such as Windows, the pointer functionality will hook into the host's capabilities. If the display is native then the pointer service will manage its own cursor exclusively.

    Internally, a system-wide pointer object is automatically created with a name of SystemPointer. This should be used for all interactions with this service.

    diff --git a/docs/xml/modules/classes/proxy.xml b/docs/xml/modules/classes/proxy.xml index 71ac44cf7..f9f67d1cc 100644 --- a/docs/xml/modules/classes/proxy.xml +++ b/docs/xml/modules/classes/proxy.xml @@ -12,7 +12,7 @@ ID_PROXY Network modules/proxy.h - Paul Manias © 2005-2023 + Paul Manias © 2005-2024

    The proxy server class provides a global management service for a user's proxy servers. You can alter proxy settings manually or present the user with a dialog box to edit and create new proxies. Scanning functions are also provided with filtering, allowing you to scan for proxies that should be used with the user's network connection.

    Proxy objects are designed to work similarly to database recordsets. Creating a new proxy object will allow you to create a new proxy record if all required fields are set and the object is saved.

    @@ -55,7 +55,7 @@ Delete Removes a proxy from the database. - ERROR prxDelete(OBJECTPTR Object) + ERR prxDelete(OBJECTPTR Object)

    Call the Delete method to remove a proxy from the system. The proxy will be permanently removed from the proxy database on the success of this function.

    @@ -67,7 +67,7 @@ Find Search for a proxy that matches a set of filters. - ERROR prxFind(OBJECTPTR Object, LONG Port, LONG Enabled) + ERR prxFind(OBJECTPTR Object, LONG Port, LONG Enabled) The port number to access. If zero, all proxies will be returned if you perform a looped search. Set to TRUE to return only enabled proxies, FALSE for disabled proxies or -1 for all proxies. @@ -93,9 +93,9 @@ if (proxy.ok()) { FindNext Continues an initiated search. - ERROR prxFindNext(OBJECTPTR Object) + ERR prxFindNext(OBJECTPTR Object) -

    This method continues searches that have been initiated by the Find method. If a proxy is found that matches the filter, ERR_Okay is returned and the details of the proxy object will reflect the data of the discovered record. ERR_NoSearchResult is returned if there are no more matching proxies.

    +

    This method continues searches that have been initiated by the Find method. If a proxy is found that matches the filter, ERR::Okay is returned and the details of the proxy object will reflect the data of the discovered record. ERR::NoSearchResult is returned if there are no more matching proxies.

    A proxy was discovered. @@ -184,7 +184,7 @@ if (proxy.ok()) { INT

    The Record is set to the unique ID of the current proxy record. If no record is indexed then the Record is set to zero.

    -

    If you set the Record manually, the proxy object will attempt to lookup that record. ERR_Okay will be returned if the record is found and all record fields will be updated to reflect the data of that proxy.

    +

    If you set the Record manually, the proxy object will attempt to lookup that record. ERR::Okay will be returned if the record is found and all record fields will be updated to reflect the data of that proxy.

    diff --git a/docs/xml/modules/classes/remapfx.xml b/docs/xml/modules/classes/remapfx.xml index 276077e5f..ad0bd2df0 100644 --- a/docs/xml/modules/classes/remapfx.xml +++ b/docs/xml/modules/classes/remapfx.xml @@ -12,7 +12,7 @@ ID_REMAPFX Graphics modules/remapfx.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    The RemapFX class provides an implementation of the feComponentTransfer functionality in SVG.

    Internally the pixel rendering process is implemented using pixel lookup tables. As such this particular effect carries minimal overhead compared to most other effect classes.

    @@ -33,7 +33,7 @@ SelectDiscrete Apply the discrete function to a pixel component. - ERROR rfSelectDiscrete(OBJECTPTR Object, CMP Component, DOUBLE * Values, LONG Size) + ERR rfSelectDiscrete(OBJECTPTR Object, CMP Component, DOUBLE * Values, LONG Size) The pixel component to which the discrete function must be applied. A list of values for the discrete function. @@ -47,7 +47,7 @@ SelectGamma Apply the gamma function to a pixel component. - ERROR rfSelectGamma(OBJECTPTR Object, CMP Component, DOUBLE Amplitude, DOUBLE Offset, DOUBLE Exponent) + ERR rfSelectGamma(OBJECTPTR Object, CMP Component, DOUBLE Amplitude, DOUBLE Offset, DOUBLE Exponent) The pixel component to which the gamma function must be applied. The amplitude of the gamma function. @@ -62,7 +62,7 @@ SelectIdentity Apply the identity function to a pixel component. - ERROR rfSelectIdentity(OBJECTPTR Object, CMP Component) + ERR rfSelectIdentity(OBJECTPTR Object, CMP Component) The pixel component to which the identity function must be applied. @@ -74,7 +74,7 @@ SelectInvert Apply the invert function to a pixel component. - ERROR rfSelectInvert(OBJECTPTR Object, CMP Component) + ERR rfSelectInvert(OBJECTPTR Object, CMP Component) The pixel component to which the function must be applied. @@ -87,7 +87,7 @@ SelectLinear Apply the linear function to a pixel component. - ERROR rfSelectLinear(OBJECTPTR Object, CMP Component, DOUBLE Slope, DOUBLE Intercept) + ERR rfSelectLinear(OBJECTPTR Object, CMP Component, DOUBLE Slope, DOUBLE Intercept) The pixel component to which the function must be applied. The slope of the linear function. @@ -101,7 +101,7 @@ SelectMask Apply the mask function to a pixel component. - ERROR rfSelectMask(OBJECTPTR Object, CMP Component, LONG Mask) + ERR rfSelectMask(OBJECTPTR Object, CMP Component, LONG Mask) The pixel component to which the function must be applied. The bit mask to be AND'd with each value. @@ -115,7 +115,7 @@ SelectTable Apply the table function to a pixel component. - ERROR rfSelectTable(OBJECTPTR Object, CMP Component, DOUBLE * Values, LONG Size) + ERR rfSelectTable(OBJECTPTR Object, CMP Component, DOUBLE * Values, LONG Size) The pixel component to which the table function must be applied. A list of values for the table function. diff --git a/docs/xml/modules/classes/scintilla.xml b/docs/xml/modules/classes/scintilla.xml index 37a696e89..a220632ba 100644 --- a/docs/xml/modules/classes/scintilla.xml +++ b/docs/xml/modules/classes/scintilla.xml @@ -12,7 +12,7 @@ ID_SCINTILLA Tool modules/scintilla.h - Paul Manias © 2005-2023 + Paul Manias © 2005-2024

    The Scintilla class provides advanced text editing capabilities that are suitable for modifying text files of any kind, as well as simple user input features for text input boxes. The code is based on the Scintilla project at http://scintilla.org and it may be useful to study the official Scintilla documentation for further insight into its capabilities.

    @@ -87,7 +87,7 @@ DeleteLine Deletes a line. - ERROR sciDeleteLine(OBJECTPTR Object, LONG Line) + ERR sciDeleteLine(OBJECTPTR Object, LONG Line) The number of the line to delete. Indexing starts from 0. @@ -99,7 +99,7 @@ GetLine Copies the text content of any line to a user-supplied buffer. - ERROR sciGetLine(OBJECTPTR Object, LONG Line, STRING Buffer, LONG Length) + ERR sciGetLine(OBJECTPTR Object, LONG Line, STRING Buffer, LONG Length) The index of the line to retrieve. The destination buffer. @@ -113,7 +113,7 @@ GetPos Returns the byte position of a given line and column number. - ERROR sciGetPos(OBJECTPTR Object, LONG Line, LONG Column, LONG * Pos) + ERR sciGetPos(OBJECTPTR Object, LONG Line, LONG Column, LONG * Pos) Line index Column index @@ -127,7 +127,7 @@ GotoLine Moves the cursor to any line in the document. - ERROR sciGotoLine(OBJECTPTR Object, LONG Line) + ERR sciGotoLine(OBJECTPTR Object, LONG Line) The line index to move to. @@ -139,7 +139,7 @@ InsertText Inserts text into a document. - ERROR sciInsertText(OBJECTPTR Object, CSTRING String, LONG Pos) + ERR sciInsertText(OBJECTPTR Object, CSTRING String, LONG Pos) A text string to add. -1 inserts at the current cursor position, -2 replaces currently selected text, zero or above inserts at the character index indicated. @@ -153,7 +153,7 @@ ReplaceLine Replaces a line with new text content. - ERROR sciReplaceLine(OBJECTPTR Object, LONG Line, CSTRING String, LONG Length) + ERR sciReplaceLine(OBJECTPTR Object, LONG Line, CSTRING String, LONG Length) Index of the line being targeted. The new string that will replace the line. @@ -167,7 +167,7 @@ ReplaceText Replaces all text within an entire document or limited range. - ERROR sciReplaceText(OBJECTPTR Object, CSTRING Find, CSTRING Replace, STF Flags, LONG Start, LONG End) + ERR sciReplaceText(OBJECTPTR Object, CSTRING Find, CSTRING Replace, STF Flags, LONG Start, LONG End) The keyword string to find. The string that will replace the keyword. @@ -183,7 +183,7 @@ SelectRange Selects a range of text, can also deselect all text. - ERROR sciSelectRange(OBJECTPTR Object, LONG Start, LONG End) + ERR sciSelectRange(OBJECTPTR Object, LONG Start, LONG End) The character at which the selection will start. The character at which the selection will end. If negative, the last character in the document will be targeted. @@ -196,7 +196,7 @@ SetFont Changes the font that is used for text display. - ERROR sciSetFont(OBJECTPTR Object, CSTRING Face) + ERR sciSetFont(OBJECTPTR Object, CSTRING Face) The name of the new font face. @@ -209,7 +209,7 @@ TrimWhitespace Strips trailing white-space from the document. - ERROR sciTrimWhitespace(OBJECTPTR Object) + ERR sciTrimWhitespace(OBJECTPTR Object)

    The TrimWhitespace method will remove trailing white-space from every line in the document. Both tabs and spaces are considered white-space - all other characters shall be treated as content.

    The position of the cursor is reset to the left margin as a result of calling this method.

    @@ -296,7 +296,7 @@ Get/Set FUNCTION -

    Set this field with a reference to a callback function to receive notifications when the user drops a file onto the Scintilla object's surface. The synopsis for the callback function is ERROR Function(*Scintilla, CSTRING Path)

    +

    Set this field with a reference to a callback function to receive notifications when the user drops a file onto the Scintilla object's surface. The synopsis for the callback function is ERR Function(*Scintilla, CSTRING Path)

    If multiple files are dropped, the callback will be repeatedly called until all of the file paths have been reported.

    diff --git a/docs/xml/modules/classes/scintillasearch.xml b/docs/xml/modules/classes/scintillasearch.xml index cb5e9fcd8..d820ca132 100644 --- a/docs/xml/modules/classes/scintillasearch.xml +++ b/docs/xml/modules/classes/scintillasearch.xml @@ -12,7 +12,7 @@ ID_SCINTILLASEARCH Tool modules/scintillasearch.h - Paul Manias © 2005-2023 + Paul Manias © 2005-2024 class_scintilla_search.cxx @@ -22,7 +22,7 @@ Find Searches for a specific text string. - ERROR ssFind(OBJECTPTR Object, LONG * Pos, STF Flags) + ERR ssFind(OBJECTPTR Object, LONG * Pos, STF Flags) The position to start searching from. Set to -1 to start from the cursor position. This parameter is updated with the byte position of the discovered string sequence. Optional flags. @@ -36,19 +36,19 @@ Next Continues a text search. - ERROR ssNext(OBJECTPTR Object, LONG * Pos) + ERR ssNext(OBJECTPTR Object, LONG * Pos) The byte-position of the discovered string sequence is returned here. -

    Use Next to continue a search after calling the Find method. If a string sequence matching that of Text is discovered, its byte position will be returned in the Pos parameter. If a new match is not discovered then ERR_Search is returned to indicate an end to the search.

    +

    Use Next to continue a search after calling the Find method. If a string sequence matching that of Text is discovered, its byte position will be returned in the Pos parameter. If a new match is not discovered then ERR::Search is returned to indicate an end to the search.

    Prev Continues a text search in reverse. - ERROR ssPrev(OBJECTPTR Object, LONG * Pos) + ERR ssPrev(OBJECTPTR Object, LONG * Pos) The byte-position of the discovered string is returned here. diff --git a/docs/xml/modules/classes/script.xml b/docs/xml/modules/classes/script.xml index 5f20228e0..31e35a30c 100644 --- a/docs/xml/modules/classes/script.xml +++ b/docs/xml/modules/classes/script.xml @@ -12,7 +12,7 @@ ID_SCRIPT Data modules/script.h - Paul Manias 1996-2023 + Paul Manias 1996-2024

    The Script class defines a common interface for the purpose of executing scripts, such as Fluid. The base class does not include a default parser or execution process of any kind.

    To execute a script file, choose a sub-class that matches the language and create the script object. Set the Path field and then Activate the script. Global input parameters for the script can be defined via the SetVar action.

    @@ -49,12 +49,12 @@ Callback An internal method for managing callbacks. - ERROR scCallback(OBJECTPTR Object, LARGE ProcedureID, const struct ScriptArg * Args, LONG TotalArgs, LONG * Error) + ERR scCallback(OBJECTPTR Object, LARGE ProcedureID, const struct ScriptArg * Args, LONG TotalArgs, ERR * Error) An identifier for the target procedure. Optional CSV string containing arguments to pass to the procedure. The total number of arguments in the Args parameter. - The error code returned from the script, if any. + The error code returned from the script, if any.

    Private

    @@ -68,7 +68,7 @@ DerefProcedure Dereferences a function. - ERROR scDerefProcedure(OBJECTPTR Object, FUNCTION * Procedure) + ERR scDerefProcedure(OBJECTPTR Object, FUNCTION * Procedure) The function to be dereferenced. @@ -85,7 +85,7 @@ Exec Executes a procedure in the script. - ERROR scExec(OBJECTPTR Object, CSTRING Procedure, const struct ScriptArg * Args, LONG TotalArgs) + ERR scExec(OBJECTPTR Object, CSTRING Procedure, const struct ScriptArg * Args, LONG TotalArgs) The name of the procedure to execute, or NULL for the default entry point. Optional CSV string containing arguments to pass to the procedure (applies to script-based Exec only). @@ -129,7 +129,7 @@ struct ScriptArg { GetProcedureID Converts a procedure name to an ID. - ERROR scGetProcedureID(OBJECTPTR Object, CSTRING Procedure, LARGE * ProcedureID) + ERR scGetProcedureID(OBJECTPTR Object, CSTRING Procedure, LARGE * ProcedureID) The name of the procedure. The computed ID will be returned in this parameter. @@ -176,9 +176,9 @@ SET_FUNCTION_SCRIPT(callback, script, procedure_id); Error If a script fails during execution, an error code may be readable here. Read - ERROR + ERR -

    On execution of a script, the Error value is reset to ERR_Okay and will be updated if the script fails. Be mindful that if a script is likely to be executed recursively then the first thrown error will have priority and be propagated through the call stack.

    +

    On execution of a script, the Error value is reset to ERR::Okay and will be updated if the script fails. Be mindful that if a script is likely to be executed recursively then the first thrown error will have priority and be propagated through the call stack.

    @@ -221,12 +221,12 @@ SET_FUNCTION_SCRIPT(callback, script, procedure_id); Path - The location of the file that is to be processed as a script. + The location of a script file to be loaded. Get/Set STRING -

    Script files can be loaded by a script object by setting the Path field to the path of the source file. The source must be provided prior to the initialisation process or the script object will fail (as an alternative, the Statement field can also be set).

    -

    Special parameters can also be passed to the script when setting the location. The name of an executable procedure may be passed by following the location with a semicolon, then the name of the procedure to execute. Arguments can also be passed to the script by following this with a second semicolon, then a sequence of arguments, each separated with a comma. The following string illustrates the format used:

    +

    A script file can be loaded by setting the Path to its location. The path must be defined prior to the initialisation process, or alternatively the client can define the Statement field.

    +

    Optional parameters can also be passed to the script via the Path string. The name of a function is passed first, surrounded by semicolons. Arguments can be passed to the function by appending them as a CSV list. The following string illustrates the format used:

    dir:location;procedure;arg1=val1,arg2,arg3=val2

    A target for the script may be specified by using the 'target' argument in the parameter list (value must refer to a valid existing object).

    @@ -234,11 +234,11 @@ SET_FUNCTION_SCRIPT(callback, script, procedure_id); Procedure - Allows you to specify a procedure to be executed from within a script. + Specifies a procedure to be executed from within a script. Get/Set STRING -

    Sometimes scripts are split into several procedures or functions that can be executed independently from the 'main' area of the script. If a script that you have loaded contains procedures, you can set the Procedure field to execute a specific routine whenever the script is activated with the Activate action.

    +

    Sometimes scripts are split into several procedures or functions that can be executed independently from the 'main' area of the script. If a loaded script contains procedures, the client can set the Procedure field to execute a specific routine whenever the script is activated with the Activate action.

    If this field is not set, the first procedure in the script, or the 'main' procedure (as defined by the script type) is executed by default.

    @@ -280,7 +280,7 @@ SET_FUNCTION_SCRIPT(callback, script, procedure_id); Get INT -

    The total number of arguments that have been set in a script object through the unlisted field mechanism are reflected in the value of this field. If you have not set any arguments then the field value will be zero.

    +

    The total number of arguments that have been set in a script object through the unlisted field mechanism are reflected in the value of this field.

    @@ -292,7 +292,7 @@ SET_FUNCTION_SCRIPT(callback, script, procedure_id);

    The working path for a script is defined here. By default this is defined as the location from which the script was loaded, without the file name. If this cannot be determined then the working path for the parent process is used (this is usually set to the location of the program).

    The working path is always fully qualified with a slash or colon at the end of the string.

    -

    You can manually change the working path by setting this field with a custom string.

    +

    A client can manually change the working path by setting this field with a custom string.

    diff --git a/docs/xml/modules/classes/sound.xml b/docs/xml/modules/classes/sound.xml index a70459591..6f25818c2 100644 --- a/docs/xml/modules/classes/sound.xml +++ b/docs/xml/modules/classes/sound.xml @@ -14,7 +14,7 @@ ID_SOUND Audio modules/sound.h - Paul Manias © 2002-2023 + Paul Manias © 2002-2024

    The Sound class provides a simple API for programs to load and play audio sample files. By default all loading and saving of sound data is in WAVE format. Other audio formats such as MP3 can be supported through Sound class extensions, if available.

    Automatic streaming is enabled by default. If an attempt is made to play an audio file that exceeds the maximum buffer size, it will be streamed from the source location. Streaming behaviour can be modified via the Stream field.

    diff --git a/docs/xml/modules/classes/sourcefx.xml b/docs/xml/modules/classes/sourcefx.xml index fcda26651..b6652993f 100644 --- a/docs/xml/modules/classes/sourcefx.xml +++ b/docs/xml/modules/classes/sourcefx.xml @@ -12,7 +12,7 @@ ID_SOURCEFX Graphics modules/sourcefx.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    The SourceFX class will render a named vector into a given rectangle within the current user coordinate system.

    Technically the SourceFX object is represented by a new viewport, the bounds of which are defined by attributes X, Y, Width and Height. The placement and scaling of the referenced vector is controlled by the AspectRatio field.

    @@ -56,7 +56,7 @@ Set STRING -

    Setting Def to the name of a pre-registered scene definition will reference that object in Source. If the name is not registered then ERR_Search is returned. The named object must be derived from the Vector class.

    +

    Setting Def to the name of a pre-registered scene definition will reference that object in Source. If the name is not registered then ERR::Search is returned. The named object must be derived from the Vector class.

    Vectors are registered via the VectorScene AddDef() method.

    diff --git a/docs/xml/modules/classes/storagedevice.xml b/docs/xml/modules/classes/storagedevice.xml index 34456ba67..813f3b581 100644 --- a/docs/xml/modules/classes/storagedevice.xml +++ b/docs/xml/modules/classes/storagedevice.xml @@ -12,7 +12,7 @@ ID_STORAGEDEVICE System modules/storagedevice.h - Paul Manias 1996-2023 + Paul Manias 1996-2024

    The StorageDevice class returns the meta data of file system volumes. A reference to an existing volume is required in the Volume field in order to make a successful analysis. If the volume name cannot be resolved, initialisation will fail.

    Following initialisation, all meta fields describing the volume are readable for further information.

    diff --git a/docs/xml/modules/classes/surface.xml b/docs/xml/modules/classes/surface.xml index d9f74e466..77f535b53 100644 --- a/docs/xml/modules/classes/surface.xml +++ b/docs/xml/modules/classes/surface.xml @@ -12,7 +12,7 @@ ID_SURFACE GUI modules/surface.h - Paul Manias 2003-2023 + Paul Manias 2003-2024

    The Surface class is used to manage the positioning, drawing and interaction with layered display interfaces. It works in conjunction with the Bitmap class for rendering graphics, and the Pointer class for user interaction.

    On a platform such as Windows or Linux, the top-level surface will typically be hosted in an application window. On Android or when a full screen display is required, a surface can cover the entire display and be window-less. The top-level surface can act as a host to additional surfaces, which are referred to as children. Placing more surface objects inside of these children will create a hierarchy of many objects that requires sophisticated management that is provisioned by the Surface class.

    @@ -144,12 +144,12 @@ the surface area first). AddCallback Inserts a function hook into the drawing process of a surface object. - ERROR drwAddCallback(OBJECTPTR Object, FUNCTION * Callback) + ERR drwAddCallback(OBJECTPTR Object, FUNCTION * Callback) Pointer to the callback routine or NULL to remove callbacks for the given Object. -

    The AddCallback() method provides a gateway for custom functions to draw directly to a surface. Whenever a surface object performs a redraw event, all functions inserted by this method will be called in their original subscription order with a direct reference to the Surface's target bitmap. The C/C++ prototype is Function(APTR Context, *Surface, *Bitmap).

    +

    The AddCallback() method provides a hook for custom functions to draw directly to a surface. Whenever a surface object performs a redraw event, all functions inserted by this method will be called in their original subscription order with a direct reference to the Surface's target bitmap. The C/C++ prototype is Function(APTR Context, *Surface, *Bitmap, APTR Meta).

    The Fluid prototype is function draw(Surface, Bitmap)

    The subscriber can draw to the bitmap surface as it would with any freshly allocated bitmap object (refer to the Bitmap class). To get the width and height of the available drawing space, please read the Width and Height fields from the Surface object. If writing to the bitmap directly, please observe the bitmap's clipping region and the XOffset and YOffset values.

    @@ -164,7 +164,7 @@ the surface area first). Expose Redraws a surface region to the display, preferably from its graphics buffer. - ERROR drwExpose(OBJECTPTR Object, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags) + ERR drwExpose(OBJECTPTR Object, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags) X coordinate of the expose area. Y coordinate of the expose area. @@ -183,7 +183,7 @@ the surface area first). InvalidateRegion Redraws all of the content in a surface object. - ERROR drwInvalidateRegion(OBJECTPTR Object, LONG X, LONG Y, LONG Width, LONG Height) + ERR drwInvalidateRegion(OBJECTPTR Object, LONG X, LONG Y, LONG Width, LONG Height) X coordinate of the region to invalidate. Y coordinate of the region to invalidate. @@ -204,7 +204,7 @@ the surface area first). Minimise For hosted surfaces only, this method will minimise the surface to an icon. - ERROR drwMinimise(OBJECTPTR Object) + ERR drwMinimise(OBJECTPTR Object)

    If a surface is hosted in a desktop window, calling the Minimise method will perform the default minimise action on that window. On a platform such as Microsoft Windows, this would normally result in the window being minimised to the task bar.

    Calling Minimise on a surface that is already in the minimised state may result in the host window being restored to the desktop. This behaviour is platform dependent and should be manually tested to confirm its reliability on the host platform.

    @@ -214,7 +214,7 @@ the surface area first). RemoveCallback Removes a callback previously inserted by AddCallback(). - ERROR drwRemoveCallback(OBJECTPTR Object, FUNCTION * Callback) + ERR drwRemoveCallback(OBJECTPTR Object, FUNCTION * Callback) Pointer to the callback routine to remove, or NULL to remove all assoicated callback routines. @@ -231,7 +231,7 @@ the surface area first). ResetDimensions Changes the dimensions of a surface. - ERROR drwResetDimensions(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE XOffset, DOUBLE YOffset, DOUBLE Width, DOUBLE Height, LONG Dimensions) + ERR drwResetDimensions(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE XOffset, DOUBLE YOffset, DOUBLE Width, DOUBLE Height, LONG Dimensions) New X coordinate. New Y coordinate. @@ -255,7 +255,7 @@ the surface area first). ScheduleRedraw Schedules a redraw operation for the next frame. - ERROR drwScheduleRedraw(OBJECTPTR Object) + ERR drwScheduleRedraw(OBJECTPTR Object)

    Use ScheduleRedraw to indicate that a surface needs to be drawn to the display. The surface and all child surfaces will be drawn on the next frame cycle (typically 1/60th of a second). All manual draw operations for the target surface are ignored until the scheduled operation is completed.

    Scheduling is ideal in situations where a cluster of redraw events may occur within a tight time period, and it would be inefficient to draw those changes to the display individually.

    @@ -269,7 +269,7 @@ the surface area first). SetDisplay Changes the screen resolution (applies to top-level surface objects only). - ERROR drwSetDisplay(OBJECTPTR Object, LONG X, LONG Y, LONG Width, LONG Height, LONG InsideWidth, LONG InsideHeight, LONG BitsPerPixel, DOUBLE RefreshRate, LONG Flags) + ERR drwSetDisplay(OBJECTPTR Object, LONG X, LONG Y, LONG Width, LONG Height, LONG InsideWidth, LONG InsideHeight, LONG BitsPerPixel, DOUBLE RefreshRate, LONG Flags) The horizontal coordinate/offset for the display. The vertical coordinate/offset for the display. @@ -296,7 +296,7 @@ the surface area first). SetOpacity Alters the opacity of a surface object. - ERROR drwSetOpacity(OBJECTPTR Object, DOUBLE Value, DOUBLE Adjustment) + ERR drwSetOpacity(OBJECTPTR Object, DOUBLE Value, DOUBLE Adjustment) The new opacity value between 0 and 100% (ignored if you have set the Adjustment parameter). Adjustment value to add or subtract from the existing opacity (set to zero if you want to set a fixed Value instead). @@ -428,7 +428,7 @@ the surface area first). INT

    The dimension settings of a surface object can be read from this field. The flags indicate the dimension fields that are in use, and whether the values are fixed or relative.

    -

    It is strongly recommended that this field is never set manually, because the flags are automatically managed for the client when setting fields such as X and Width. If circumstances require manual configuration, take care to ensure that the flags do not conflict. For instance, FIXED_X and RELATIVE_X cannot be paired, nor could FIXED_X, FIXED_XOFFSET and FIXED_WIDTH simultaneously.

    +

    It is strongly recommended that this field is never set manually, because the flags are automatically managed for the client when setting fields such as X and Width. If circumstances require manual configuration, take care to ensure that the flags do not conflict. For instance, FIXED_X and SCALED_X cannot be paired, nor could FIXED_X, FIXED_XOFFSET and FIXED_WIDTH simultaneously.

    @@ -483,7 +483,7 @@ the surface area first). Get/Set INT -

    The height of a surface object is manipulated through this field, although you can also use the Resize() action, which is faster if you need to set both the Width and the Height. A client can set the Height as a fixed value by default, or as a relative value if you set the FD_PERCENT marker. Relative heights are always calculated in relationship to a surface object's container, e.g. if the container is 200 pixels high and surface Height is 80%, then your surface object will be 160 pixels high.

    +

    The height of a surface object is manipulated through this field. Alternatively, use the Resize() action to adjust the Width and Height at the same time. A client can set the Height as a fixed value by default, or as a scaled value in conjunction with the FD_SCALED flag. Scaled values are multiplied by the height of their parent container.

    Setting the Height while a surface object is on display causes an immediate graphical update to reflect the change. Any objects that are within the surface area will be re-drawn and resized as necessary.

    If a value less than zero is passed to an initialised surface, the height will be 'turned off' - this is convenient for pairing the Y and YOffset fields together for dynamic height adjustment.

    @@ -629,7 +629,7 @@ the surface area first).

    Setting the PopOver field to a sibling surface ID will keep the surface in front of its sibling at all times. For dialog windows, it is recommended that the popover and modal options be combined together to prevent interaction with other surfaces created by the current program.

    Setting the PopOver field to zero will return the surface to its normal state.

    -

    If an object that does not belong to the Surface class is detected, an attempt will be made to read that object's Surface field, if available. If this does not yield a valid surface then ERR_InvalidObject is returned.

    +

    If an object that does not belong to the Surface class is detected, an attempt will be made to read that object's Surface field, if available. If this does not yield a valid surface then ERR::InvalidObject is returned.

    @@ -766,9 +766,9 @@ the surface area first). Get/Set INT -

    The width of a surface object is manipulated through this field, although you can also use the Resize() action, which is faster if you need to set both the Width and the Height. A client can set the Width as a fixed value by default, or as a relative value if you set the FD_PERCENT field. Relative widths are always calculated in relationship to a surface object's container, e.g. if the container is 200 pixels wide and surface Width is 80%, then your surface object will be 160 pixels wide.

    +

    The width of a surface object is manipulated through this field. Alternatively, use the Resize() action to adjust the Width and Height at the same time. A client can set the Width as a fixed value by default, or as a scaled value in conjunction with the FD_SCALED flag. Scaled values are multiplied by the width of their parent container.

    Setting the Width while a surface object is on display causes an immediate graphical update to reflect the change. Any objects that are within the surface area will be re-drawn and resized as necessary.

    -

    Width values of 0 or less are illegal, and will result in an ERR_OutOfRange error-code.

    +

    Width values of 0 or less are illegal, and will result in an ERR::OutOfRange error-code.

    @@ -801,7 +801,7 @@ the surface area first). Get/Set INT -

    The horizontal position of a surface object can be set through this field. You have the choice of setting a fixed coordinate (the default) or a relative coordinate if you use the FD_PERCENT flag.

    +

    The horizontal position of a surface object can be set through this field. You have the choice of setting a fixed coordinate (the default) or a scaled coordinate if you use the FD_SCALED flag.

    If you set the X while the surface object is on display, the position of the surface area will be updated immediately.

    @@ -814,7 +814,7 @@ the surface area first).

    The XOffset has a dual purpose depending on whether or not it is set in conjunction with the X or Width fields.

    If set in conjunction with the X field, the width of the surface object will be from that X coordinate up to the width of the container, minus the value given in the XOffset. This means that the width of the surface object is dynamically calculated in relation to the width of its container.

    -

    If the XOffset field is set in conjunction with a fixed or relative width then the surface object will be positioned at an X coordinate calculated from the formula X = ContainerWidth - SurfaceWidth - XOffset.

    +

    If the XOffset field is set in conjunction with a fixed or scaled width then the surface object will be positioned at an X coordinate calculated from the formula X = ContainerWidth - SurfaceWidth - XOffset.

    @@ -824,7 +824,7 @@ the surface area first). Get/Set INT -

    The vertical position of a surface object can be set through this field. You have the choice of setting a fixed coordinate (the default) or a relative coordinate if you use the FD_PERCENT flag.

    +

    The vertical position of a surface object can be set through this field. You have the choice of setting a fixed coordinate (the default) or a scaled coordinate if you use the FD_SCALED flag.

    If the value is changed while the surface is on display, its position will be updated immediately.

    @@ -837,7 +837,7 @@ the surface area first).

    The YOffset has a dual purpose depending on whether or not it is set in conjunction with the Y or Height fields.

    If set in conjunction with the Y field, the height of the surface object will be from that Y coordinate up to the height of the container, minus the value given in the YOffset. This means that the height of the surface object is dynamically calculated in relation to the height of its container.

    -

    If the YOffset field is set in conjunction with a fixed or relative height then the surface object will be positioned at a Y coordinate calculated from the formula "Y = ContainerHeight - SurfaceHeight - YOffset".

    +

    If the YOffset field is set in conjunction with a fixed or scaled height then the surface object will be positioned at a Y coordinate calculated from the formula "Y = ContainerHeight - SurfaceHeight - YOffset".

    diff --git a/docs/xml/modules/classes/svg.xml b/docs/xml/modules/classes/svg.xml index 822c63afe..562490b0f 100644 --- a/docs/xml/modules/classes/svg.xml +++ b/docs/xml/modules/classes/svg.xml @@ -12,10 +12,11 @@ ID_SVG GUI modules/svg.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024 -

    The SVG class provides support for parsing SVG statements into native Vector objects and related definitions. For low-level vector programming, consider using the Vector class directly, or use the SVG class to parse an SVG script and then access the Viewport field to perform transforms and manipulation of the vector group.

    -

    Please refer to the W3C documentation on SVG for a complete reference to the attributes that can be applied to SVG elements. Unfortunately we do not support all SVG capabilities at this time, but support will improve in future.

    +

    The SVG class provides support for parsing SVG statements into a scene graph that consists of Vector objects and related constructs. The generated scene graph is accessible via the Scene and Viewport fields.

    +

    It is possible to parse SVG documents directly to the UI. Set the Target field with a vector to contain the SVG content and it will be structured in the existing scene graph.

    +

    Please refer to the W3C documentation on SVG for a complete reference to the attributes that can be applied to SVG elements.

    class_svg.cpp @@ -26,7 +27,8 @@ Activate Initiates playback of SVG animations. -

    SVG documents that use animation features will remain static until they are activated with this action. The animation code will be processed in the background at the pre-defined FrameRate. The client may hook into the animation cycle by setting the FrameCallback with a suitable function.

    +

    SVG documents that use animation features will remain static until they are activated with this action. The animation code will be processed in the background at the pre-defined FrameRate. The Scene will be redrawn automatically as each frame is processed.

    +

    The client can hook into the animation cycle by setting the FrameCallback with a suitable function.

    @@ -60,10 +62,24 @@ + + ParseSymbol + Generate a vector scene graph from an SVG symbol, targeting a viewport. + ERR svgParseSymbol(OBJECTPTR Object, CSTRING ID, objVectorViewport * Viewport) + + Name of the symbol to parse. + The target viewport. + + +

    ParseSymbol() allows the symbols of a loaded SVG document to be processed post-initialisation. This is useful for utilising symbols in a way that is akin to running macros as required by the program.

    +

    The Name must refer to a symbol that has been declared in the loaded document. A VectorViewport must be provided for the symbol's generated content to target.

    +
    +
    + Render Render the scene to a target Bitamp. - ERROR svgRender(OBJECTPTR Object, objBitmap * Bitmap, LONG X, LONG Y, LONG Width, LONG Height) + ERR svgRender(OBJECTPTR Object, objBitmap * Bitmap, LONG X, LONG Y, LONG Width, LONG Height) The target bitmap. Target X coordinate. @@ -79,6 +95,16 @@
    + + Colour + Defines the default fill to use for 'currentColor' references. + Get/Set + STRING + +

    Set the Colour value to alter the default fill that is used for currentColor references. Typically a standard RGB painter fill reference should be used for this purpose, e.g. rgb(255,255,255). It is however, also acceptable to use URL references to named definitions such as gradients and images. This will work as long as the named definition is registered in the top-level VectorScene object.

    +
    +
    + Flags Optional flags. @@ -124,7 +150,7 @@ Path - The location of the source SVG data. + A path referring to an SVG file. Get/Set STRING @@ -142,15 +168,26 @@ + + Statement + A string containing SVG data. + Read/Set + STRING + +

    SVG data can be loaded from a string by specifying it here prior to initialisation. If the Path field has been defined, it will take precedent and the Statement is ignored.

    +

    Alternatively the DataFeed action can be used to parse data on-the-fly after the SVG object is initialised.

    +
    +
    + Target - The root Viewport that is generated during SVG initialisation can be created as a child of this target object. + The container object for new SVG content can be declared here. Read/Set OBJECTPTR -

    During the initialisation of an SVG object, a VectorViewport will be created that hosts the SVG's vector objects. The target of this VectorViewport can be specified here, conditional on that object residing within a VectorScene, or is a VectorScene itself.

    -

    An attempt will be made to find the new target's parent VectorScene. If none is identified, an error will be returned and no further action is taken.

    -

    If a SVG object is initialised with no Target being defined, a VectorScene will be created automatically and referenced by the Target field.

    +

    During the normal initialisation process, a new VectorViewport is created to host the SVG scene graph. By default, the viewport and its content is strictly owned by the SVG object unless a Target is defined to redirect the scene graph elsewhere.

    +

    The provided Target can be any object class, as long as it forms part of a scene graph owned by a VectorScene object. It is recommended that the chosen target is a VectorViewport.

    +

    The use of a Target will make the generated scene graph independent of the SVG object. Consequently, it is possible to terminate the SVG object without impacting the resources it created.

    diff --git a/docs/xml/modules/classes/task.xml b/docs/xml/modules/classes/task.xml index f97b066ce..61c45e52d 100644 --- a/docs/xml/modules/classes/task.xml +++ b/docs/xml/modules/classes/task.xml @@ -14,10 +14,10 @@ ID_TASK System modules/task.h - Paul Manias 1996-2023 + Paul Manias 1996-2024

    Tasks, also known as processes, form the basis of process execution in an operating system. By creating a task object, it is possible to execute a program from within the host system.

    -

    To execute a compiled program, set the Location field to point to the executable file before initialising the task. Arguments can be passed to the executable by setting the Parameters field. Once the task object is successfully initialised, use the Activate action to run the executable. If the file executes successfully, a new task object is spawned separately to represent the executable (which means it is safe to destroy your task object immediately afterwards). If the Activate action returns with ERR_Okay then the executable program was run successfully.

    +

    To execute a compiled program, set the Location field to point to the executable file before initialising the task. Arguments can be passed to the executable by setting the Parameters field. Once the task object is successfully initialised, use the Activate action to run the executable. If the file executes successfully, a new task object is spawned separately to represent the executable (which means it is safe to destroy your task object immediately afterwards). If the Activate action returns with ERR::Okay then the executable program was run successfully.

    To find the task object that represents the active process, use the CurrentTask function to quickly retrieve it.

    class_task.cpp @@ -68,7 +68,7 @@ AddArgument Adds a new argument to the Parameters field. - ERROR taskAddArgument(OBJECTPTR Object, CSTRING Argument) + ERR taskAddArgument(OBJECTPTR Object, CSTRING Argument) The new argument string. @@ -84,7 +84,7 @@ Expunge Forces a Task to expunge unused code. - ERROR taskExpunge(OBJECTPTR Object) + ERR taskExpunge(OBJECTPTR Object)

    The Expunge method releases all loaded libraries that are no longer in use by the active process.

    @@ -96,13 +96,13 @@ GetEnv Retrieves environment variables for the active process. - ERROR taskGetEnv(OBJECTPTR Object, CSTRING Name, CSTRING * Value) + ERR taskGetEnv(OBJECTPTR Object, CSTRING Name, CSTRING * Value) The name of the environment variable to retrieve. The value of the environment variable is returned in this parameter. -

    On platforms that support environment variables, GetEnv() returns the value of the environment variable matching the Name string. If there is no matching variable, ERR_DoesNotExist is returned.

    +

    On platforms that support environment variables, GetEnv() returns the value of the environment variable matching the Name string. If there is no matching variable, ERR::DoesNotExist is returned.

    In Windows, it is possible to look up registry keys if the string starts with one of the following (in all other cases, the system's environment variables are queried):

    \HKEY_LOCAL_MACHINE\
     \HKEY_CURRENT_USER\
    @@ -123,7 +123,7 @@
         
           Quit
           Sends a quit message to a task.
    -      ERROR taskQuit(OBJECTPTR Object)
    +      ERR taskQuit(OBJECTPTR Object)
           
     

    The Quit method can be used as a convenient way of sending a task a quit message. This will normally result in the destruction of the task, so long as it is still functioning correctly and has been coded to respond to the MSGID_QUIT message type. It is legal for a task to ignore a quit request if it is programmed to stay alive. A task can be killed outright with the Free action.

    @@ -135,7 +135,7 @@ SetEnv Sets environment variables for the active process. - ERROR taskSetEnv(OBJECTPTR Object, CSTRING Name, CSTRING Value) + ERR taskSetEnv(OBJECTPTR Object, CSTRING Name, CSTRING Value) The name of the environment variable to set. The value to assign to the environment variable. @@ -226,9 +226,9 @@ Get/Set FUNCTION -

    The InputCallback field is available for use only when the Task object represents the current process. The referenced function will be called when process receives data from STDIN. The callback must follow the synopsis Function(*Task, APTR Data, LONG Size, ERROR Status)

    +

    The InputCallback field is available for use only when the Task object represents the current process. The referenced function will be called when process receives data from STDIN. The callback must follow the synopsis Function(*Task, APTR Data, LONG Size, ERR Status)

    The information read from STDOUT will be returned in the Data pointer and the byte-length of the data will be indicated by the Size. The data buffer is temporary and will be invalid once the callback function has returned.

    -

    A status of ERR_Finished is sent if the stdinput handle has been closed.

    +

    A status of ERR::Finished is sent if the stdinput handle has been closed.

    @@ -342,7 +342,7 @@ Get/Set INT -

    Once a process has completed execution then its return code can be read from this field. If process is still running, the error code ERR_TaskStillExists will be returned.

    +

    Once a process has completed execution then its return code can be read from this field. If process is still running, the error code ERR::TaskStillExists will be returned.

    diff --git a/docs/xml/modules/classes/thread.xml b/docs/xml/modules/classes/thread.xml index 98177762c..c8498ae35 100644 --- a/docs/xml/modules/classes/thread.xml +++ b/docs/xml/modules/classes/thread.xml @@ -12,12 +12,12 @@ ID_THREAD System modules/thread.h - Paul Manias 1996-2023 + Paul Manias 1996-2024

    The Thread class provides the means to execute and manage threads within an application.

    The following code illustrates how to create a temporary thread that is automatically destroyed after the thread_entry() function has completed:

    -
    static ERROR thread_entry(objThread *Thread) {
    -   return ERR_Okay;
    +
    static ERR thread_entry(objThread *Thread) {
    +   return ERR::Okay;
     }
     
     objThread::create thread = { fl::Routine(thread_entry), fl::Flags(THF::AUTO_FREE) };
    @@ -58,7 +58,7 @@ if (thread.ok()) thread->activate(thread);
         
           SetData
           Attaches data to the thread.
    -      ERROR thSetData(OBJECTPTR Object, APTR Data, LONG Size)
    +      ERR thSetData(OBJECTPTR Object, APTR Data, LONG Size)
           
             Pointer to the data buffer.
             Size of the data buffer.  If zero, the pointer is stored directly, with no copy operation taking place.
    @@ -110,7 +110,7 @@ if (thread.ok()) thread->activate(thread);
           Error
           Reflects the error code returned by the thread routine.
           Read
    -      ERROR
    +      ERR
         
     
         
    @@ -129,7 +129,7 @@ if (thread.ok()) thread->activate(thread);
           Get/Set
           FUNCTION
           
    -

    The routine that will be executed when the thread is activated must be specified here. The function synopsis is ERROR routine(objThread *Thread).

    +

    The routine that will be executed when the thread is activated must be specified here. The function synopsis is ERR routine(objThread *Thread).

    When the routine is called, a reference to the thread object is passed as a parameter. Once the routine has finished processing, the resulting error code will be stored in the thread object's Error field.

    diff --git a/docs/xml/modules/classes/time.xml b/docs/xml/modules/classes/time.xml index f9276018b..979c01819 100644 --- a/docs/xml/modules/classes/time.xml +++ b/docs/xml/modules/classes/time.xml @@ -12,10 +12,9 @@ ID_TIME System modules/time.h - Paul Manias 1996-2023 + Paul Manias 1996-2024 -

    The Time class is available for programs that require time and date recording. In future, support will also be provided for the addition and subtraction of date values.

    -

    Please note that the Time class uses strict metric interpretations of "millisecond" and "microsecond" terminology. That is, a millisecond is 1/1000th (one thousandth) of a second, a microsecond is 1/1000000th (one millionth) of a second.

    +

    The Time class is available for programs that require time and date management in a multi-platform manner.

    To get the current system time, use the Query action.

    class_time.cpp @@ -34,7 +33,7 @@ SetTime Apply the time to the system clock. - ERROR tmSetTime(OBJECTPTR Object) + ERR tmSetTime(OBJECTPTR Object)

    This method will apply the time object's values to the BIOS. Depending on the host platform, this method may only work if the user is logged in as the administrator.

    @@ -66,14 +65,14 @@ MicroSecond - Microsecond (0 - 999999) + A microsecond is one millionth of a second (0 - 999999) Read/Write INT MilliSecond - Millisecond (0 - 999) + A millisecond is one thousandth of a second (0 - 999) Read/Write INT @@ -116,7 +115,7 @@ BIGINT

    The TimeStamp field is a 64-bit integer that represents the time object as an approximation of the number of milliseconds represented in the time object (approximately the total amount of time passed since Zero-AD). This is convenient for summarising a time value for comparison with other time stamps, or for storing time in a 64-bit space.

    -

    The TimeStamp is dynamically calculated when you read this field.

    +

    The TimeStamp value is dynamically calculated when reading this field.

    diff --git a/docs/xml/modules/classes/turbulencefx.xml b/docs/xml/modules/classes/turbulencefx.xml index 52d55e6eb..248f5df65 100644 --- a/docs/xml/modules/classes/turbulencefx.xml +++ b/docs/xml/modules/classes/turbulencefx.xml @@ -12,7 +12,7 @@ ID_TURBULENCEFX Graphics modules/turbulencefx.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    This filter effect creates an image using the Perlin turbulence function. It allows the synthesis of artificial textures like clouds or marble. For a detailed description the of the Perlin turbulence function, see "Texturing and Modeling", Ebert et al, AP Professional, 1994. The resulting image will fill the entire filter primitive subregion for this filter primitive.

    It is possible to create bandwidth-limited noise by synthesizing only one octave.

    diff --git a/docs/xml/modules/classes/vector.xml b/docs/xml/modules/classes/vector.xml index 0279b1fc1..1e8a8b227 100644 --- a/docs/xml/modules/classes/vector.xml +++ b/docs/xml/modules/classes/vector.xml @@ -12,7 +12,7 @@ ID_VECTOR Graphics modules/vector.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    Vector is an abstract class that is used as a blueprint for other vector classes that provide specific functionality for a vector scene. At this time the classes are VectorClip, VectorEllipse, VectorGroup, VectorPath, VectorPolygon, VectorRectangle, VectorSpiral, VectorText, VectorViewport and VectorWave.

    The majority of sub-classes support all of the functionality provided by Vector. The general exception is that graphics functions will not be supported by non-graphical classes, for instance VectorGroup and VectorViewport do not produce a vector path and therefore cannot be rendered.

    @@ -67,7 +67,7 @@ Debug Internal functionality for debugging. - ERROR vecDebug(OBJECTPTR Object) + ERR vecDebug(OBJECTPTR Object)

    This internal method prints comprehensive debugging information to the log.

    @@ -79,7 +79,7 @@ FreeMatrix Remove an allocated VectorMatrix structure. - ERROR vecFreeMatrix(OBJECTPTR Object, struct VectorMatrix * Matrix) + ERR vecFreeMatrix(OBJECTPTR Object, struct VectorMatrix * Matrix) Reference to the structure that requires removal. @@ -95,7 +95,7 @@ GetBoundary Returns the graphical boundary of a vector. - ERROR vecGetBoundary(OBJECTPTR Object, VBF Flags, DOUBLE * X, DOUBLE * Y, DOUBLE * Width, DOUBLE * Height) + ERR vecGetBoundary(OBJECTPTR Object, VBF Flags, DOUBLE * X, DOUBLE * Y, DOUBLE * Width, DOUBLE * Height) Optional flags. The left-most position of the boundary is returned here. @@ -120,7 +120,7 @@ NewMatrix Returns a VectorMatrix structure that allows transformations to be applied to the vector. - ERROR vecNewMatrix(OBJECTPTR Object, struct VectorMatrix ** Transform) + ERR vecNewMatrix(OBJECTPTR Object, struct VectorMatrix ** Transform) A reference to the new transform structure is returned here. @@ -138,7 +138,7 @@ PointInPath Checks if point at (X,Y) is within a vector's path. - ERROR vecPointInPath(OBJECTPTR Object, DOUBLE X, DOUBLE Y) + ERR vecPointInPath(OBJECTPTR Object, DOUBLE X, DOUBLE Y) The X coordinate of the point. The Y coordinate of the point. @@ -158,13 +158,13 @@ Push Push a vector to a new position within its area of the vector stack. - ERROR vecPush(OBJECTPTR Object, LONG Position) + ERR vecPush(OBJECTPTR Object, LONG Position) Specify a relative position index here (-ve to move backwards, +ve to move forwards)

    This method moves the position of a vector within its branch of the vector stack. Repositioning is relative to the current position of the vector. Every unit specified in the Position parameter will move the vector by one index in the stack frame. Negative values will move the vector backwards; positive values move it forward.

    -

    It is not possible for an vector to move outside of its branch, i.e. it cannot change its parent. If the vector reaches the edge of its branch with excess units remaining, the method will return immediately with an ERR_Okay error code.

    +

    It is not possible for an vector to move outside of its branch, i.e. it cannot change its parent. If the vector reaches the edge of its branch with excess units remaining, the method will return immediately with an ERR::Okay error code.

    Operation successful. @@ -175,17 +175,17 @@ SubscribeFeedback Subscribe to events that relate to the vector. - ERROR vecSubscribeFeedback(OBJECTPTR Object, FM Mask, FUNCTION * Callback) + ERR vecSubscribeFeedback(OBJECTPTR Object, FM Mask, FUNCTION * Callback) Defines the feedback events required by the client. Set to 0xffffffff if all messages are required. The function that will receive feedback events.

    Use this method to receive feedback for events that have affected the state of a vector.

    -

    To remove an existing subscription, call this method again with the same Callback and an empty Mask. Alternatively have the callback function return ERR_Terminate.

    +

    To remove an existing subscription, call this method again with the same Callback and an empty Mask. Alternatively have the callback function return ERR::Terminate.

    The synopsis for the Callback is:

    - ERROR callback(*Vector, LONG Event)

    +ERR callback(*Vector, FM Event)

    Operation successful. @@ -196,19 +196,19 @@ SubscribeInput Create a subscription for input events that relate to the vector. - ERROR vecSubscribeInput(OBJECTPTR Object, JTYPE Mask, FUNCTION * Callback) + ERR vecSubscribeInput(OBJECTPTR Object, JTYPE Mask, FUNCTION * Callback) Combine JTYPE flags to define the input messages required by the client. Set to zero to remove an existing subscription. Reference to a function that will receive input messages. -

    The SubscribeInput method filters events from gfxSubscribeInput() by limiting their relevance to that of the target vector. The original events are transferred with some modifications - X, Y, AbsX and AbsY are converted to the vector's coordinate system, and ENTERED_SURFACE and LEFT_SURFACE events are triggered during passage through the clipping area.

    +

    The SubscribeInput method filters events from gfxSubscribeInput() by limiting their relevance to that of the target vector. The original events are transferred with some modifications - X, Y, AbsX and AbsY are converted to the vector's coordinate system, and CROSSED_IN and CROSSED_OUT events are triggered during passage through the clipping area.

    It is a pre-requisite that the associated VectorScene has been linked to a Surface.

    -

    To remove an existing subscription, call this method again with the same Callback and an empty Mask. Alternatively have the function return ERR_Terminate.

    +

    To remove an existing subscription, call this method again with the same Callback and an empty Mask. Alternatively have the function return ERR::Terminate.

    Please refer to gfxSubscribeInput() for further information on event management and message handling.

    The synopsis for the Callback is:

    - ERROR callback(*Vector, *InputEvent)

    +ERR callback(*Vector, *InputEvent)

    Operation successful. @@ -222,7 +222,7 @@ SubscribeKeyboard Create a subscription for input events that relate to the vector. - ERROR vecSubscribeKeyboard(OBJECTPTR Object, FUNCTION * Callback) + ERR vecSubscribeKeyboard(OBJECTPTR Object, FUNCTION * Callback) Reference to a callback function that will receive input messages. @@ -230,12 +230,12 @@

    The SubscribeKeyboard method provides a callback mechanism for handling keyboard events. Events are reported when the vector or one of its children has the user focus. It is a pre-requisite that the associated VectorScene has been linked to a Surface.

    The prototype for the callback is as follows, whereby Qualifers are KQ flags and the Code is a K constant representing the raw key value. The Unicode value is the resulting character when the qualifier and code are translated through the user's keymap.

    - ERROR callback(*Viewport, LONG Qualifiers, LONG Code, LONG Unicode);

    -

    If the callback returns ERR_Terminate then the subscription will be ended. All other error codes are ignored.

    +ERR callback(*Viewport, LONG Qualifiers, LONG Code, LONG Unicode);

    +

    If the callback returns ERR::Terminate then the subscription will be ended. All other error codes are ignored.

    Operation successful. - The VectorScene has no reference to a Surface. + The VectorScene's Surface field has not been defined. A call to AllocMemory() failed to create a new memory block. Function call missing argument value(s) A call to gfxSubscribeInput() failed. @@ -245,14 +245,14 @@ TracePath Returns the coordinates for a vector path, using callbacks. - ERROR vecTracePath(OBJECTPTR Object, FUNCTION * Callback) + ERR vecTracePath(OBJECTPTR Object, FUNCTION * Callback) The function to call with each coordinate of the path. -

    Any vector that generates a path can be traced by calling this method. Tracing allows the caller to follow the path for each pixel that would be drawn if the path were to be rendered with a stroke size of 1. The prototype of the callback function is ERROR Function(OBJECTPTR Vector, LONG Index, LONG Command, DOUBLE X, DOUBLE Y).

    +

    Any vector that generates a path can be traced by calling this method. Tracing allows the caller to follow the path for each pixel that would be drawn if the path were to be rendered with a stroke size of 1. The prototype of the callback function is ERR Function(OBJECTPTR Vector, LONG Index, LONG Command, DOUBLE X, DOUBLE Y, APTR Meta).

    The Vector parameter refers to the vector targeted by the method. The Index is an incrementing counter that reflects the currently plotted point. The X and Y parameters reflect the coordinate of a point on the path.

    -

    If the Callback returns ERR_Terminate, then no further coordinates will be processed.

    +

    If the Callback returns ERR::Terminate, then no further coordinates will be processed.

    Operation successful. @@ -344,7 +344,8 @@ Get/Set STRING -

    The painter used for filling a vector path can be defined through this field. The string is parsed through the ReadPainter function in the Vector module. Please refer to it for further details on valid formatting.

    +

    The painter used for filling a vector path can be defined through this field using SVG compatible formatting. The string is parsed through the ReadPainter function in the Vector module. Please refer to it for further details on valid formatting.

    +

    It is possible to enable dual-fill painting via this field, whereby a second fill operation can follow the first by separating them with a semi-colon ; character. This feature makes it easy to use a common background fill and follow it with an independent foreground, alleviating the need for additional vector objects. Be aware that this feature is intended for programmed use-cases and is not SVG compliant.

    @@ -567,10 +568,10 @@ FUNCTION

    Use ResizeEvent to receive feedback when the viewport that hosts the vector is resized. The function prototype is as follows:

    -
    void callback(*VectorViewport, *Vector, DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height)
    +
    void callback(*VectorViewport, *Vector, DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height, APTR Meta)
     

    The dimension values refer to the current location and size of the viewport.

    -

    Note that this callback feature is provided for convenience, and only one subscription to the viewport is possible at any time. The conventional means for monitoring the size and position of any vector is to subscribe to the PATH_CHANGED event.

    +

    Note that this callback feature is provided for convenience. Only one subscription to the viewport is possible at any time. The conventional means for monitoring the size and position of any vector is to subscribe to the PATH_CHANGED event.

    @@ -645,7 +646,7 @@ Z: Close Path Get/Set DOUBLE -

    The StrokeWidth defines the pixel width of a path when it is stroked. The path will not be stroked if the value is zero. A percentage can be used to define the stroke width if it should be relative to the size of the viewbox (along its diagonal). Note that this incurs a slight computational penalty when drawing.

    +

    The StrokeWidth defines the pixel width of a path when it is stroked. The path will not be stroked if the value is zero. A percentage can be used to define the stroke width if it should be scaled to the size of the viewbox (along its diagonal). Note that this incurs a slight computational penalty when drawing.

    The size of the stroke is also affected by scaling factors imposed by transforms and viewports.

    diff --git a/docs/xml/modules/classes/vectorclip.xml b/docs/xml/modules/classes/vectorclip.xml index 6dd6eff35..874081f73 100644 --- a/docs/xml/modules/classes/vectorclip.xml +++ b/docs/xml/modules/classes/vectorclip.xml @@ -12,11 +12,13 @@ ID_VECTORCLIP Graphics modules/vectorclip.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024 -

    The VectorClip defines a clipping path that can be used by other vectors as a mask. The clipping path is defined by creating Vector shapes that are initialised to the VectorClip as child objects.

    -

    Any Vector that defines a path can utilise a VectorClip by referencing it through the Vector's Mask field.

    -

    VectorClip objects must always be owned by their relevant VectorScene or VectorViewport. It is valid for a VectorClip to be shared by multiple vector objects within the same scene.

    +

    The VectorClip defines a clipping path that can be used by other vectors as a mask. The clipping path is defined by creating Vector shapes that are initialised to the VectorClip's Viewport as child objects.

    +

    Vector shapes can utilise a VectorClip by referring to it via the Vector's Vector:Mask field.

    +

    VectorClip objects must be owned by a VectorScene. It is valid for a VectorClip to be shared amongst multiple vector objects within the same scene. If optimum drawing efficiency is required, we recommend that each VectorClip is referenced by one vector only. This will reduce the frequency of path recomputation and redrawing of the clipping path.

    +

    The SVG standard makes a distinction between clipping paths and masks. Consequently, this distinction also exists in the VectorClip design, and by default VectorClip objects will operate in path clipping mode. This means that the clipping path is constructed as a solid filled area, and stroke instructions are completely ignored. To create more complex masks, such as one with a filled gradient, use the VCLF::APPLY_FILLS option in Flags. If stroking operations are required, define VCLF::APPLY_STROKES.

    +

    Finally, for the purposes of UI development it may often be beneficial to set Units to VUNIT::BOUNDING_BOX so that the clipping path is sized to match the target vector. A viewbox size of 0 0 1 1 is applied by default, but if a 1:1 match to the target vector is preferred, set the Viewport VectorViewport:ViewWidth and VectorViewport:ViewHeight to match the target vector's dimensions.

    clip.cpp @@ -24,12 +26,12 @@ - Transform - Applies a transform to the paths in the clipping mask. - Set - STRING + Flags + Optional flags. + Get/Set + VCLF -

    A transform can be applied to the paths in the clipping mask by setting this field with an SVG compliant transform string.

    +
    @@ -37,13 +39,37 @@ Units Defines the coordinate system for fields X, Y, Width and Height. Get/Set - INT + VUNIT + +

    The default coordinate system for clip-paths is BOUNDING_BOX, which positions the clipping region relative to the vector that references it. The alternative is USERSPACE, which positions the path relative to the vector's parent viewport.

    + +
    + + + + Viewport + This viewport hosts the Vector objects that will contribute to the clip path. + Get + *VectorViewport -

    The default coordinate system for clip-paths is BOUNDING_BOX, which positions the clipping region against the vector that references it. The alternative is USERSPACE, which positions the path relative to the current viewport.

    +

    To define the path(s) that will be used to build the clipping mask, add at least one Vector object to the viewport declared here.

    + + + Apply fill instructions when drawing the clipping path(s). + Apply stroke instructions when drawing the clipping path(s). + + + + Coordinates are scaled to the object's bounding box. + + Coordinates are scaled to the current viewport. + + + diff --git a/docs/xml/modules/classes/vectorcolour.xml b/docs/xml/modules/classes/vectorcolour.xml index 486c10f42..0bb2e9b40 100644 --- a/docs/xml/modules/classes/vectorcolour.xml +++ b/docs/xml/modules/classes/vectorcolour.xml @@ -12,7 +12,7 @@ ID_VECTORCOLOUR Graphics modules/vectorcolour.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    VectorColour is a stub class for exclusive use with the Vector module's DrawPath() function, for use in either the StrokeStyle or FillStyle parameters. VectorColour allows the path to be drawn with a solid colour, as specified in the Red, Green, Blue and Alpha fields.

    diff --git a/docs/xml/modules/classes/vectorellipse.xml b/docs/xml/modules/classes/vectorellipse.xml index d8fa72d0c..f9f965fe8 100644 --- a/docs/xml/modules/classes/vectorellipse.xml +++ b/docs/xml/modules/classes/vectorellipse.xml @@ -12,7 +12,7 @@ ID_VECTORELLIPSE Graphics modules/vectorellipse.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    The VectorEllipse class provides the necessary functionality for elliptical path generation.

    @@ -23,21 +23,21 @@ CenterX - The horizontal center of the ellipse. Expressed as a fixed or relative coordinate. + The horizontal center of the ellipse. Expressed as a fixed or scaled coordinate. Get/Set DOUBLE -

    The horizontal center of the ellipse is defined here as either a fixed or relative value.

    +

    The horizontal center of the ellipse is defined here as either a fixed or scaled value.

    CenterY - The vertical center of the ellipse. Expressed as a fixed or relative coordinate. + The vertical center of the ellipse. Expressed as a fixed or scaled coordinate. Get/Set DOUBLE -

    The vertical center of the ellipse is defined here as either a fixed or relative value.

    +

    The vertical center of the ellipse is defined here as either a fixed or scaled value.

    @@ -53,10 +53,10 @@ The RadiusY value is a fixed coordinate. The CenterX value is a fixed coordinate. The CenterY value is a fixed coordinate. -The RadiusX value is a relative coordinate. -The RadiusY value is a relative coordinate. -The CenterX value is a relative coordinate. -The CenterY value is a relative coordinate. +The RadiusX value is a scaled coordinate. +The RadiusY value is a scaled coordinate. +The CenterX value is a scaled coordinate. +The CenterY value is a scaled coordinate. @@ -73,11 +73,11 @@ Radius - The radius of the ellipse. Expressed as a fixed or relative coordinate. + The radius of the ellipse. Expressed as a fixed or scaled coordinate. Get/Set DOUBLE -

    The radius of the ellipse is defined here as either a fixed or relative value. Updating the radius will set both the RadiusX and RadiusY values simultaneously.

    +

    The radius of the ellipse is defined here as either a fixed or scaled value. Updating the radius will set both the RadiusX and RadiusY values simultaneously.

    @@ -87,7 +87,7 @@ Get/Set DOUBLE -

    The horizontal radius of the ellipse is defined here as either a fixed or relative value.

    +

    The horizontal radius of the ellipse is defined here as either a fixed or scaled value.

    @@ -97,7 +97,7 @@ Get/Set DOUBLE -

    The vertical radius of the ellipse is defined here as either a fixed or relative value.

    +

    The vertical radius of the ellipse is defined here as either a fixed or scaled value.

    diff --git a/docs/xml/modules/classes/vectorfilter.xml b/docs/xml/modules/classes/vectorfilter.xml index a9ffb1076..09d32b026 100644 --- a/docs/xml/modules/classes/vectorfilter.xml +++ b/docs/xml/modules/classes/vectorfilter.xml @@ -12,7 +12,7 @@ ID_VECTORFILTER Graphics modules/vectorfilter.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    The VectorFilter class allows post-effect filters to be applied to vectors as they are being rendered. Filter support is closely modelled around the SVG standard, and effect results are intended to match that of the standard. Once created, a filter can be utilised by vector objects through their Filter field. By way of example in SVG:

    <circle cx="160" cy="50" r="40" fill="#f00" filter="url(#EffectPipeline)"/>
    @@ -34,6 +34,16 @@
       
     
       
    +    
    +      AspectRatio
    +      Aspect ratio to use when scaling X/Y values
    +      Read/Write
    +      VFA
    +      
    +
    +      
    +    
    +
         
           ColourSpace
           The colour space of the filter graphics (SRGB or linear RGB).
    @@ -48,7 +58,7 @@
     
         
           Dimensions
    -      Dimension flags define whether individual dimension fields contain fixed or relative values.
    +      Dimension flags define whether individual dimension fields contain fixed or scaled values.
           Read
           INT
           
    @@ -56,12 +66,12 @@
     
     The X value is a fixed coordinate.
     The Y value is a fixed coordinate.
    -The X value is a relative coordinate.
    -The Y value is a relative coordinate.
    +The X value is a scaled coordinate.
    +The Y value is a scaled coordinate.
     The Width value is a fixed coordinate.
     The Height value is a fixed coordinate.
    -The Width value is a relative coordinate.
    -The Height value is a relative coordinate.
    +The Width value is a scaled coordinate.
    +The Height value is a scaled coordinate.
     
           
         
    @@ -78,11 +88,11 @@
     
         
           Height
    -      The height of the filter area.  Can be expressed as a fixed or relative coordinate.
    +      The height of the filter area.  Can be expressed as a fixed or scaled coordinate.
           Get/Set
           DOUBLE
           
    -

    The height of the filter area is expressed here as a fixed or relative coordinate. The width and height effectively restrain the working space for the effect processing, making them an important consideration for efficiency.

    +

    The height of the filter area is expressed here as a fixed or scaled coordinate. The width and height effectively restrain the working space for the effect processing, making them an important consideration for efficiency.

    The coordinate system for the width and height depends on the value for Units.

    If width or height is not specified, the effect is as if a value of 120% were specified.

    @@ -114,7 +124,7 @@ Read/Write VUNIT -

    PrimitiveUnits alters the behaviour of some effects when their dimensions are calculated. The default value is USERSPACE. When set to BOUNDING_BOX, the effect may calculate its dimensions strictly based on the client vector using a relative coordinate space of (0,0,100%,100%).

    +

    PrimitiveUnits alters the behaviour of some effects when their dimensions are calculated. The default value is USERSPACE. When set to BOUNDING_BOX, the effect may calculate its dimensions strictly based on the client vector using a scaled coordinate space of (0,0,100%,100%).

    @@ -152,11 +162,11 @@ Width - The width of the filter area. Can be expressed as a fixed or relative coordinate. + The width of the filter area. Can be expressed as a fixed or scaled coordinate. Get/Set DOUBLE -

    The width of the filter area is expressed here as a fixed or relative coordinate. The width and height effectively restrain the working space for the effect processing, making them an important consideration for efficiency.

    +

    The width of the filter area is expressed here as a fixed or scaled coordinate. The width and height effectively restrain the working space for the effect processing, making them an important consideration for efficiency.

    The coordinate system for the width and height depends on the value for Units.

    If width or height is not specified, the effect is as if a value of 120% were specified.

    @@ -192,10 +202,15 @@ The default colour-space is sRGB, recommended for its speed. + + Scale X/Y values independently and in relation to the width/height of the parent viewport. + Scale X/Y values on a 1:1 basis, in relation to the diagonal of the parent viewport. + + - Coordinates are relative to the object's bounding box. + Coordinates are scaled to the object's bounding box. - Coordinates are relative to the current viewport. + Coordinates are scaled to the current viewport. diff --git a/docs/xml/modules/classes/vectorgradient.xml b/docs/xml/modules/classes/vectorgradient.xml index ec02b3798..d453092b5 100644 --- a/docs/xml/modules/classes/vectorgradient.xml +++ b/docs/xml/modules/classes/vectorgradient.xml @@ -12,7 +12,7 @@ ID_VECTORGRADIENT Graphics modules/vectorgradient.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    The VectorGradient class is used by Vector painting algorithms to fill and stroke vectors with gradients. This is achieved by initialising a VectorGradient object with the desired settings and then registering it with a VectorScene via the VectorScene:AddDef() method.

    Any vector within the target scene will be able to utilise the gradient for filling or stroking by referencing its name through the Vector:Fill and Vector:Stroke fields. For instance 'url(#redgradient)'.

    @@ -83,7 +83,7 @@ Read/Write VGF -

    Dimension flags that indicate whether field values are fixed or relative are defined here.

    +

    Dimension flags that indicate whether field values are fixed or scaled are defined here.

    @@ -136,7 +136,7 @@ Get/Set DOUBLE -

    The radius of the gradient can be defined in fixed units or relative terms to its container. A default radius of 50% (0.5) applies if this field is not set.

    +

    The radius of the gradient can be defined in fixed units or scaled terms to its container. A default radius of 50% (0.5) applies if this field is not set.

    The Radius value has no effect if the gradient is linear.

    @@ -199,7 +199,7 @@ Read/Init VUNIT -

    The default coordinate system for gradients is BOUNDING_BOX, which positions the gradient around the vector that references it. The alternative is USERSPACE, which positions the gradient relative to the current viewport.

    +

    The default coordinate system for gradients is BOUNDING_BOX, which positions the gradient around the vector that references it. The alternative is USERSPACE, which positions the gradient scaled to the current viewport.

    @@ -211,7 +211,7 @@ DOUBLE

    The (X1,Y1) field values define the starting coordinate for mapping linear gradients. Other gradient types ignore these values. The gradient will be drawn from (X1,Y1) to (X2,Y2).

    -

    Coordinate values can be expressed as percentages that are relative to the target space.

    +

    Coordinate values can be expressed as percentages that are scaled to the target space.

    @@ -222,7 +222,7 @@ DOUBLE

    The (X2,Y2) field values define the end coordinate for mapping linear gradients. Other gradient types ignore these values. The gradient will be drawn from (X1,Y1) to (X2,Y2).

    -

    Coordinate values can be expressed as percentages that are relative to the target space.

    +

    Coordinate values can be expressed as percentages that are scaled to the target space.

    @@ -243,7 +243,7 @@ DOUBLE

    The (X2,Y2) field values define the end coordinate for mapping linear gradients. Other gradient types ignore these values. The gradient will be drawn from (X1,Y1) to (X2,Y2).

    -

    Coordinate values can be expressed as percentages that are relative to the target space.

    +

    Coordinate values can be expressed as percentages that are scaled to the target space.

    @@ -265,15 +265,15 @@ X2 is fixed Y1 is fixed Y2 is fixed - CX is relative - CY is relative - FX is relative - FY is relative - Radius is relative - X1 is relative - X2 is relative - Y1 is relative - Y2 is relative + CX is scaled + CY is scaled + FX is scaled + FY is scaled + Radius is scaled + X1 is scaled + X2 is scaled + Y1 is scaled + Y2 is scaled @@ -295,9 +295,9 @@ - Coordinates are relative to the object's bounding box. + Coordinates are scaled to the object's bounding box. - Coordinates are relative to the current viewport. + Coordinates are scaled to the current viewport. diff --git a/docs/xml/modules/classes/vectorgroup.xml b/docs/xml/modules/classes/vectorgroup.xml new file mode 100644 index 000000000..4de0a7c8c --- /dev/null +++ b/docs/xml/modules/classes/vectorgroup.xml @@ -0,0 +1,25 @@ + + + + + + VectorGroup + class + Vector + Extends the Vector class with support for organising vectors into groups. + 1 + 88397565 + ID_VECTORGROUP + Graphics + modules/vectorgroup.h + Paul Manias © 2010-2024 + +

    Groups provide a simple way of grouping vector objects. Groups have a passive effect on the drawing process and can be effective at assigning inheritable attributes to child vectors.

    +

    If there is a need to adjust the container dimensions, use a VectorViewport instead.

    + + group.cpp + +
    + + +
    diff --git a/docs/xml/modules/classes/vectorimage.xml b/docs/xml/modules/classes/vectorimage.xml index de77bc5c5..e6870f084 100644 --- a/docs/xml/modules/classes/vectorimage.xml +++ b/docs/xml/modules/classes/vectorimage.xml @@ -12,11 +12,12 @@ ID_VECTORIMAGE Graphics modules/vectorimage.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    The VectorImage class is used by Vector painting algorithms to fill and stroke vectors with bitmap images. This is achieved by initialising a VectorImage object with the desired settings and then registering it with a VectorScene via the VectorScene:AddDef() method.

    Any vector within the target scene will be able to utilise the image for filling or stroking by referencing its name through the Vector:Fill and Vector:Stroke fields. For instance 'url(#logo)'.

    -

    It is strongly recommended that the VectorImage is owned by the VectorScene that is handling the definition. This will ensure that the VectorImage is de-allocated when the scene is destroyed.

    +

    It is strongly recommended that the VectorImage is owned by the VectorScene that is handling the definition. This will ensure that the VectorImage is de-allocated when the scene is destroyed.

    +

    NOTE: For the rendering of vectors as flattened images, use VectorPattern.

    image.cpp @@ -46,11 +47,11 @@ Dimensions - Dimension flags define whether individual dimension fields contain fixed or relative values. + Dimension flags define whether individual dimension fields contain fixed or scaled values. Read/Write INT -

    Of the Dimension flags that are available, only FIXED_X, FIXED_Y, RELATIVE_X and RELATIVE_Y are applicable.

    +

    Of the Dimension flags that are available, only FIXED_X, FIXED_Y, SCALED_X and SCALED_Y are applicable.

    @@ -67,11 +68,11 @@ SpreadMethod - Defines the drawing mode. + Defines image tiling behaviour, if desired. Read/Write VSPREAD -

    The SpreadMethod defines the way in which the image is drawn within the target area. The default setting is PAD.

    +

    The SpreadMethod defines the way in which the image is tiled within the target area if it is smaller than the available space. It is secondary to the application of AspectRatio. The default setting is CLIP, which prevents the image from being tiled.

    @@ -82,7 +83,7 @@ Read/Write VUNIT -

    This field declares the coordinate system that is used for values in the X and Y fields. The default is BOUNDING_BOX.

    +

    This field declares the coordinate system that is used for values in the X and Y fields. The default is BOUNDING_BOX.

    @@ -126,9 +127,9 @@ - Coordinates are relative to the object's bounding box. + Coordinates are scaled to the object's bounding box. - Coordinates are relative to the current viewport. + Coordinates are scaled to the current viewport. diff --git a/docs/xml/modules/classes/vectorpath.xml b/docs/xml/modules/classes/vectorpath.xml index dbaa0de39..92a9bc10b 100644 --- a/docs/xml/modules/classes/vectorpath.xml +++ b/docs/xml/modules/classes/vectorpath.xml @@ -12,7 +12,7 @@ ID_VECTORPATH Graphics modules/vectorpath.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    VectorPath provides support for parsing SVG styled path strings.

    @@ -37,7 +37,7 @@ AddCommand Add one or more commands to the end of the path sequence. - ERROR vpAddCommand(OBJECTPTR Object, struct PathCommand * Commands, LONG Size) + ERR vpAddCommand(OBJECTPTR Object, struct PathCommand * Commands, LONG Size) Array of commands to add to the path. The size of the Command buffer, in bytes. @@ -51,7 +51,7 @@ GetCommand Retrieve a specific command from the path sequence. - ERROR vpGetCommand(OBJECTPTR Object, LONG Index, struct PathCommand ** Command) + ERR vpGetCommand(OBJECTPTR Object, LONG Index, struct PathCommand ** Command) The index of the command to retrieve. The requested command will be returned in this parameter. @@ -64,7 +64,7 @@ RemoveCommand Remove at least one command from the path sequence. - ERROR vpRemoveCommand(OBJECTPTR Object, LONG Index, LONG Total) + ERR vpRemoveCommand(OBJECTPTR Object, LONG Index, LONG Total) The index of the command to remove. The total number of commands to remove, starting from the given Index. @@ -77,7 +77,7 @@ SetCommand Copies one or more commands into an existing path. - ERROR vpSetCommand(OBJECTPTR Object, LONG Index, struct PathCommand * Command, LONG Size) + ERR vpSetCommand(OBJECTPTR Object, LONG Index, struct PathCommand * Command, LONG Size) The index of the command that is to be set. An array of commands to set in the path. @@ -91,9 +91,9 @@ SetCommandList The fastest available mechanism for setting a series of path instructions. - ERROR vpSetCommandList(OBJECTPTR Object, APTR Commands, LONG Size) + ERR vpSetCommandList(OBJECTPTR Object, APTR Commands, LONG Size) - An array of path command structures. + An array of PathCommand structures. The byte size of the Commands buffer. @@ -108,10 +108,11 @@ Commands Direct pointer to the PathCommand array. - Get + Get/Set STRUCT [] -

    Read the Commands field to obtain a direct pointer to the PathCommand array. This will allow the path to be modified directly. After making changes to the path, call Flush to register the changes for the next redraw.

    +

    Read the Commands field to obtain a direct pointer to the PathCommand array. This will allow the control points of the path to be modified directly, but it is not possible to resize the path. After making changes to the path, call Flush to register the changes for the next redraw.

    +

    This field can also be written at any time with a new array of PathCommand structures. Doing so will clear the existing path, if any.

    @@ -163,12 +164,11 @@ Z: Close Path The command type (PE value) - Private Equivalent to the large-arc-flag in SVG, it ensures that the arc follows the longest drawing path when TRUE. Equivalent to the sweep-flag in SVG, it inverts the default behaviour in generating arc paths. Private - The targeted X coordinate (absolute or relative) for the command - The targeted Y coordinate (absolute or relative) for the command + The targeted X coordinate (absolute or scaled) for the command + The targeted Y coordinate (absolute or scaled) for the command Private Private The X2 coordinate for curve commands, or RX for arcs diff --git a/docs/xml/modules/classes/vectorpattern.xml b/docs/xml/modules/classes/vectorpattern.xml index 15466134d..b6a72796f 100644 --- a/docs/xml/modules/classes/vectorpattern.xml +++ b/docs/xml/modules/classes/vectorpattern.xml @@ -12,10 +12,10 @@ ID_VECTORPATTERN Graphics modules/vectorpattern.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    The VectorPattern class is used by Vector painting algorithms to fill and stroke vectors with pre-rendered patterns. It is the most efficient way of rendering a common set of graphics multiple times.

    -

    The VectorPattern must be registered with a VectorScene via the AddDef method. Any vector within the target scene will be able to utilise the pattern for filling or stroking by referencing its name through the Vector:Fill and Vector:Stroke fields. For instance 'url(#dots)'.

    +

    The VectorPattern must be registered with a VectorScene via the AddDef method. Any vector within the target scene will be able to utilise the pattern for filling or stroking by referencing its name through the Vector:Fill and Vector:Stroke fields. For instance url(#dots).

    A special use case is made for patterns that are applied as a fill operation in VectorViewport objects. In this case the renderer will dynamically render the pattern as a background within the viewport. This ensures that the pattern is rendered at maximum fidelity whenever it is used, and not affected by bitmap clipping restrictions. It should be noted that this means the image caching feature will be disabled.

    It is strongly recommended that the VectorPattern is owned by the VectorScene that is handling the definition. This will ensure that the VectorPattern is deallocated when the scene is destroyed.

    @@ -40,7 +40,7 @@ Get/Set DOUBLE -

    The (Width,Height) field values define the dimensions of the pattern tile. If the provided value is a percentage then the dimension is calculated relative to the bounding box or viewport applying the pattern, dependent on the Units setting.

    +

    The (Width,Height) field values define the dimensions of the pattern tile. If the provided value is scaled, then the dimension is calculated relative to the bounding box or viewport applying the pattern, dependent on the Units setting.

    @@ -133,7 +133,7 @@ Get/Set DOUBLE -

    The (Width,Height) field values define the dimensions of the pattern tile. If the provided value is a percentage then the dimension is calculated relative to the bounding box or viewport applying the pattern, dependent on the Units setting.

    +

    The (Width,Height) field values define the dimensions of the pattern tile. If the provided value is scaled, the dimension is calculated relative to the bounding box or viewport applying the pattern, dependent on the Units setting.

    @@ -170,9 +170,9 @@ - Coordinates are relative to the object's bounding box. + Coordinates are scaled to the object's bounding box. - Coordinates are relative to the current viewport. + Coordinates are scaled to the current viewport. diff --git a/docs/xml/modules/classes/vectorpolygon.xml b/docs/xml/modules/classes/vectorpolygon.xml index e7337a499..8bc4508e8 100644 --- a/docs/xml/modules/classes/vectorpolygon.xml +++ b/docs/xml/modules/classes/vectorpolygon.xml @@ -12,7 +12,7 @@ ID_VECTORPOLYGON Graphics modules/vectorpolygon.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    The VectorPolygon class provides support for three different types of vector:

    * Closed-point polygons consisting of at least 3 points. * Open polygons consisting of at least 3 points (a 'polyline' in SVG). * Single lines consisting of two points only (a 'line' in SVG).

    @@ -81,7 +81,7 @@ DOUBLE

    This field defines the X coordinate of the first point of the polygon. It is recommended that this field is only used when creating a VectorPolygon that will be used to draw a single line.

    -

    By default the value will be treated as a fixed coordinate. Relative values are supported if the value is a defined as a percentage.

    +

    By default the value will be treated as a fixed coordinate. Scaled values are supported if the value is a defined as a percentage.

    @@ -92,7 +92,7 @@ DOUBLE

    This field defines the X coordinate of the second point of the polygon. It is recommended that this field is only used when creating a VectorPolygon that will be used to draw a single line.

    -

    By default the value will be treated as a fixed coordinate. Relative values are supported if the value is a defined as a percentage.

    +

    By default the value will be treated as a fixed coordinate. Scaled values are supported if the value is a defined as a percentage.

    @@ -103,7 +103,7 @@ DOUBLE

    This field defines the Y coordinate of the first point of the polygon. It is recommended that this field is only used when creating a VectorPolygon that will be used to draw a single line.

    -

    By default the value will be treated as a fixed coordinate. Relative values are supported if the value is a defined as a percentage.

    +

    By default the value will be treated as a fixed coordinate. Scaled values are supported if the value is a defined as a percentage.

    @@ -114,7 +114,7 @@ DOUBLE

    This field defines the Y coordinate of the second point of the polygon. It is recommended that this field is only used when creating a VectorPolygon that will be used to draw a single line.

    -

    By default the value will be treated as a fixed coordinate. Relative values are supported if the value is a defined as a percentage.

    +

    By default the value will be treated as a fixed coordinate. Scaled values are supported if the value is a defined as a percentage.

    @@ -123,8 +123,8 @@ The X coordinate of this point. The Y coordinate of this point. - TRUE if the X value is relative to its viewport (between 0 and 1.0). - TRUE if the Y value is relative to its viewport (between 0 and 1.0). + TRUE if the X value is scaled to its viewport (between 0 and 1.0). + TRUE if the Y value is scaled to its viewport (between 0 and 1.0).
    diff --git a/docs/xml/modules/classes/vectorrectangle.xml b/docs/xml/modules/classes/vectorrectangle.xml index a169f5a87..a03bf8590 100644 --- a/docs/xml/modules/classes/vectorrectangle.xml +++ b/docs/xml/modules/classes/vectorrectangle.xml @@ -12,7 +12,7 @@ ID_VECTORRECTANGLE Graphics modules/vectorrectangle.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    VectorRectangle extends the Vector class with the ability to generate rectangular paths.

    @@ -23,7 +23,7 @@ Dimensions - Dimension flags define whether individual dimension fields contain fixed or relative values. + Dimension flags define whether individual dimension fields contain fixed or scaled values. Get/Set INT @@ -33,21 +33,25 @@ The Width value is a fixed coordinate. The X value is a fixed coordinate. The Y value is a fixed coordinate. -The Height value is a relative coordinate. -The Width value is a relative coordinate. -The X value is a relative coordinate. -The Y value is a relative coordinate. +The RoundX value is a fixed coordinate. +The RoundY value is a fixed coordinate. +The Height value is a scaled coordinate. +The Width value is a scaled coordinate. +The X value is a scaled coordinate. +The Y value is a scaled coordinate. +The RoundX value is a scaled coordinate. +The RoundY value is a scaled coordinate. Height - The height of the rectangle. Can be expressed as a fixed or relative coordinate. + The height of the rectangle. Can be expressed as a fixed or scaled coordinate. Get/Set DOUBLE -

    The height of the rectangle is defined here as either a fixed or relative value. Negative values are permitted (this will flip the rectangle on the vertical axis).

    +

    The height of the rectangle is defined here as either a fixed or scaled value. Negative values are permitted (this will flip the rectangle on the vertical axis).

    @@ -71,34 +75,53 @@
    + + Rounding + Precisely controls rounded corner positioning. + Get/Set + DOUBLE [] + +

    Set the Rounding field if all four corners of the rectangle need to be precisely controlled. Four X,Y sizing pairs must be provided in sequence, with the first describing the top-left corner and proceeding in clockwise fashion. Each pair of values is equivalent to a RoundX,RoundY definition for that corner only.

    +

    By default, values will be treated as fixed pixel units. They can be changed to scaled values by defining the DMF_SCALED_RADIUS_X and/or DMF_SCALED_RADIUS_Y flags in the Dimensions field. The scale is calculated against the rectangle's diagonal.

    +
    +
    + Width - The width of the rectangle. Can be expressed as a fixed or relative coordinate. + The width of the rectangle. Can be expressed as a fixed or scaled coordinate. Get/Set DOUBLE -

    The width of the rectangle is defined here as either a fixed or relative value. Negative values are permitted (this will flip the rectangle on the horizontal axis).

    +

    The width of the rectangle is defined here as either a fixed or scaled value. Negative values are permitted (this will flip the rectangle on the horizontal axis).

    X - The left-side of the rectangle. Can be expressed as a fixed or relative coordinate. + The left-side of the rectangle. Can be expressed as a fixed or scaled coordinate. + Get/Set + DOUBLE + + + + XOffset + The right-side of the rectangle, expressed as a fixed or scaled offset value. Get/Set DOUBLE - -

    The position of the rectangle on the x-axis is defined here as a fixed or relative coordinate.

    -
    Y - The top of the rectangle. Can be expressed as a fixed or relative coordinate. + The top of the rectangle. Can be expressed as a fixed or scaled coordinate. + Get/Set + DOUBLE + + + + YOffset + The bottom of the rectangle, expressed as a fixed or scaled offset value. Get/Set DOUBLE - -

    The position of the rectangle on the y-axis is defined here as a fixed or relative coordinate.

    -
    diff --git a/docs/xml/modules/classes/vectorscene.xml b/docs/xml/modules/classes/vectorscene.xml index a437e6d2e..305b6ca2b 100644 --- a/docs/xml/modules/classes/vectorscene.xml +++ b/docs/xml/modules/classes/vectorscene.xml @@ -12,7 +12,7 @@ ID_VECTORSCENE Graphics modules/vectorscene.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    The VectorScene class acts as a container and control point for the management of vector definitions. Its main purpose is to draw the scene to a target Bitmap or Surface provided by the client.

    Vector scenes are created by initialising multiple Vector objects such as VectorPath and VectorViewport and positioning them within a vector tree. The VectorScene must lie at the root.

    @@ -57,15 +57,16 @@ AddDef - Adds a new definition to a vector tree. - ERROR scAddDef(OBJECTPTR Object, CSTRING Name, OBJECTPTR Def) + Registers a named definition object within a scene graph. + ERR scAddDef(OBJECTPTR Object, CSTRING Name, OBJECTPTR Def) The unique name to associate with the definition. Reference to the definition object. -

    This method will add a new definition object to the root of a vector tree. This feature is provided to support SVG style referencing for features such as gradients, images and patterns. By providing a name with the definition object, the object can then be referenced in URL strings.

    -

    For instance, if creating a gradient with a name of "redGradient" it would be possible to reference it with url(#redGradient) in common graphics attributes such as fill and stroke.

    +

    This method will add a new definition object to the root of a vector tree and gives it a name. This feature is provided to support SVG style referencing for features such as gradients, images and patterns. By providing a name with the definition object, the object can then be referenced in URL strings.

    +

    For example, if creating a gradient with a name of "redGradient" it would be possible to reference it with url(#redGradient) in common graphics attributes such as fill and stroke.

    +

    At the time of writing, the provided object must belong to one of the following classes to be valid: Vector, VectorScene, VectorGradient, VectorImage, VectorPath, VectorPattern, VectorFilter, VectorTransition, VectorClip.

    Operation successful. @@ -79,9 +80,9 @@ Debug Internal functionality for debugging. - ERROR scDebug(OBJECTPTR Object) + ERR scDebug(OBJECTPTR Object) -

    This internal method prints comprehensive debugging information to the log.

    +

    This internal method prints comprehensive information that describes the scene graph to the log.

    Operation successful. @@ -91,7 +92,7 @@ FindDef Search for a vector definition by name. - ERROR scFindDef(OBJECTPTR Object, CSTRING Name, OBJECTPTR * Def) + ERR scFindDef(OBJECTPTR Object, CSTRING Name, OBJECTPTR * Def) The name of the definition. A pointer to the definition object is returned here if discovered. @@ -110,7 +111,7 @@ SearchByID Search for a vector by numeric ID. - ERROR scSearchByID(OBJECTPTR Object, LONG ID, OBJECTPTR * Result) + ERR scSearchByID(OBJECTPTR Object, LONG ID, OBJECTPTR * Result) The ID to search for. This parameter will be updated with the discovered vector, or NULL if not found. @@ -218,8 +219,8 @@ Read *VectorViewport -

    The first object in the vector scene is referenced here. It must belong to the VectorViewport class, because it will be used to define the size and location of the area rendered by the scene.

    -

    The Viewport field must not be set by the client. The VectorViewport object will configure its ownership to the VectorScene prior to initialisation. The Viewport field value will then be set automatically when the VectorViewport object is initialised.

    +

    The first object in the vector scene is referenced here. It must belong to the VectorViewport class, which will be used to define the size and location of the area rendered by the scene.

    +

    The Viewport value cannot be set by the client. It will be automatically defined when the first VectorViewport owned by the VectorScene is initialised.

    diff --git a/docs/xml/modules/classes/vectorshape.xml b/docs/xml/modules/classes/vectorshape.xml index 29abaaf7f..44733517a 100644 --- a/docs/xml/modules/classes/vectorshape.xml +++ b/docs/xml/modules/classes/vectorshape.xml @@ -12,7 +12,7 @@ ID_VECTORSHAPE Graphics modules/vectorshape.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    The VectorShape class extends the Vector class with support for generating paths with the Superformula algorithm by Johan Gielis. This feature is not part of the SVG standard and therefore should not be used in cases where SVG compliance is a strict requirement.

    The Superformula is documented in detail at Wikipedia: http://en.wikipedia.org/wiki/Superformula

    @@ -44,21 +44,21 @@ CenterX - The center of the shape on the x-axis. Expressed as a fixed or relative coordinate. + The center of the shape on the x-axis. Expressed as a fixed or scaled coordinate. Get/Set DOUBLE -

    The horizontal center of the shape is defined here as either a fixed or relative value.

    +

    The horizontal center of the shape is defined here as either a fixed or scaled value.

    CenterY - The center of the shape on the y-axis. Expressed as a fixed or relative coordinate. + The center of the shape on the y-axis. Expressed as a fixed or scaled coordinate. Get/Set DOUBLE -

    The vertical center of the shape is defined here as either a fixed or relative value.

    +

    The vertical center of the shape is defined here as either a fixed or scaled value.

    @@ -74,7 +74,7 @@ Dimensions - Dimension flags define whether individual dimension fields contain fixed or relative values. + Dimension flags define whether individual dimension fields contain fixed or scaled values. Get/Set INT @@ -83,9 +83,9 @@ The CenterX value is a fixed coordinate. The CenterY value is a fixed coordinate. The Radius value is a fixed coordinate. -The CenterX value is a relative coordinate. -The CenterY value is a relative coordinate. -The Radius value is a relative coordinate. +The CenterX value is a scaled coordinate. +The CenterY value is a scaled coordinate. +The Radius value is a scaled coordinate. @@ -163,11 +163,11 @@ Radius - The radius of the generated shape. Expressed as a fixed or relative coordinate. + The radius of the generated shape. Expressed as a fixed or scaled coordinate. Get/Set DOUBLE -

    The Radius defines the final size of the generated shape. It can be expressed in fixed or relative terms.

    +

    The Radius defines the final size of the generated shape. It can be expressed in fixed or scaled terms.

    diff --git a/docs/xml/modules/classes/vectorspiral.xml b/docs/xml/modules/classes/vectorspiral.xml index cf5e429fd..0104eb436 100644 --- a/docs/xml/modules/classes/vectorspiral.xml +++ b/docs/xml/modules/classes/vectorspiral.xml @@ -12,9 +12,9 @@ ID_VECTORSPIRAL Graphics modules/vectorspiral.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024 -

    The VectorSpiral class provides the necessary functionality for generating spiral paths that extend from a central point.

    +

    The VectorSpiral class generates spiral paths that extend from a central point.

    spiral.cpp @@ -23,21 +23,21 @@ CenterX - The horizontal center of the spiral. Expressed as a fixed or relative coordinate. + The horizontal center of the spiral. Expressed as a fixed or scaled coordinate. Get/Set DOUBLE -

    The horizontal center of the spiral is defined here as either a fixed or relative value.

    +

    The horizontal center of the spiral is defined here as either a fixed or scaled value.

    CenterY - The vertical center of the spiral. Expressed as a fixed or relative coordinate. + The vertical center of the spiral. Expressed as a fixed or scaled coordinate. Get/Set DOUBLE -

    The vertical center of the spiral is defined here as either a fixed or relative value.

    +

    The vertical center of the spiral is defined here as either a fixed or scaled value.

    @@ -51,9 +51,20 @@ + + LoopLimit + Used to limit the number of loops produced by the spiral path generator. + Get/Set + DOUBLE + +

    The LoopLimit can be used to impose a limit on the total number of loops that are performed by the spiral path generator. It can be used as an alternative to, or conjunction with the Radius value to limit the final spiral size.

    +

    If the LoopLimit is not set, the Radius will take precedence.

    +
    +
    + Offset - Offset the generation of the path by a given value. + Offset the starting coordinate of the spiral by this value. Get/Set DOUBLE @@ -73,21 +84,23 @@ Radius - The radius of the spiral. Expressed as a fixed or relative coordinate. + The radius of the spiral. Expressed as a fixed or scaled coordinate. Get/Set DOUBLE -

    The radius of the spiral is defined here as either a fixed or relative value.

    +

    The radius of the spiral is defined here as either a fixed or scaled value. If zero, preference is given to LoopLimit.

    - Scale - The scale of the spiral, expressed as a multiplier. + Spacing + Declares the amount of empty space between each loop of the spiral. Get/Set DOUBLE -

    The spiral path can be scaled by setting this field. The points on the spiral will be scaled by being multiplied by the scale factor.

    +

    Spacing tightly controls the computation of the spiral path, ensuring that a specific amount of empty space is left between each loop. The space is declared in pixel units.

    +

    If Spacing is undeclared, the spiral expands at an incremental rate of +Step * 0.1.

    @@ -97,7 +110,7 @@ Get/Set DOUBLE -

    The Step value alters the distance between each vertex in the spiral path during its generation. The default value is 0.1. Using larger values will create a spiral with more visible corners due to the overall reduction in vertices.

    +

    The Step value affects the distance between each vertex in the spiral path during its generation. The default value is 1.0. Using larger values will create a spiral with jagged corners due to the reduction in vertices.

    diff --git a/docs/xml/modules/classes/vectortext.xml b/docs/xml/modules/classes/vectortext.xml index eacf4da35..794e59818 100644 --- a/docs/xml/modules/classes/vectortext.xml +++ b/docs/xml/modules/classes/vectortext.xml @@ -12,7 +12,7 @@ ID_VECTORTEXT Graphics modules/vectortext.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    To create text along a path, set the #Morph field with a reference to any Vector object that generates a path. The following extract illustrates the SVG equivalent of this feature:

    <defs>
    @@ -36,7 +36,7 @@
         
           DeleteLine
           Deletes any line number.
    -      ERROR vtDeleteLine(OBJECTPTR Object, LONG Line)
    +      ERR vtDeleteLine(OBJECTPTR Object, LONG Line)
           
             The line number that you want to delete.  If negative, the last line will be deleted.
           
    @@ -110,18 +110,53 @@
           
         
     
    +    
    +      Descent
    +      The font descent measured in pixels, after DPI conversion.
    +      Get
    +      INT
    +      
    +

    Use Descent to retrieve the height of the font descent region in actual display pixels, after DPI conversion has been taken into account.

    +
    +
    + + + DisplayHeight + The font height measured in pixels, after DPI conversion. + Get + INT + +

    Use DisplayHeight to retrieve the font height in actual display pixels, after DPI conversion has been taken into account. The height includes the top region reserved for accents, but excludes the descent value.

    +
    +
    + + + DisplaySize + The FontSize measured in pixels, after DPI conversion. + Get + INT + +

    Use DisplaySize to retrieve the FontSize in actual display pixels, after DPI conversion has been taken into account. For example, if FontSize is set to 16 in a 96 DPI environment, the resulting value is 12 after performing the calculation 16 * 72 / 96.

    +
    +
    + Face Defines the font face/family to use in rendering the text string. Get/Set STRING -

    The face/family of the desired font for rendering the text is specified here. It is possible to list multiple fonts in CSV format in case the first-choice font is unavailable. For instance, Arial,Open Sans would load the Open Sans font if Arial was unavailable.

    -

    If none of the listed fonts are available, the default system font will be used.

    -

    Please note that referencing bitmap fonts is unsupported and they will be ignored by the font loader.

    +

    The family name of the principal font for rendering text is specified here.

    +

    It is possible to list multiple fonts in CSV format in case the first-choice font is unavailable. For instance, Arial,Noto Sans would select the Noto Sans font if Arial was unavailable in the font database. The name of the closest matching font will be stored as the Face value.

    + + Fill + Get/Set + STRING + + Focus Refers to the object that will be monitored for user focussing. @@ -135,11 +170,11 @@ Font - The primary Font object that is used to source glyphs for the text string. - Get + Copies key meta information from a Font or other VectorText to create a matching text object. + Set OBJECTPTR -

    Returns the Font object that is used for drawing the text. The object may be queried but must remain unmodified. Any modification by the client that happens to work in the present code release may fail in future releases.

    +

    To create a VectorText object that uses a matching typeset from another Font or VectorText object, set this field with a reference to that object. This can only be done prior to initialisation and the other object must have been initialised.

    @@ -149,8 +184,10 @@ Get/Set STRING -

    The FontSize refers to the height of the font from baseline to baseline. By default, the value corresponds to the current user coordinate system in pixels. To define the point size, append 'pt' to the number.

    -

    If retrieving the font size, the string must be freed by the client when no longer in use.

    +

    The FontSize is equivalent to the SVG font-size attribute and refers to the height of the font from the dominant baseline to the hanging baseline. This would mean that a capitalised letter without accents should fill the entire vertical space defined by FontSize.

    +

    The default unit value of FontSize is in pixels at a resolution of 72 DPI. This means that if the display is configured to a more common 96 DPI for instance, the actual pixel size on the display will be FontSize * 72 / 96. Point sizes are also measured at a constant ratio of 1/72 irrespective of display settings, and this may need to factor into precise size calculations.

    +

    Standard unit measurements such as px, em and pt are supported by appending them after the numeric value. 1em is equivalent to the 'default font size', which is typically 16px unless modified.

    +

    When retrieving the font size, the resulting string must be freed by the client when no longer in use.

    @@ -185,6 +222,26 @@ + + LineSpacing + The number of pixels from one line to the next. + Get + INT + +

    This field can be queried for the amount of space between each line, measured in display pixels.

    +
    +
    + + + Point + Returns the point-size of the font. + Get + INT + +

    Reading the Point value will return the point-size of the font, calculated as FontSize * 72 / DisplayDPI.

    +
    +
    + Rotate Applies vertical spacing on a per-character basis. @@ -266,9 +323,12 @@ TextWidth - The raw pixel width of the widest line in the String value. + The pixel width of the widest line in the String field. Get INT + +

    This field will return the pixel width of the widest line in the String field. The result is not modified by transforms.

    +
    @@ -295,7 +355,7 @@ Get/Set DOUBLE -

    The x-axis coordinate of the text is specified here as a fixed value. Relative coordinates are not supported.

    +

    The x-axis coordinate of the text is specified here as a fixed value. Scaled coordinates are not supported.

    @@ -305,7 +365,7 @@ Get/Set DOUBLE -

    The Y-axis coordinate of the text is specified here as a fixed value. Relative coordinates are not supported.

    +

    The Y-axis coordinate of the text is specified here as a fixed value. Scaled coordinates are not supported.

    Unlike other vector shapes, the Y coordinate positions the text from its base line rather than the top of the shape.

    diff --git a/docs/xml/modules/classes/vectorviewport.xml b/docs/xml/modules/classes/vectorviewport.xml index a70424663..219b9328c 100644 --- a/docs/xml/modules/classes/vectorviewport.xml +++ b/docs/xml/modules/classes/vectorviewport.xml @@ -12,7 +12,7 @@ ID_VECTORVIEWPORT Graphics modules/vectorviewport.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    This class is used to declare a viewport within a vector scene graph. A master viewport is required as the first object in a VectorScene and it must contain all vector graphics content.

    The size of the viewport is initially set to (0,0,100%,100%) so as to be all inclusive. Setting the X, Y, Width and Height fields will determine the position and clipping of the displayed content (the 'target area'). The ViewX, ViewY, ViewWidth and ViewHeight fields declare the viewbox ('source area') that will be sampled for the target.

    @@ -84,7 +84,7 @@ Dimensions - Dimension flags define whether individual dimension fields contain fixed or relative values. + Dimension flags define whether individual dimension fields contain fixed or scaled values. Get/Set INT @@ -113,7 +113,7 @@ Get/Set DOUBLE -

    The height of the viewport's target area is defined here as a fixed or relative value. The default value is 100% for full coverage.

    +

    The height of the viewport's target area is defined here as a fixed or scaled value. The default value is 100% for full coverage.

    The fixed value is always returned when retrieving the height.

    @@ -197,7 +197,7 @@ Get/Set DOUBLE -

    The width of the viewport's target area is defined here as a fixed or relative value. The default value is 100% for full coverage.

    +

    The width of the viewport's target area is defined here as a fixed or scaled value. The default value is 100% for full coverage.

    @@ -207,7 +207,7 @@ Get/Set DOUBLE -

    The display position targeted by the viewport is declared by the (X,Y) field values. Coordinates can be expressed as fixed or relative pixel units.

    +

    The display position targeted by the viewport is declared by the (X,Y) field values. Coordinates can be expressed as fixed or scaled pixel units.

    If an offset from the edge of the parent is desired, the XOffset field must be defined. If a X and XOffset value are defined together, the width of the viewport is computed on-the-fly and will change in response to the parent's width.

    @@ -218,7 +218,7 @@ Get/Set DOUBLE -

    The display position targeted by the viewport is declared by the (X,Y) field values. Coordinates can be expressed as fixed or relative pixel units.

    +

    The display position targeted by the viewport is declared by the (X,Y) field values. Coordinates can be expressed as fixed or scaled pixel units.

    If an offset from the edge of the parent is desired, the XOffset field must be defined. If a X and XOffset value are defined together, the width of the viewport is computed on-the-fly and will change in response to the parent's width.

    @@ -229,7 +229,7 @@ Get/Set DOUBLE -

    The display position targeted by the viewport is declared by the (X,Y) field values. Coordinates can be expressed as fixed or relative pixel units.

    +

    The display position targeted by the viewport is declared by the (X,Y) field values. Coordinates can be expressed as fixed or scaled pixel units.

    If an offset from the edge of the parent is desired, the YOffset must be defined. If a Y and YOffset value are defined together, the height of the viewport is computed on-the-fly and will change in response to the parent's height.

    @@ -240,7 +240,7 @@ Get/Set DOUBLE -

    The display position targeted by the viewport is declared by the (X,Y) field values. Coordinates can be expressed as fixed or relative pixel units.

    +

    The display position targeted by the viewport is declared by the (X,Y) field values. Coordinates can be expressed as fixed or scaled pixel units.

    If an offset from the edge of the parent is desired, the YOffset must be defined. If a Y and YOffset value are defined together, the height of the viewport is computed on-the-fly and will change in response to the parent's height.

    @@ -266,6 +266,13 @@ + + Capitalised font height + Vertical advance from one line to the next + Height from the baseline to the top of the font, including accents. + Height from the baseline to the bottom of the font + + The next transform in the list. The vector associated with the transform. @@ -277,5 +284,12 @@ Matrix value F + + A VectorPattern object, suitable for pattern based fills. + A VectorImage object, suitable for image fills. + A VectorGradient object, suitable for gradient fills. + A single RGB colour definition, suitable for block colour fills. + + diff --git a/docs/xml/modules/classes/vectorwave.xml b/docs/xml/modules/classes/vectorwave.xml index c782b6934..98d4de2ca 100644 --- a/docs/xml/modules/classes/vectorwave.xml +++ b/docs/xml/modules/classes/vectorwave.xml @@ -12,7 +12,7 @@ ID_VECTORWAVE Graphics modules/vectorwave.h - Paul Manias © 2010-2023 + Paul Manias © 2010-2024

    The VectorWave class provides functionality for generating paths based on sine waves. This feature is not part of the SVG standard and therefore should not be used in cases where SVG compliance is a strict requirement.

    The sine wave will be generated within a rectangular region at (X,Y) with size (Width,Height). The horizontal center-line within the rectangle will dictate the orientation of the sine wave, and the path vertices are generated on a left-to-right basis.

    @@ -66,7 +66,7 @@ Dimensions - Dimension flags define whether individual dimension fields contain fixed or relative values. + Dimension flags define whether individual dimension fields contain fixed or scaled values. Get/Set INT @@ -76,10 +76,10 @@ The Width value is a fixed coordinate. The X value is a fixed coordinate. The Y value is a fixed coordinate. -The Height value is a relative coordinate. -The Width value is a relative coordinate. -The X value is a relative coordinate. -The Y value is a relative coordinate. +The Height value is a scaled coordinate. +The Width value is a scaled coordinate. +The X value is a scaled coordinate. +The Y value is a scaled coordinate. @@ -100,7 +100,7 @@ Get/Set DOUBLE -

    The height of the area containing the wave is defined here as a fixed or relative value.

    +

    The height of the area containing the wave is defined here as a fixed or scaled value.

    @@ -131,27 +131,27 @@ Get/Set DOUBLE -

    The width of the area containing the wave is defined here as a fixed or relative value.

    +

    The width of the area containing the wave is defined here as a fixed or scaled value.

    X - The x coordinate of the wave. Can be expressed as a fixed or relative coordinate. + The x coordinate of the wave. Can be expressed as a fixed or scaled coordinate. Get/Set DOUBLE -

    The x coordinate of the wave is defined here as either a fixed or relative value.

    +

    The x coordinate of the wave is defined here as either a fixed or scaled value.

    Y - The y coordinate of the wave. Can be expressed as a fixed or relative coordinate. + The y coordinate of the wave. Can be expressed as a fixed or scaled coordinate. Get/Set DOUBLE -

    The y coordinate of the wave is defined here as either a fixed or relative value.

    +

    The y coordinate of the wave is defined here as either a fixed or scaled value.

    diff --git a/docs/xml/modules/classes/xml.xml b/docs/xml/modules/classes/xml.xml index 23357c05b..2d8a56a8e 100644 --- a/docs/xml/modules/classes/xml.xml +++ b/docs/xml/modules/classes/xml.xml @@ -14,7 +14,7 @@ ID_XML Data modules/xml.h - Paul Manias © 2001-2023 + Paul Manias © 2001-2024

    The XML class provides functionality to create and maintain XML data files. It is capable of parsing and validating XML files with or without correct structure, and can perform optional parsing behaviours such as stripping comments during processing.

    Data can be loaded into an XML object either by specifying a file Path or by giving it an XML Statement. If multiple XML statements need to be processed then reset the Path or Statement field after initialisation and the XML object will rebuild itself. This saves on allocating multiple XML objects for batch processing.

    @@ -82,7 +82,7 @@ Count Count all tags that match a given XPath. - ERROR xmlCount(OBJECTPTR Object, CSTRING XPath, LONG * Result) + ERR xmlCount(OBJECTPTR Object, CSTRING XPath, LONG * Result) The XPath on which to perform the count. The total number of matching tags is returned here. @@ -99,7 +99,7 @@ Filter Filters the XML data down to a single tag and its children. - ERROR xmlFilter(OBJECTPTR Object, CSTRING XPath) + ERR xmlFilter(OBJECTPTR Object, CSTRING XPath) Refers to a valid XPath string. @@ -117,15 +117,15 @@ FindTag Searches for a tag via XPath. - ERROR xmlFindTag(OBJECTPTR Object, CSTRING XPath, FUNCTION * Callback, LONG * Result) + ERR xmlFindTag(OBJECTPTR Object, CSTRING XPath, FUNCTION * Callback, LONG * Result) An XPath string. Optional reference to a function that should be called for each matching tag. The index of the first matching tag is returned in this parameter (not valid if a Callback is defined). -

    This method will return the first tag that matches the search string specified in XPath. Optionally, if the XPath uses wildcards or would match multiple tags, a Callback function may be passed that will be called for each matching tag that is discovered. The prototype for the callback function is ERROR Function(*XML, XMLTag &Tag, CSTRING Attrib).

    -

    The Callback routine can terminate the search early by returning ERR_Terminate. All other error codes are ignored.

    +

    This method will return the first tag that matches the search string specified in XPath. Optionally, if the XPath uses wildcards or would match multiple tags, a Callback function may be passed that will be called for each matching tag that is discovered. The prototype for the callback function is ERR Function(*XML, XMLTag &Tag, CSTRING Attrib).

    +

    The Callback routine can terminate the search early by returning ERR::Terminate. All other error codes are ignored.

    A matching tag was found. @@ -138,7 +138,7 @@ GetAttrib Retrieves the value of an XML attribute. - ERROR xmlGetAttrib(OBJECTPTR Object, LONG Index, CSTRING Attrib, CSTRING * Value) + ERR xmlGetAttrib(OBJECTPTR Object, LONG Index, CSTRING Attrib, CSTRING * Value) The index of the XML tag to search. The name of the attribute to search for (case insensitive). If NULL or an empty string, the tag name is returned as the result. @@ -157,15 +157,15 @@ GetContent - Extracts the content embedded inside an XML tag. - ERROR xmlGetContent(OBJECTPTR Object, LONG Index, STRING Buffer, LONG Length) + Extracts the content of an XML tag. + ERR xmlGetContent(OBJECTPTR Object, LONG Index, STRING Buffer, LONG Length) Index of a tag that contains content. Pointer to a buffer that will receive the string data. The length of the Buffer in bytes. -

    The GetContent method is used to extract the string content from an XML tag. It will extract content that is immediately embedded within the XML tag and will not perform deep analysis of the tag structure (refer to GetString for deep extraction). Consider the following structure:

    +

    The GetContent method is used to extract the string content from an XML tag. It will extract content that is immediately embedded within the XML tag and will not perform deep analysis of the tag structure (refer to Serialise for deep extraction). Consider the following structure:

    <body>
       Hello
       <bold>my</bold>
    @@ -182,37 +182,16 @@
           
         
     
    -    
    -      GetString
    -      Retrieves data from an XML object in standard XML string format.
    -      ERROR xmlGetString(OBJECTPTR Object, LONG Index, XMF Flags, STRING * Result)
    -      
    -        Index to a source tag for pulling data out of the XML object.  Zero will always refer to the first tag.
    -        Special flags that affect the construction of the XML string.
    -        The resulting string is returned in this parameter.
    -      
    -      
    -

    The GetString method builds XML strings from data that has been loaded into an XML object. The string is created from the entire XML object or from a specific area of the XML tree by setting the Index parameter.

    -

    The XML string that is built by this method will be stored in the Result parameter. The memory block must be freed once the content is no longer required.

    -
    - - The XML string was retrieved. - Invalid arguments passed to function. - No information has been loaded into the XML object. - Failed to allocate an XML string for the result. - -
    - GetTag Returns a pointer to the XMLTag structure for a given tag index. - ERROR xmlGetTag(OBJECTPTR Object, LONG Index, struct XMLTag ** Result) + ERR xmlGetTag(OBJECTPTR Object, LONG Index, struct XMLTag ** Result) The index of the tag that is being retrieved. The XMLTag is returned in this parameter. -

    This method will return the XMLTag structure for a given tag Index. The Index is checked to ensure it is valid prior to retrieval, and an ERR_OutOfRange error will be returned if it is invalid.

    +

    This method will return the XMLTag structure for a given tag Index. The Index is checked to ensure it is valid prior to retrieval, and an ERR::OutOfRange error will be returned if it is invalid.

    Operation successful. @@ -224,7 +203,7 @@ InsertContent Inserts XML content into the XML tree. - ERROR xmlInsertContent(OBJECTPTR Object, LONG Index, XMI Where, CSTRING Content, LONG * Result) + ERR xmlInsertContent(OBJECTPTR Object, LONG Index, XMI Where, CSTRING Content, LONG * Result) Identifies the target XML tag. Use PREV or NEXT to insert behind or ahead of the target tag. Use CHILD for a child insert. @@ -244,8 +223,8 @@ InsertXML - Inserts an XML statement in the XML tree. - ERROR xmlInsertXML(OBJECTPTR Object, LONG Index, XMI Where, CSTRING XML, LONG * Result) + Parse an XML string and insert it in the XML tree. + ERR xmlInsertXML(OBJECTPTR Object, LONG Index, XMI Where, CSTRING XML, LONG * Result) The new data will target the tag specified here. Use PREV or NEXT to insert behind or ahead of the target tag. Use CHILD or CHILD_END for a child insert. @@ -267,7 +246,7 @@ InsertXPath Inserts an XML statement in an XML tree. - ERROR xmlInsertXPath(OBJECTPTR Object, CSTRING XPath, XMI Where, CSTRING XML, LONG * Result) + ERR xmlInsertXPath(OBJECTPTR Object, CSTRING XPath, XMI Where, CSTRING XML, LONG * Result) An XPath string that refers to the target insertion point. Use PREV or NEXT to insert behind or ahead of the target tag. Use CHILD for a child insert. @@ -287,7 +266,7 @@ MoveTags Move an XML tag group to a new position in the XML tree. - ERROR xmlMoveTags(OBJECTPTR Object, LONG Index, LONG Total, LONG DestIndex, XMI Where) + ERR xmlMoveTags(OBJECTPTR Object, LONG Index, LONG Total, LONG DestIndex, XMI Where) Index of the source tag to be moved. The total number of sibling tags to be moved from the source index. Minimum value of 1. @@ -309,7 +288,7 @@ RemoveTag Removes tag(s) from the XML structure. - ERROR xmlRemoveTag(OBJECTPTR Object, LONG Index, LONG Total) + ERR xmlRemoveTag(OBJECTPTR Object, LONG Index, LONG Total) Reference to the tag that will be removed. The total number of sibling (neighbouring) tags that should also be deleted. A value of one or less will remove only the indicated tag and its children. The total may exceed the number of tags actually available, in which case all tags up to the end of the branch will be affected. @@ -330,7 +309,7 @@ RemoveXPath Removes tag(s) from the XML structure, using an xpath lookup. - ERROR xmlRemoveXPath(OBJECTPTR Object, CSTRING XPath, LONG Limit) + ERR xmlRemoveXPath(OBJECTPTR Object, CSTRING XPath, LONG Limit) An XML path string. The maximum number of matching tags that should be deleted. A value of one or less will remove only the indicated tag and its children. The total may exceed the number of tags actually available, in which case all matching tags up to the end of the tree will be affected. @@ -348,10 +327,31 @@
    + + Serialise + Serialise part of the XML tree to an XML string. + ERR xmlSerialise(OBJECTPTR Object, LONG Index, XMF Flags, STRING * Result) + + Index to a source tag for which serialisation will start. Set to zero to serialise the entire tree. + Use INCLUDE_SIBLINGS to include siblings of the tag found at Index. + The resulting string is returned in this parameter. + + +

    The Serialise method will serialise all or part of the XML data tree to a string.

    +

    The string will be allocated as a memory block and stored in the Result parameter. It must be freed once the data is no longer required.

    +
    + + The XML string was retrieved. + Invalid arguments passed to function. + No information has been loaded into the XML object. + Failed to allocate an XML string for the result. + +
    + SetAttrib Adds, updates and removes XML attributes. - ERROR xmlSetAttrib(OBJECTPTR Object, LONG Index, LONG Attrib, CSTRING Name, CSTRING Value) + ERR xmlSetAttrib(OBJECTPTR Object, LONG Index, LONG Attrib, CSTRING Name, CSTRING Value) Identifies the tag that is to be updated. Either the index number of the attribute that is to be updated, or set to XMS_NEW, XMS_UPDATE or XMS_UPDATE_ONLY. @@ -376,7 +376,7 @@ Sort Sorts XML tags to your specifications. - ERROR xmlSort(OBJECTPTR Object, CSTRING XPath, CSTRING Sort, XSF Flags) + ERR xmlSort(OBJECTPTR Object, CSTRING XPath, CSTRING Sort, XSF Flags) Sort everything under the specified tag, or NULL to sort the entire top level. Pointer to a sorting instruction string. @@ -491,14 +491,14 @@ By default the XML parser will trim whitespace (such as return codes, spaces and tabs) found in the XML content between tags. Setting this flag turns off this feature, allowing all whitespace to be included. By default, comments are stripped from all XML input. This flag ensures that they are retained. Include siblings when building an XML string (GetXMLString only) - Indent the output of XML tags to improve readability. + Indent the output of serialised XML to improve readability. Prevents removal of tags from the XML tree. This specifically affects the RemoveTag and RemoveXPath methods. Print extra log messages. Creates an empty XML object on initialisation - if the Path field has been set, the source file will not be loaded. Turns off escape code conversion. Entity references in the DTD will be parsed automatically. Automatically parse HTML escape codes. - Indent the output of XML tags to improve readability. + Indent the output of serialised XML to improve readability. Do not echo CDATA sections. Note that this option is used as a parameter, not an object flag. Strip all content from incoming XML data. XML headers found in the source data will not be included in the parsed results. diff --git a/docs/xml/modules/core.xml b/docs/xml/modules/core.xml index b8fa56689..8d5580048 100644 --- a/docs/xml/modules/core.xml +++ b/docs/xml/modules/core.xml @@ -5,7 +5,7 @@ Core module - Paul Manias 1996-2023 + Paul Manias 1996-2024 CompressedStream Compression @@ -36,7 +36,7 @@ AccessMemory Memory Grants access to memory blocks by identifier. - ERROR AccessMemory(MEMORYID Memory, MEM Flags, LONG MilliSeconds, APTR * Result) + ERR AccessMemory(MEMORYID Memory, MEM Flags, LONG MilliSeconds, APTR * Result) The ID of the memory block that you want to access. Set to READ, WRITE or READ_WRITE according to requirements. @@ -47,7 +47,7 @@

    Call AccessMemory() to resolve a memory ID to its address and acquire a lock so that it is inaccessible to other threads.

    Memory blocks should never be locked for extended periods of time. Ensure that all locks are matched with a call to ReleaseMemory within the same code block.

    - + Operation successful. Invalid arguments passed to function. Function timed-out before successful completion. @@ -61,7 +61,7 @@ AccessObject Objects Grants exclusive access to objects via unique ID. - ERROR AccessObject(OBJECTID Object, LONG MilliSeconds, OBJECTPTR * Result) + ERR AccessObject(OBJECTID Object, LONG MilliSeconds, OBJECTPTR * Result) The unique ID of the target object. The limit in milliseconds before a timeout occurs. The maximum limit is 60000, and 100 is recommended. @@ -69,7 +69,7 @@

    This function resolves an object ID to its address and acquires a lock on the object so that other threads cannot use it simultaneously.

    -

    If the object is already locked, it will wait until the object becomes available. This must occur within the amount of time specified in the Milliseconds parameter. If the time expires, the function will return with an ERR_TimeOut error code. If successful, ERR_Okay is returned and a reference to the object's address is stored in the Result variable.

    +

    If the object is already locked, it will wait until the object becomes available. This must occur within the amount of time specified in the Milliseconds parameter. If the time expires, the function will return with an ERR::TimeOut error code. If successful, ERR::Okay is returned and a reference to the object's address is stored in the Result variable.

    It is crucial that calls to AccessObject() are followed with a call to ReleaseObject once the lock is no longer required. Calls to AccessObject() will also nest, so they must be paired with ReleaseObject correctly.

    It is recommended that C++ developers use the ScopedObjectLock class to acquire object locks rather than making direct calls to AccessObject(). The following example illustrates lock acquisition within a 1 second time limit:

    {
    @@ -81,7 +81,7 @@
     
     
    - + Operation successful. Function timed-out before successful completion. Part of the system is unreachable due to a persistent lock. @@ -94,7 +94,7 @@ Action Objects This function is responsible for executing action routines. - ERROR Action(LONG Action, OBJECTPTR Object, APTR Parameters) + ERR Action(LONG Action, OBJECTPTR Object, APTR Parameters) An action or method ID must be specified here (e.g. AC_Query). A pointer to the object that is going to perform the action. @@ -115,10 +115,10 @@ 2b. Window->move(30, 15, 0);
    -

    If the class of an object does not support the action ID, an error code of ERR_NoSupport is returned. To test an object to see if its class supports an action, use the CheckAction function.

    +

    If the class of an object does not support the action ID, an error code of ERR::NoSupport is returned. To test an object to see if its class supports an action, use the CheckAction function.

    In circumstances where an object ID is known without its pointer, the use of ActionMsg or QueueAction may be desirable to avoid acquiring an object lock.

    - + Operation successful. The object does not support this operation. Illegal action ID (number outside of valid range). @@ -169,7 +169,7 @@ struct FunctionField argsResize[] = { ActionMsg Objects Execute an action or method by way of object ID. - ERROR ActionMsg(LONG Action, OBJECTID Object, APTR Args) + ERR ActionMsg(LONG Action, OBJECTID Object, APTR Args) The ID of the action or method to be executed. The target object. @@ -178,7 +178,7 @@ struct FunctionField argsResize[] = {

    Use ActionMsg() to execute an action when only the object ID is known.

    - + Operation successful. General failure. A specified number is outside of the valid range. @@ -190,7 +190,7 @@ struct FunctionField argsResize[] = { ActionThread Objects Execute an action in parallel, via a separate thread. - ERROR ActionThread(LONG Action, OBJECTPTR Object, APTR Args, FUNCTION * Callback, LONG Key) + ERR ActionThread(LONG Action, OBJECTPTR Object, APTR Args, FUNCTION * Callback, LONG Key) An action or method ID must be specified here. A pointer to the object that is going to perform the action. @@ -200,12 +200,12 @@ struct FunctionField argsResize[] = {

    This function follows the same principles of execution as the Action() function, with the difference of executing the action in parallel via a dynamically allocated thread. Please refer to the Action function for general information on action execution.

    -

    To receive feedback of the action's completion, use the Callback parameter and supply a function. The function prototype for the callback routine is callback(ACTIONID ActionID, OBJECTPTR Object, ERROR Error, LONG Key)

    +

    To receive feedback of the action's completion, use the Callback parameter and supply a function. The function prototype for the callback routine is callback(ACTIONID ActionID, OBJECTPTR Object, ERR Error, LONG Key)

    It is crucial that the target object is not destroyed while the thread is executing. Use the Callback routine to receive notification of the thread's completion and then free the object if desired. The callback will be processed in the next call to ProcessMessages, so as to maintain an orderly execution process within the application.

    The 'Error' parameter in the callback reflects the error code returned by the action after it has been called. Note that if ActionThread() fails, the callback will never be executed because the thread attempt will have been aborted.

    Please note that there is some overhead involved when safely initialising and executing a new thread. This function is at its most effective when used to perform lengthy processes such as the loading and parsing of data.

    - + Operation successful. Error in Init()ialising an object. Illegal method ID (number outside of valid range). @@ -219,7 +219,7 @@ struct FunctionField argsResize[] = { AddInfoTag Files Adds new tags to FileInfo structures. - ERROR AddInfoTag(struct FileInfo * Info, CSTRING Name, CSTRING Value) + ERR AddInfoTag(struct FileInfo * Info, CSTRING Name, CSTRING Value) Pointer to a valid FileInfo structure. The name of the tag. @@ -228,7 +228,7 @@ struct FunctionField argsResize[] = {

    This function adds file tags to FileInfo structures. It is intended for use by the FileSystem module and related drivers only. Tags allow extended attributes to be associated with a file, for example the number of seconds of audio in an MP3 file.

    - + Operation successful. Function call missing argument value(s) @@ -238,7 +238,7 @@ struct FunctionField argsResize[] = { AddMsgHandler Messages Adds a new message handler for processing incoming messages. - ERROR AddMsgHandler(APTR Custom, LONG MsgType, FUNCTION * Routine, struct MsgHandler ** Handle) + ERR AddMsgHandler(APTR Custom, LONG MsgType, FUNCTION * Routine, struct MsgHandler ** Handle) A custom pointer that will be passed to the message handler when messages are received. The message type that the handler wishes to intercept. If zero, all incoming messages are passed to the handler. @@ -249,11 +249,11 @@ struct FunctionField argsResize[] = {

    This function allows handlers to be added for the interception of incoming messages. Message handling works as follows:

    During a call to ProcessMessages, each incoming message will be scanned to determine if a message handler is able to process that message. All handlers that accept the message type will be called with a copy of the message structure and any additional data. The message is then removed from the message queue.

    When calling AddMsgHandler(), you can provide an optional Custom pointer that will have meaning to the handler. The MsgType acts as a filter so that only messages with the same type identifier will be passed to the handler. The Routine parameter must point to the function handler, which will follow this definition:

    -
    ERROR handler(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize)
    -

    The handler must return ERR_Okay if the message was handled. This means that the message will not be passed to message handlers that are yet to receive the message. Throw ERR_NothingDone if the message has been ignored or ERR_Continue if the message was processed but may be analysed by other handlers. Throw ERR_Terminate to break the current ProcessMessages() loop. When using Fluid, this is best achieved by writing check(errorcode) in the handler.

    +
    ERR handler(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize)
    +

    The handler must return ERR::Okay if the message was handled. This means that the message will not be passed to message handlers that are yet to receive the message. Throw ERR::NothingDone if the message has been ignored or ERR::Continue if the message was processed but may be analysed by other handlers. Throw ERR::Terminate to break the current ProcessMessages() loop. When using Fluid, this is best achieved by writing check(errorcode) in the handler.

    The handler will be identified by a unique pointer returned in the Handle parameter. This handle will be garbage collected or can be passed to FreeResource once it is no longer required.

    - + Operation successful. A call to AllocMemory() failed to create a new memory block. Function call missing argument value(s) @@ -280,7 +280,7 @@ struct FunctionField argsResize[] = { AllocMemory Memory Allocates a new memory block on the heap. - ERROR AllocMemory(LONG Size, MEM Flags, APTR * Address, MEMORYID * ID) + ERR AllocMemory(LONG Size, MEM Flags, APTR * Address, MEMORYID * ID) The size of the memory block. Optional flags. @@ -302,7 +302,7 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) {

    If the client retrieves both the ID and Address pointer, an internal call will be made to AccessMemory to lock the memory block. This means that before freeing the memory block the client must call ReleaseMemory to unlock it. Blocks that are persistently locked will remain in memory until the process is terminated.

    Memory that is allocated through AllocMemory() is automatically cleared with zero-byte values. When allocating large blocks it may be wise to turn off this feature, achieved by setting the MEM::NO_CLEAR flag.

    - + Operation successful. General failure. Invalid arguments passed to function. @@ -330,7 +330,7 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) { AnalysePath Files Analyses paths to determine their type (file, folder or volume). - ERROR AnalysePath(CSTRING Path, LOC * Type) + ERR AnalysePath(CSTRING Path, LOC * Type) The path to analyse. The result will be stored in the LONG variable referred to by this argument. The return types are DIRECTORY, FILE and VOLUME. You can set this argument to NULL if you are only interested in checking if the file exists. @@ -342,7 +342,7 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) {

    To check if a volume name is valid, call ResolvePath first and then pass the resulting path to this function.

    If the queried path does not exist, a fail code is returned. This behaviour makes the AnalysePath() function a good candidate for testing the validity of a path string.

    - + Operation successful. Resource does not exist. Function call missing argument value(s) @@ -353,7 +353,7 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) { Base64Decode Strings Decodes a base 64 string to its binary form. - ERROR Base64Decode(struct pfBase64Decode * State, CSTRING Input, LONG InputSize, APTR Output, LONG * Written) + ERR Base64Decode(struct pfBase64Decode * State, CSTRING Input, LONG InputSize, APTR Output, LONG * Written) Pointer to an pfBase64Decode structure, initialised to zero. A base 64 input string. The pointer will be updated when the function returns. @@ -365,7 +365,7 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) {

    This function will decode a base 64 string to its binary form. It is designed to support streaming from the source Input and gracefully handles buffer over-runs by forwarding data to the next call.

    To use this function effectively, call it repeatedly in a loop until all of the input is exhausted.

    - + Operation successful. Invalid arguments passed to function. Function call missing argument value(s) @@ -395,7 +395,7 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) { BroadcastEvent Events Broadcast an event to all event listeners in the system. - ERROR BroadcastEvent(APTR Event, LONG EventSize) + ERR BroadcastEvent(APTR Event, LONG EventSize) Pointer to an event structure. The size of the Event structure, in bytes. @@ -409,7 +409,7 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) {

    This document does not describe the available system events. For more information about them, please refer to the System Events Reference manual.

    - + Operation successful. Function call missing argument value(s) @@ -419,7 +419,7 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) { CheckAction Objects Checks objects to see whether or not they support certain actions. - ERROR CheckAction(OBJECTPTR Object, LONG Action) + ERR CheckAction(OBJECTPTR Object, LONG Action) The target object. A registered action ID. @@ -431,7 +431,7 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) { }
    - + Operation successful. The result is false. The object has lost its class reference. @@ -443,14 +443,14 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) { CheckMemoryExists Memory Checks if a memory block still exists. - ERROR CheckMemoryExists(MEMORYID ID) + ERR CheckMemoryExists(MEMORYID ID) The ID of the memory block that will be checked.

    Use CheckMemoryExists() to confirm if a specific memory block still exists by referencing its ID.

    - + Operation successful. The result is false. @@ -460,14 +460,14 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) { CheckObjectExists Objects Checks if a particular object is still available in the system. - ERROR CheckObjectExists(OBJECTID Object) + ERR CheckObjectExists(OBJECTID Object) The object identity to verify.

    The CheckObjectExists() function verifies the presence of any object created by NewObject.

    - + Operation successful. The result is false. Failed to lock a required resource. @@ -478,16 +478,16 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) { CompareFilePaths Files Checks if two file paths refer to the same physical file. - ERROR CompareFilePaths(CSTRING PathA, CSTRING PathB) + ERR CompareFilePaths(CSTRING PathA, CSTRING PathB) File location 1. File location 2. -

    This function will test two file paths, checking if they refer to the same file in a storage device. It uses a string comparison on the resolved path names, then attempts a second test based on an in-depth analysis of file attributes if the string comparison fails. In the event of a match, ERR_Okay is returned. All other error codes indicate a mis-match or internal failure.

    +

    This function will test two file paths, checking if they refer to the same file in a storage device. It uses a string comparison on the resolved path names, then attempts a second test based on an in-depth analysis of file attributes if the string comparison fails. In the event of a match, ERR::Okay is returned. All other error codes indicate a mis-match or internal failure.

    The targeted paths do not have to refer to an existing file or folder in order to match (i.e. match on string comparison succeeds).

    - + Operation successful. The result is false. Function call missing argument value(s) @@ -498,7 +498,7 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) { CopyFile Files Makes copies of folders and files. - ERROR CopyFile(CSTRING Source, CSTRING Dest, FUNCTION * Callback) + ERR CopyFile(CSTRING Source, CSTRING Dest, FUNCTION * Callback) The source location. The destination location. @@ -516,9 +516,9 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) {

    The Callback parameter can be set with a function that matches this prototype:

    LONG Callback(struct FileFeedback *)

    -

    For each file that is processed during the copy operation, a FileFeedback structure is passed that describes the source file and its target. The callback must return a constant value that can potentially affect file processing. Valid values are FFR::Okay (copy the file), FFR::Skip (do not copy the file) and FFR::Abort (abort the process completely and return ERR_Cancelled as an error code).

    +

    For each file that is processed during the copy operation, a FileFeedback structure is passed that describes the source file and its target. The callback must return a constant value that can potentially affect file processing. Valid values are FFR::Okay (copy the file), FFR::Skip (do not copy the file) and FFR::Abort (abort the process completely and return ERR::Cancelled as an error code).

    - + Operation successful. General failure. Invalid arguments passed to function. @@ -529,7 +529,7 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) { CreateFolder Files Makes new folders. - ERROR CreateFolder(CSTRING Path, PERMIT Permissions) + ERR CreateFolder(CSTRING Path, PERMIT Permissions) The location of the folder. Security permissions to apply to the created Dir(s). Set to NULL if only the current user should have access. @@ -538,7 +538,7 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) {

    This function creates new folders. You are required to specify the full path of the new folder. Standard permission flags can be passed to determine the new permissions to set against the newly created Dir(s). If no permission flags are passed, only the current user will have access to the new folder (assuming that the file system supports security settings on the given media). This function will create multiple folders if the complete path does not exist at the time of the call.

    On Unix systems you can define the owner and group ID's for the new folder by calling the SetDefaultPermissions function prior to CreateFolder().

    - + Operation successful. General failure. This request is not supported. @@ -551,17 +551,17 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) { CreateLink Files Creates symbolic links on Unix file systems. - ERROR CreateLink(CSTRING From, CSTRING To) + ERR CreateLink(CSTRING From, CSTRING To) The symbolic link will be created at the location specified here. The file that you are linking to is specified here.

    Use the CreateLink() function to create symbolic links on Unix file systems. The link connects a new file created at From to an existing file referenced at To. The To link is allowed to be relative to the From location - for instance, you can link documents:myfiles/newlink.txt to ../readme.txt or folder/readme.txt. The .. path component must be used when making references to parent folders.

    -

    The permission flags for the link are inherited from the file that you are linking to. If the file location referenced at From already exists as a file or folder, the function will fail with an ERR_FileExists error code.

    +

    The permission flags for the link are inherited from the file that you are linking to. If the file location referenced at From already exists as a file or folder, the function will fail with an ERR::FileExists error code.

    This function does not automatically create folders in circumstances where new folders are required to complete the From link. You will need to call CreateFolder to ensure that the necessary paths exist beforehand. If the file referenced at To does not exist, the link will be created without error, but any attempts to open the link will fail until the target file or folder exists.

    - + Operation successful. This request is not supported. General memory error. @@ -602,7 +602,7 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) { DeleteFile Files Deletes files and folders. - ERROR DeleteFile(CSTRING Path, FUNCTION * Callback) + ERR DeleteFile(CSTRING Path, FUNCTION * Callback) String referring to the file or folder to be deleted. Folders must be denoted with a trailing slash. Optional callback for receiving feedback during the operation. @@ -613,9 +613,9 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) {

    The Callback parameter can be set with a function that matches this prototype:

    LONG Callback(struct FileFeedback *)

    -

    Prior to the deletion of any file, a FileFeedback structure is passed that describes the file's location. The callback must return a constant value that can potentially affect file processing. Valid values are FFR::Okay (delete the file), FFR::Skip (do not delete the file) and FFR::Abort (abort the process completely and return ERR_Cancelled as an error code).

    +

    Prior to the deletion of any file, a FileFeedback structure is passed that describes the file's location. The callback must return a constant value that can potentially affect file processing. Valid values are FFR::Okay (delete the file), FFR::Skip (do not delete the file) and FFR::Abort (abort the process completely and return ERR::Cancelled as an error code).

    - + Operation successful. File error, e.g. file not found. File not found. @@ -628,14 +628,14 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) { DeleteVolume Files Deletes volumes from the system. - ERROR DeleteVolume(CSTRING Name) + ERR DeleteVolume(CSTRING Name) The name of the volume.

    This function deletes volume names from the system. Once a volume is deleted, any further references to it will result in errors unless the volume is recreated.

    - + Operation successful. Failed to lock a required resource. General security violation. @@ -685,7 +685,7 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) {

    The FindField() function checks if an object supports a specified field by scanning its class descriptor for a FieldID. If a matching field is declared, its descriptor is returned. For example:

    -
    if (auto field = FindField(Screen, FID_Width, NULL)) {
    +
    if (auto field = FindField(Display, FID_Width, NULL)) {
        log.msg("The field name is \"%s\".", field->Name);
     }
     
    @@ -699,7 +699,7 @@ if (!AllocMemory(1000, MEM::DATA, &address, NULL)) { FindObject Objects Searches for objects by name. - ERROR FindObject(CSTRING Name, CLASSID ClassID, FOF Flags, OBJECTID * ObjectID) + ERR FindObject(CSTRING Name, CLASSID ClassID, FOF Flags, OBJECTID * ObjectID) The name of an object to search for. Optional. Set to a class ID to filter the results down to a specific class type. @@ -714,7 +714,7 @@ FindObject("SystemPointer", ID_POINTER, 0, &id);

    If FindObject() cannot find any matching objects then it will return an error code.

    - + Operation successful. A search routine in this function failed. Invalid arguments passed to function. @@ -728,7 +728,7 @@ FindObject("SystemPointer", ID_POINTER, 0, &id); FreeResource Memory Frees resources originating from AllocMemory(). - ERROR FreeResource(MEMORYID ID) + ERR FreeResource(MEMORYID ID) The unique ID of the memory block. @@ -737,7 +737,7 @@ FindObject("SystemPointer", ID_POINTER, 0, &id);

    In some circumstances the termination of the block will not take place immediately. If the block is locked then it will be marked for deletion and not be collected until the lock count reaches zero.

    Crash protection measures are built-in. If the memory header or tail is missing from the block, it is assumed that code has over-written the memory boundaries. All caught errors are reported to the application log and warrant priority attention.

    - + Operation successful. There is an error in the provided data. Memory block does not exist. @@ -792,9 +792,9 @@ FindObject("SystemPointer", ID_POINTER, 0, &id); GetErrorMsg Logging Translates error codes into human readable strings. - CSTRING GetErrorMsg(ERROR Error) + CSTRING GetErrorMsg(ERR Error) - The error code to lookup. + The error code to lookup.

    The GetErrorMsg() function converts error codes into human readable strings. If the Code is invalid, a string of "Unknown error code" is returned.

    @@ -825,7 +825,7 @@ FindObject("SystemPointer", ID_POINTER, 0, &id); GetField Fields Retrieves single field values from objects. - ERROR GetField(OBJECTPTR Object, FIELD Field, APTR Result) + ERR GetField(OBJECTPTR Object, FIELD Field, APTR Result) Pointer to an object. The ID of the field to read, OR'd with a type indicator. @@ -848,7 +848,7 @@ GetField(Object, FID_Y|TLONG, &y); A 32-bit pointer that refers to a string.
    - + Operation successful. Invalid arguments passed to function. Access to a field was denied. @@ -860,7 +860,7 @@ GetField(Object, FID_Y|TLONG, &y); GetFieldArray Fields Retrieves array field values from objects. - ERROR GetFieldArray(OBJECTPTR Object, FIELD Field, APTR * Result, LONG * Elements) + ERR GetFieldArray(OBJECTPTR Object, FIELD Field, APTR * Result, LONG * Elements) Pointer to an object. The ID of the field that will be read. @@ -872,7 +872,7 @@ GetField(Object, FID_Y|TLONG, &y);

    This function returns the array as-is with no provision for type conversion. If the array is null terminated, it is standard practice not to count the null terminator in the total returned by Elements.

    To achieve a minimum level of type safety, the anticipated type of array values can be specified by OR'ing a field type with the field identifier, e.g. TLONG or TSTR. If no type is incorporated then a check will not be performed.

    - + Operation successful. Access to a field was denied. The specified field is not supported by the object's class. @@ -885,7 +885,7 @@ GetField(Object, FID_Y|TLONG, &y); GetFieldVariable Fields Retrieves field values by converting them into strings. - ERROR GetFieldVariable(OBJECTPTR Object, CSTRING Field, STRING Buffer, LONG Size) + ERR GetFieldVariable(OBJECTPTR Object, CSTRING Field, STRING Buffer, LONG Size) Pointer to an object. The name of the field that is to be retrieved. @@ -900,7 +900,7 @@ GetField(Object, FID_Y|TLONG, &y);

    If the field name refers to an array, it is possible to index specific values within that array by specifying a dot after the field name, then the index number to lookup.

    To check if a string is defined (rather than retrieving the entire string content which can be time consuming), prefix the Field name with a question mark. A value of 1 will be returned in the Buffer if the string has a minimum length of 1 character, otherwise a value of 0 is returned in the Buffer.

    - + Operation successful. Invalid arguments passed to function. Access to a field was denied. @@ -913,7 +913,7 @@ GetField(Object, FID_Y|TLONG, &y); GetMessage Messages Reads messages from message queues. - ERROR GetMessage(LONG Type, MSF Flags, APTR Buffer, LONG Size) + ERR GetMessage(LONG Type, MSF Flags, APTR Buffer, LONG Size) Filter down to this message type or set to zero to receive the next message on the queue. This argument is reserved for future use. Set it to zero. @@ -921,11 +921,11 @@ GetField(Object, FID_Y|TLONG, &y); The byte-size of the buffer that you have supplied. -

    The GetMessage() function is used to read messages that have been stored in the local message queue. You can use this function to read the next immediate message stored on the queue, or the first message on the queue that matches a particular Type. It is also possible to call this function in a loop to clear out all messages, until an error code other than ERR_Okay is returned.

    +

    The GetMessage() function is used to read messages that have been stored in the local message queue. You can use this function to read the next immediate message stored on the queue, or the first message on the queue that matches a particular Type. It is also possible to call this function in a loop to clear out all messages, until an error code other than ERR::Okay is returned.

    Messages will often (although not always) carry data that is relevant to the message type. To retrieve this data you need to supply a buffer, preferably one that is large enough to receive all the data that you expect from your messages. If the buffer is too small, the message data will be cut off to fit inside the buffer.

    Message data is written to the supplied buffer with a Message structure, which is immediately followed up with the actual message data.

    - + Operation successful. A search routine in this function failed. Invalid arguments passed to function. @@ -992,7 +992,7 @@ GetField(Object, FID_Y|TLONG, &y); IdentifyFile Files Analyse a file and identify a class that can process it. - ERROR IdentifyFile(CSTRING Path, CLASSID * Class, CLASSID * SubClass) + ERR IdentifyFile(CSTRING Path, CLASSID * Class, CLASSID * SubClass) The location of the object data. Must refer to a CLASSID variable that will store the resulting class ID. @@ -1001,9 +1001,9 @@ GetField(Object, FID_Y|TLONG, &y);

    This function examines the relationship between file data and installed classes. It allows for instance, a JPEG file to be identified as a datatype of the Picture class, or an MP3 file to be identified as a datatype of the Sound class.

    The method involves analysing the Path's file extension and comparing it to the supported extensions of all available classes. If a class supports the file extension then the ID of that class will be returned. If the file extension is not listed in the class dictionary or if it is listed more than once, the first 80 bytes of the file's data will be loaded and checked against classes that can match against file header information. If a match is found, the ID of the matching class will be returned.

    -

    This function returns an error code of ERR_Search in the event that a suitable class is not available to match against the given file.

    +

    This function returns an error code of ERR::Search in the event that a suitable class is not available to match against the given file.

    - + Operation successful. A search routine in this function failed. File not found. @@ -1016,16 +1016,16 @@ GetField(Object, FID_Y|TLONG, &y); InitObject Objects Initialises an object so that it is ready for use. - ERROR InitObject(OBJECTPTR Object) + ERR InitObject(OBJECTPTR Object) The object to initialise.

    This function initialises objects so that they can be used for their intended purpose. The process of initialisation is compulsory, and a client may not use any other actions on an object until it has been initialised. Exceptions to this rule only apply to the GetVar() and SetVar() actions.

    If the initialisation of an object fails due to a support problem (for example, if a PNG Picture object attempts to load a JPEG file), the initialiser will search for a sub-class that can handle the data. If a sub-class that can provide ample support exists, a partial transfer of ownership will occur and the object's management will be shared between both the base class and the sub-class.

    -

    If an object does not support the data or its configuration, an error code of ERR_NoSupport will be returned. Other appropriate error codes can be returned if initialisation fails.

    +

    If an object does not support the data or its configuration, an error code of ERR::NoSupport will be returned. Other appropriate error codes can be returned if initialisation fails.

    - + Operation successful. The object has lost its class reference. The object structure is corrupt or has not been initialised. @@ -1036,7 +1036,7 @@ GetField(Object, FID_Y|TLONG, &y); ListChildren Objects Returns a list of all children belonging to an object. - ERROR ListChildren(OBJECTID Object, pf::vector<ChildEntry> * List) + ERR ListChildren(OBJECTID Object, pf::vector<ChildEntry> * List) An object to query. Must refer to an array of ChildEntry structures. @@ -1045,7 +1045,7 @@ GetField(Object, FID_Y|TLONG, &y);

    The ListChildren() function returns a list of all children belonging to an object. The client must provide an empty vector of ChildEntry structures to host the results, which include unique object ID's and their class identifiers.

    Note that any child objects marked with the INTEGRAL flag will be excluded because they are private members of the targeted object.

    - + Operation successful. Invalid arguments passed to function. Function call missing argument value(s) @@ -1056,7 +1056,7 @@ GetField(Object, FID_Y|TLONG, &y); LoadFile Files Loads files into a local cache for fast file processing. - ERROR LoadFile(CSTRING Path, LDF Flags, struct CacheFile ** Cache) + ERR LoadFile(CSTRING Path, LDF Flags, struct CacheFile ** Cache) The location of the file to be cached. Optional flags are specified here. @@ -1068,7 +1068,7 @@ GetField(Object, FID_Y|TLONG, &y);

    File content will be loaded into a readable memory buffer that is referenced by the Data field of the CacheFile structure. A hidden null byte is appended at the end of the buffer to assist the processing of text files. Other pieces of information about the file can be derived from the CacheFile meta data.

    Calls to LoadFile() must be matched with a call to UnloadFile to decrement the cache counter. When the counter returns to zero, the file can be unloaded from the cache during the next resource collection phase.

    - + Operation successful. A search routine in this function failed. A call to AllocMemory() failed to create a new memory block. @@ -1080,7 +1080,7 @@ GetField(Object, FID_Y|TLONG, &y); LockObject Objects Lock an object to prevent contention between threads. - ERROR LockObject(OBJECTPTR Object, LONG MilliSeconds) + ERR LockObject(OBJECTPTR Object, LONG MilliSeconds) The address of the object to lock. The total number of milliseconds to wait before giving up. If -1, the function will wait indefinitely. @@ -1090,7 +1090,7 @@ GetField(Object, FID_Y|TLONG, &y);

    Be aware that while this function is faster than AccessObject, it is unsafe if other threads could terminate the object without a suitable barrier in place.

    If it is guaranteed that an object is not being shared between threads, object locking is unnecessary.

    - + Operation successful. Function timed-out before successful completion. A resource cannot be accessed as it is marked for deletion. @@ -1103,7 +1103,7 @@ GetField(Object, FID_Y|TLONG, &y); MemoryIDInfo Memory Returns information on memory ID's. - ERROR MemoryIDInfo(MEMORYID ID, struct MemInfo * MemInfo, LONG Size) + ERR MemoryIDInfo(MEMORYID ID, struct MemInfo * MemInfo, LONG Size) Pointer to a valid memory ID. Pointer to a MemInfo structure. @@ -1118,7 +1118,7 @@ if (!MemoryIDInfo(memid, &info)) {

    If the call fails, the MemInfo structure's fields will be driven to NULL and an error code is returned.

    - + Operation successful. Invalid arguments passed to function. Memory block does not exist. @@ -1131,7 +1131,7 @@ if (!MemoryIDInfo(memid, &info)) { MemoryPtrInfo Memory Returns information on memory addresses. - ERROR MemoryPtrInfo(APTR Address, struct MemInfo * MemInfo, LONG Size) + ERR MemoryPtrInfo(APTR Address, struct MemInfo * MemInfo, LONG Size) Pointer to a valid memory area. Pointer to a MemInfo structure to be filled out. @@ -1147,7 +1147,7 @@ if (!MemoryPtrInfo(ptr, &info)) {

    If the call to MemoryPtrInfo() fails then the MemInfo structure's fields will be driven to NULL and an error code will be returned.

    Please note that referencing by a pointer requires a slow reverse-lookup to be employed in this function's search routine. We recommend that calls to this function are avoided unless circumstances absolutely require it.

    - + Operation successful. Memory block does not exist. Function call missing argument value(s) @@ -1158,7 +1158,7 @@ if (!MemoryPtrInfo(ptr, &info)) { MoveFile Files Moves folders and files to new locations. - ERROR MoveFile(CSTRING Source, CSTRING Dest, FUNCTION * Callback) + ERR MoveFile(CSTRING Source, CSTRING Dest, FUNCTION * Callback) The source path. The destination path. @@ -1179,9 +1179,9 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents

    The Callback parameter can be set with a function that matches this prototype:

    LONG Callback(struct FileFeedback *)

    -

    For each file that is processed during the move operation, a FileFeedback structure is passed that describes the source file and its target. The callback must return a constant value that can potentially affect file processing. Valid values are FFR::Okay (move the file), FFR::Skip (do not move the file) and FFR::Abort (abort the process completely and return ERR_Cancelled as an error code).

    +

    For each file that is processed during the move operation, a FileFeedback structure is passed that describes the source file and its target. The callback must return a constant value that can potentially affect file processing. Valid values are FFR::Okay (move the file), FFR::Skip (do not move the file) and FFR::Abort (abort the process completely and return ERR::Cancelled as an error code).

    - + Operation successful. General failure. Function call missing argument value(s) @@ -1192,7 +1192,7 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents NewObject Objects Creates new objects. - ERROR NewObject(LARGE ClassID, NF Flags, OBJECTPTR * Object) + ERR NewObject(LARGE ClassID, NF Flags, OBJECTPTR * Object) A class ID from "system/register.h" or generated by ResolveClassName. Optional flags. @@ -1204,7 +1204,7 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents

    A pointer to the new object will be returned in the Object parameter. By default, object allocations are context sensitive and will be collected when their owner is terminated. It is possible to track an object to a different owner by using the SetOwner function.

    To destroy an object, call FreeResource.

    - + Operation successful. General failure. The class could not be found in the system. @@ -1217,16 +1217,16 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents NotifySubscribers Objects Used to send notification messages to action subscribers. - void NotifySubscribers(OBJECTPTR Object, LONG Action, APTR Args, ERROR Error) + void NotifySubscribers(OBJECTPTR Object, LONG Action, APTR Args, ERR Error) Pointer to the object that is to receive the notification message. The action ID for notification. Pointer to an action parameter structure that is relevant to the ActionID. - The error code that is associated with the action result. + The error code that is associated with the action result.

    This function can be used by classes that need total control over notification management. The system default for notifying action subscribers is to call them immediately after an action has taken place. This may be inconvenient if the code for an action needs to execute code post-notification. Using NotifySubscribers() allows these scenarios to be addressed. Another possible use is for customised parameter values to be sent to subscribers instead of the original values.

    -

    NOTE: Calling NotifySubscribers() does nothing to prevent the core from sending out an action notification as it normally would, thus causing duplication. To prevent this the client must logical-or the return code of the action function with ERF_Notified, e.g. ERR_Okay|ERF_Notified.

    +

    NOTE: Calling NotifySubscribers() does nothing to prevent the core from sending out an action notification as it normally would, thus causing duplication. To prevent this the client must logical-or the return code of the action function with ERR::Notified, e.g. ERR::Okay|ERR::Notified.

    @@ -1234,7 +1234,7 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents OpenDir Files Opens a folder for content scanning. - ERROR OpenDir(CSTRING Path, RDF Flags, struct DirInfo ** Info) + ERR OpenDir(CSTRING Path, RDF Flags, struct DirInfo ** Info) The folder location to be scanned. Using an empty string will scan for volume names. Optional flags. @@ -1244,7 +1244,7 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents

    The OpenDir() function is used to open a folder for scanning via the ScanDir function. If the provided Path can be accessed, a DirInfo structure will be returned in the Info parameter, which will need to be passed to ScanDir. Once the scanning process is complete, call the FreeResource function.

    When opening a folder, it is necessary to indicate the type of files that are of interest. If no flags are defined, the scanner will return file and folder names only. Only a subset of the available RDF flags may be used, namely SIZE, DATE, PERMISSIONS, FILE, FOLDER, QUALIFY, TAGS.

    - + Operation successful. The folder is empty. Invalid arguments passed to function. @@ -1268,7 +1268,7 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents ProcessMessages Messages Processes system messages that are queued in the task's message buffer. - ERROR ProcessMessages(PMF Flags, LONG TimeOut) + ERR ProcessMessages(PMF Flags, LONG TimeOut) Optional flags are specified here (clients should set a value of zero). A TimeOut value, measured in milliseconds. If zero, the function will return as soon as all messages on the queue are processed. If less than zero, the function does not return until a request for termination is received or a user message requires processing. @@ -1276,10 +1276,10 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents

    The ProcessMessages() function is used to process the task's message queue. Messages are dispatched to message handlers in the order in which they arrived and the queue is emptied so that space is available for more messages.

    Responding to incoming messages is a vital process - the queue is the standard means of communication between your task and the rest of the system and other tasks within it. Failing to call the ProcessMessages() function on a regular basis may cause a back-log of messages to be generated, as well as causing problems with areas such as the graphical interface. If an area of your program is likely to loop continuously for a measurable period of time without returning, consider calling ProcessMessages() at a rate of 50 times per second to ensure that incoming messages are processed.

    -

    User messages that are on the queue are passed to message handlers. If no message handler exists to interpret the message, then it is removed from the queue without being processed. Message handlers are added with the AddMsgHandler function. If a message handler returns the error code ERR_Terminate, then ProcessMessages() will stop processing the queue and returns immediately with ERR_Okay.

    -

    If a message with a MSGID_QUIT ID is found on the queue, then the function returns immediately with the error code ERR_Terminate. The program must respond to the terminate request by exiting immediately.

    +

    User messages that are on the queue are passed to message handlers. If no message handler exists to interpret the message, then it is removed from the queue without being processed. Message handlers are added with the AddMsgHandler function. If a message handler returns the error code ERR::Terminate, then ProcessMessages() will stop processing the queue and returns immediately with ERR::Okay.

    +

    If a message with a MSGID_QUIT ID is found on the queue, then the function returns immediately with the error code ERR::Terminate. The program must respond to the terminate request by exiting immediately.

    - + Operation successful. Please terminate future calls. Function timed-out before successful completion. @@ -1290,7 +1290,7 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents QueueAction Objects Delay the execution of an action by adding the call to the message queue. - ERROR QueueAction(LONG Action, OBJECTID Object, APTR Args) + ERR QueueAction(LONG Action, OBJECTID Object, APTR Args) The ID of an action or method to execute. The target object. @@ -1300,7 +1300,7 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents

    Use QueueAction() to execute an action by way of the local message queue. This means that the supplied Action and the Args will be bundled into a message that will be placed in the queue. This function then returns immediately.

    The action will be executed on the next cycle of ProcessMessages in line with the FIFO order of queued messages.

    - + Operation successful. General failure. A specified number is outside of the valid range. @@ -1315,7 +1315,7 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents ReadFileToBuffer Files Reads a file into a buffer. - ERROR ReadFileToBuffer(CSTRING Path, APTR Buffer, LONG BufferSize, LONG * Result) + ERR ReadFileToBuffer(CSTRING Path, APTR Buffer, LONG BufferSize, LONG * Result) The path of the file. Pointer to a buffer that will receive the file content. @@ -1326,7 +1326,7 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents

    This function provides a simple method for reading file content into a buffer. In some cases this procedure may be optimised for the host platform, which makes it the fastest way to read file content in simple cases.

    File path approximation is supported if the Path is prefixed with a ~ character (e.g. ~pictures:photo could be matched to photo.jpg in the same folder).

    - + Operation successful. File error, e.g. file not found. Invalid arguments passed to function. @@ -1341,16 +1341,16 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents ReadInfoTag Files Read a named tag from a FileInfo structure. - ERROR ReadInfoTag(struct FileInfo * Info, CSTRING Name, CSTRING * Value) + ERR ReadInfoTag(struct FileInfo * Info, CSTRING Name, CSTRING * Value) Pointer to a valid FileInfo structure. The name of the tag. The discovered string value is returned here if found. -

    Call ReadInfoTag() to retrieve the string value associated with a named tag in a FileInfo structure. The tag must have been added with AddInfoTag() or ERR_NotFound will be returned.

    +

    Call ReadInfoTag() to retrieve the string value associated with a named tag in a FileInfo structure. The tag must have been added with AddInfoTag() or ERR::NotFound will be returned.

    - + Operation successful. A search routine in this function failed. Function call missing argument value(s) @@ -1361,7 +1361,7 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents ReallocMemory Memory Reallocates memory blocks. - ERROR ReallocMemory(APTR Memory, ULONG Size, APTR * Address, MEMORYID * ID) + ERR ReallocMemory(APTR Memory, ULONG Size, APTR * Address, MEMORYID * ID) Pointer to a memory block obtained from AllocMemory(). The size of the new memory block. @@ -1372,7 +1372,7 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents

    This function is used to reallocate memory blocks to new lengths. You can shrink or expand a memory block as you wish. The data of your original memory block will be copied over to the new block. If the new block is of a larger size, the left-over bytes will be filled with zero-byte values. If the new block is smaller, you will lose some of the original data.

    The original block will be destroyed as a result of calling this function unless the reallocation process fails, in which case your existing memory block will remain valid.

    - + Operation successful. Invalid arguments passed to function. General memory error. @@ -1385,7 +1385,7 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents RegisterFD System Registers a file descriptor for monitoring when the task is asleep. - ERROR RegisterFD(HOSTHANDLE FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR) , APTR Data) + ERR RegisterFD(HOSTHANDLE FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR) , APTR Data) The file descriptor that is to be watched. Set to at least one of READ, WRITE, EXCEPT, REMOVE. @@ -1399,7 +1399,7 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents

    The capabilities of this function and FD handling in general is developed to suit the host platform. On POSIX compliant systems, standard file descriptors are used. In Microsoft Windows, object handles are used and blocking restrictions do not apply, except to sockets.

    Call the DeregisterFD() macro to simplify unsubscribing once the file descriptor is no longer needed or is destroyed.

    - + Operation successful. Invalid arguments passed to function. This request is not supported. @@ -1410,14 +1410,14 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents ReleaseMemory Memory Releases a lock from a memory based resource. - ERROR ReleaseMemory(MEMORYID MemoryID) + ERR ReleaseMemory(MEMORYID MemoryID) A reference to a memory resource for release.

    Successful calls to AccessMemory must be paired with a call to ReleaseMemory() so that the memory can be made available to other processes. By releasing the resource, the access count will decrease, and if applicable a thread that is in the queue for access may then be able to acquire a lock.

    - + Operation successful. A search routine in this function failed. Part of the system is unreachable due to a persistent lock. @@ -1485,7 +1485,7 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents ResolvePath Files Converts volume-based paths into absolute paths applicable to the host platform. - ERROR ResolvePath(CSTRING Path, RSF Flags, STRING * Result) + ERR ResolvePath(CSTRING Path, RSF Flags, STRING * Result) The path to be resolved. Optional flags. @@ -1501,7 +1501,7 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents

    If the path resolves to a virtual drive, it may not be possible to confirm whether the target file exists if the virtual driver does not support this check. This is common when working with network drives.

    - + Operation successful. A search routine in this function failed. File not found. @@ -1530,7 +1530,7 @@ parasol:pictures/ parasol:documents parasol:documents (Existing documents ScanDir Files Scans the content of a folder, by item. - ERROR ScanDir(struct DirInfo * Info) + ERR ScanDir(struct DirInfo * Info) Pointer to a DirInfo structure for storing scan results. @@ -1548,7 +1548,7 @@ if (!OpenDir(path, RDF::FILE|RDF::FOLDER, &info)) {

    The RDF flags that may be returned in the Flags field are VOLUME, FOLDER, FILE, LINK.

    - + Operation successful. The folder is empty. Invalid arguments passed to function. @@ -1559,7 +1559,7 @@ if (!OpenDir(path, RDF::FILE|RDF::FOLDER, &info)) { ScanMessages Messages Scans a message queue for multiple occurrences of a message type. - ERROR ScanMessages(LONG * Handle, LONG Type, APTR Buffer, LONG Size) + ERR ScanMessages(LONG * Handle, LONG Type, APTR Buffer, LONG Size) Pointer to a 32-bit value that must initially be set to zero. The ScanMessages() function will automatically update this variable with each call so that it can remember its analysis position. The message type to filter for, or zero to scan all messages in the queue. @@ -1567,7 +1567,7 @@ if (!OpenDir(path, RDF::FILE|RDF::FOLDER, &info)) { The byte-size of the supplied Buffer. -

    Use the ScanMessages() function to scan the local message queue for information without affecting the state of the queue. To use this function effectively, make repeated calls to ScanMessages() to analyse the queue until it returns an error code other than ERR_Okay.

    +

    Use the ScanMessages() function to scan the local message queue for information without affecting the state of the queue. To use this function effectively, make repeated calls to ScanMessages() to analyse the queue until it returns an error code other than ERR::Okay.

    The following example illustrates a scan for MSGID_QUIT messages:

    while (!ScanMessages(&handle, MSGID_QUIT, NULL, NULL)) {
        ...
    @@ -1575,7 +1575,7 @@ if (!OpenDir(path, RDF::FILE|RDF::FOLDER, &info)) {
     

    Messages will often (but not always) carry data that is relevant to the message type. To retrieve this data a buffer must be supplied. If the buffer is too small as indicated by the Size, the message data will be trimmed to fit without any further indication.

    - + Operation successful. A search routine in this function failed. Function call missing argument value(s) @@ -1586,7 +1586,7 @@ if (!OpenDir(path, RDF::FILE|RDF::FOLDER, &info)) { SendMessage Messages Add a message to the local message queue. - ERROR SendMessage(LONG Type, MSF Flags, APTR Data, LONG Size) + ERR SendMessage(LONG Type, MSF Flags, APTR Data, LONG Size) The message Type/ID being sent. Unique type ID's can be obtained from AllocateID. Optional flags. @@ -1596,7 +1596,7 @@ if (!OpenDir(path, RDF::FILE|RDF::FOLDER, &info)) {

    The SendMessage() function will add a message to the end of the local message queue. Messages must be associated with a Type identifier and this can help the receiver process any accompanying Data. Some common message types are pre-defined, such as MSGID_QUIT. Custom messages should use a unique type ID obtained from AllocateID.

    - + Operation successful. Invalid arguments passed to function. @@ -1606,7 +1606,7 @@ if (!OpenDir(path, RDF::FILE|RDF::FOLDER, &info)) { SetArray Fields Used to set array fields in objects. - ERROR SetArray(OBJECTPTR Object, FIELD Field, APTR Array, LONG Elements) + ERR SetArray(OBJECTPTR Object, FIELD Field, APTR Array, LONG Elements) Pointer to the target object. The universal ID of the field you wish to write to, OR'd with a type indicator. @@ -1621,7 +1621,7 @@ SetArray(Object, FID_Table|TLONG, array, 100);

    An indicator of the type of the elements in the Array must be OR'd into the Field parameter. Available field types are listed in SetField. Note that the type that you choose must be a match to the type expected for elements in the array.

    - + Operation successful. Access to a field was denied. Field type mismatch while getting or setting a field. @@ -1687,7 +1687,7 @@ FreeResource(memory); // Reference is no longer valid SetField Fields Used to set field values of objects. - ERROR SetField(OBJECTPTR Object, FIELD Field, ...) + ERR SetField(OBJECTPTR Object, FIELD Field, ...) Pointer to the target object. The universal ID of the field to update, OR'd with a type indicator. @@ -1699,20 +1699,23 @@ FreeResource(memory); // Reference is no longer valid
    SetField(Object, FID_X|TLONG, 100);
     SetField(Object, FID_Statement|TSTR, "string");
     
    -

    Fields are referenced by unique ID's that reflect their names. On occasion you may find that there is no reserved ID for the field that you wish to access. To convert field names into their relevant IDs, call the StrHash function. Reserved field ID's are listed in the parasol/system/fields.h include file.

    -

    The type of the Value parameter must be OR'd into the Field parameter. When writing a field you must give consideration to the type of the target, in order to prevent a type mismatch from occurring. All numeric types are compatible with each other and strings can also be converted to numeric types automatically. String and pointer types are interchangeable.

    +

    Fields are referenced as hashed UID's calculated from the StrHash function. The majority of field ID's are predefined in the parasol/system/fields.h include file.

    +

    The type of the Value parameter must be OR'd into the Field parameter. If the provided type does not match that of the field, a type conversion will occur. All numeric types are compatible with each other and strings can also be converted to a numeric value automatically. String and pointer types are interchangeable.

    Available field types are as follows:

    A 32-bit integer value. A 64-bit floating point value. +A 64-bit floating point value that represents a scaled multiplier or percentage (1.0 is equivalent to 100%). A 64-bit integer value. -A standard 32-bit address space pointer. -A 32-bit pointer that refers to a string. +A standard address space pointer. +A pointer that refers to a string. +A pointer to a FUNCTION structure. +A pointer to a Variable structure. -

    There is no requirement for you to have a working knowledge of the target object's field configuration in order to write information to it.

    +

    There is no requirement for the client to have a working knowledge of the target object's field configuration in order to write information to it.

    To set a field with a fixed-size array, please use the SetArray function.

    - + Operation successful. Invalid arguments passed to function. Access to a field was denied. @@ -1724,7 +1727,7 @@ SetField(Object, FID_Statement|TSTR, "string"); SetName Objects Sets the name of an object. - ERROR SetName(OBJECTPTR Object, CSTRING Name) + ERR SetName(OBJECTPTR Object, CSTRING Name) The target object. The new name for the object. @@ -1733,7 +1736,7 @@ SetField(Object, FID_Statement|TSTR, "string");

    This function sets the name of an object. This enhances log messages and allows the object to be found in searches. Please note that the length of the Name will be limited to the value indicated in the core header file, under the MAX_NAME_LEN definition. Names exceeding the allowed length are trimmed to fit.

    Object names are limited to alpha-numeric characters and the underscore symbol. Invalid characters are replaced with an underscore.

    - + Operation successful. A search routine in this function failed. Failed to lock a required resource. @@ -1745,7 +1748,7 @@ SetField(Object, FID_Statement|TSTR, "string"); SetOwner Objects Changes object ownership dynamically. - ERROR SetOwner(OBJECTPTR Object, OBJECTPTR Owner) + ERR SetOwner(OBJECTPTR Object, OBJECTPTR Owner) Pointer to the object to modify. Pointer to the new owner for the object. @@ -1759,7 +1762,7 @@ SetField(Object, FID_Statement|TSTR, "string");

    If the Object does not support the NewOwner action, or the Owner does not support the NewChild action, then the process will not fail. It will continue on the assumption that neither party is concerned about ownership management.

    - + Operation successful. Invalid arguments passed to function. Function call missing argument value(s) @@ -1790,7 +1793,7 @@ SetField(Object, FID_Statement|TSTR, "string"); SetResourcePath System Redefines the location of a system resource path. - ERROR SetResourcePath(RP PathType, CSTRING Path) + ERR SetResourcePath(RP PathType, CSTRING Path) The ID of the resource path to set. The new location to set for the resource path. @@ -1799,7 +1802,7 @@ SetField(Object, FID_Statement|TSTR, "string");

    The SetResourcePath() function changes the default locations of the Core's resource paths.

    To read a resource path, use the GetSystemState function.

    - + Operation successful. Function call missing argument value(s) @@ -1809,7 +1812,7 @@ SetField(Object, FID_Statement|TSTR, "string"); SetVolume Files Adds a new volume name to the system. - ERROR SetVolume(CSTRING Name, CSTRING Path, CSTRING Icon, CSTRING Label, CSTRING Device, VOLUME Flags) + ERR SetVolume(CSTRING Name, CSTRING Path, CSTRING Icon, CSTRING Label, CSTRING Device, VOLUME Flags) Required. The name of the volume. Required. The path to be associated with the volume. If setting multiple paths, separate each path with a semi-colon character. Each path must terminate with a forward slash to denote a folder. @@ -1823,7 +1826,7 @@ SetField(Object, FID_Statement|TSTR, "string");

    Flags that may be passed are as follows:

    - + Operation successful. Failed to lock a required resource. Function call missing argument value(s) @@ -1834,7 +1837,7 @@ SetField(Object, FID_Statement|TSTR, "string"); StrCompare Strings Compares strings to see if they are identical. - ERROR StrCompare(CSTRING String1, CSTRING String2, LONG Length, STR Flags) + ERR StrCompare(CSTRING String1, CSTRING String2, LONG Length, STR Flags) Pointer to the first string. Pointer to the second string. @@ -1842,13 +1845,13 @@ SetField(Object, FID_Statement|TSTR, "string"); Optional flags. -

    This function compares two strings against each other. If the strings match then it returns ERR_Okay, otherwise it returns ERR_False. By default the function is not case sensitive, but you can turn on case sensitivity by specifying the STR::CASE flag.

    -

    If you set the Length to 0, the function will compare both strings for differences until a string terminates. If all characters matched up until the termination, ERR_Okay will be returned regardless of whether or not one of the strings happened to be longer than the other.

    -

    If the Length is not 0, then the comparison will stop once the specified number of characters to match has been reached. If one of the strings terminates before the specified Length is matched, ERR_False will be returned.

    -

    If the STR::MATCH_LEN flag is specified, you can force the function into returning an ERR_Okay code only on the condition that both strings are of matching lengths. This flag is typically specified if the Length argument has been set to 0.

    +

    This function compares two strings against each other. If the strings match then it returns ERR::Okay, otherwise it returns ERR::False. By default the function is not case sensitive, but you can turn on case sensitivity by specifying the STR::CASE flag.

    +

    If you set the Length to 0, the function will compare both strings for differences until a string terminates. If all characters matched up until the termination, ERR::Okay will be returned regardless of whether or not one of the strings happened to be longer than the other.

    +

    If the Length is not 0, then the comparison will stop once the specified number of characters to match has been reached. If one of the strings terminates before the specified Length is matched, ERR::False will be returned.

    +

    If the STR::MATCH_LEN flag is specified, you can force the function into returning an ERR::Okay code only on the condition that both strings are of matching lengths. This flag is typically specified if the Length argument has been set to 0.

    If the STR::WILDCARD flag is set, the first string that is passed may contain wild card characters, which gives special meaning to the asterisk and question mark characters. This allows you to make abstract comparisons, for instance ABC* would match to ABCDEF and 1?3 would match to 1x3.

    - + Operation successful. The result is false. Function call missing argument value(s) @@ -1890,7 +1893,7 @@ SetField(Object, FID_Statement|TSTR, "string"); StrReadLocale Strings Read system locale information. - ERROR StrReadLocale(CSTRING Key, CSTRING * Value) + ERR StrReadLocale(CSTRING Key, CSTRING * Value) The name of a locale value to read. A pointer to the retrieved string value will be returned in this parameter. @@ -1911,7 +1914,7 @@ SetField(Object, FID_Statement|TSTR, "string"); Negative symbol, e.g. '-'
    - + Operation successful. A search routine in this function failed. No data is available for use. @@ -1923,7 +1926,7 @@ SetField(Object, FID_Statement|TSTR, "string"); SubscribeAction Objects Monitor action calls made against an object. - ERROR SubscribeAction(OBJECTPTR Object, LONG Action, FUNCTION * Callback) + ERR SubscribeAction(OBJECTPTR Object, LONG Action, FUNCTION * Callback) The target object. The ID of the action that will be monitored. Methods are not supported. @@ -1933,24 +1936,23 @@ SetField(Object, FID_Statement|TSTR, "string");

    The SubscribeAction() function allows a client to receive a callback each time that an action is executed on an object. This technique is referred to as "action monitoring" and is often used for responding to UI events and the termination of objects.

    Subscriptions are context sensitive, so the Callback will execute in the space attributed to to the caller.

    The following example illustrates how to listen to a Surface object's Redimension action and respond to resize events:

    -
    auto callback = make_function_stdc(notify_resize);
    -SubscribeAction(surface, AC_Redimension, &callback);
    +
    SubscribeAction(surface, AC_Redimension, FUNCTION(notify_resize, meta_ptr));
     

    The template below illustrates how the Callback function should be constructed:

    -
    void notify_resize(OBJECTPTR Object, ACTIONID Action, ERROR Result, APTR Parameters)
    +
    void notify_resize(OBJECTPTR Object, ACTIONID Action, ERR Result, APTR Parameters, APTR CallbackMeta)
     {
        auto Self = (objClassType *)CurrentContext();
     
        // Code here...
    -   if ((Result == ERR_Okay) and (Parameters)) {
    +   if ((Result == ERR::Okay) and (Parameters)) {
           auto resize = (struct acRedimension *)Parameters;
        }
     }
     
    -

    The Object is the original subscription target, as-is the Action ID. The Result is the error code that was generated at the end of the action call. If this is not set to ERR_Okay, assume that the action did not have an effect on state. The Parameters are the original arguments provided by the client - be aware that these can legitimately be NULL even if an action specifies a required parameter structure. Notice that because subscriptions are context sensitive, we can use CurrentContext to get a reference to the object that initiated the subscription.

    +

    The Object is the original subscription target, as-is the Action ID. The Result is the error code that was generated at the end of the action call. If this is not set to ERR::Okay, assume that the action did not have an effect on state. The Parameters are the original arguments provided by the client - be aware that these can legitimately be NULL even if an action specifies a required parameter structure. Notice that because subscriptions are context sensitive, CurrentContext can be used to get a reference to the object that initiated the subscription.

    To terminate an action subscription, use the UnsubscribeAction function. Subscriptions are not resource tracked, so it is critical to match the original call with an unsubscription.

    - + Operation successful. Invalid arguments passed to function. A specified number is outside of the valid range. @@ -1962,7 +1964,7 @@ SubscribeAction(surface, AC_Redimension, &callback); SubscribeEvent Events Subscribe to a system event. - ERROR SubscribeEvent(LARGE Event, FUNCTION * Callback, APTR Custom, APTR * Handle) + ERR SubscribeEvent(LARGE Event, FUNCTION * Callback, APTR Custom, APTR * Handle) An event identifier. The function that will be subscribed to the event. @@ -1974,7 +1976,7 @@ SubscribeAction(surface, AC_Redimension, &callback);

    An event handle will be returned in the Handle parameter to identify the subscription. This must be retained to later unsubscribe from the event with the UnsubscribeEvent function.

    The format for the Callback function is Function(APTR Custom, APTR Event, LONG Size), where 'Event' is the event structure that matches to the subscribed EventID.

    - + Operation successful. A call to AllocMemory() failed to create a new memory block. Function call missing argument value(s) @@ -1985,7 +1987,7 @@ SubscribeAction(surface, AC_Redimension, &callback); SubscribeTimer System Subscribes an object or function to the timer service. - ERROR SubscribeTimer(DOUBLE Interval, FUNCTION * Callback, APTR * Subscription) + ERR SubscribeTimer(DOUBLE Interval, FUNCTION * Callback, APTR * Subscription) The total number of seconds to wait between timer calls. A callback function is required that will be called on each time cycle. @@ -1993,12 +1995,12 @@ SubscribeAction(surface, AC_Redimension, &callback);

    This function creates a new timer subscription that will be called at regular intervals for the calling object.

    -

    A callback function must be provided that follows this prototype: ERROR Function(OBJECTPTR Subscriber, LARGE Elapsed, LARGE CurrentTime)

    -

    The Elapsed parameter is the total number of microseconds that have elapsed since the last call. The CurrentTime parameter is set to the PreciseTime value just prior to the Callback being called. The callback function can return ERR_Terminate at any time to cancel the subscription. All other error codes are ignored. Fluid callbacks should call check(ERR_Terminate) to perform the equivalent of this behaviour.

    +

    A callback function must be provided that follows this prototype: ERR Function(OBJECTPTR Subscriber, LARGE Elapsed, LARGE CurrentTime)

    +

    The Elapsed parameter is the total number of microseconds that have elapsed since the last call. The CurrentTime parameter is set to the PreciseTime value just prior to the Callback being called. The callback function can return ERR::Terminate at any time to cancel the subscription. All other error codes are ignored. Fluid callbacks should call check(ERR::Terminate) to perform the equivalent of this behaviour.

    To change the interval, call UpdateTimer with the new value. To release a timer subscription, call UpdateTimer with the resulting SubscriptionID and an Interval of zero.

    Timer management is provisioned by the ProcessMessages function. Failure to regularly process incoming messages will lead to unreliable timer cycles. It should be noted that the smaller the Interval that has been used, the more imperative regular message checking becomes. Prolonged processing inside a timer routine can also impact on other timer subscriptions that are waiting to be processed.

    - + Operation successful. Invalid arguments passed to function. Array has reached capacity and cannot be expanded. @@ -2183,7 +2185,7 @@ SubscribeAction(surface, AC_Redimension, &callback); UnsubscribeAction Objects Terminates action subscriptions. - ERROR UnsubscribeAction(OBJECTPTR Object, LONG Action) + ERR UnsubscribeAction(OBJECTPTR Object, LONG Action) The object that you are unsubscribing from. The ID of the action that will be unsubscribed, or zero for all actions. @@ -2192,7 +2194,7 @@ SubscribeAction(surface, AC_Redimension, &callback);

    The UnsubscribeAction() function will terminate subscriptions made by SubscribeAction.

    To terminate multiple subscriptions in a single call, set the Action parameter to zero.

    - + Operation successful. Invalid arguments passed to function. Function call missing argument value(s) @@ -2216,7 +2218,7 @@ SubscribeAction(surface, AC_Redimension, &callback); UpdateMessage Messages Updates the data of any message that is queued. - ERROR UpdateMessage(LONG Message, LONG Type, APTR Data, LONG Size) + ERR UpdateMessage(LONG Message, LONG Type, APTR Data, LONG Size) The ID of the message that will be updated. Defines the type of the message. If set to -1, the message will be deleted. @@ -2228,7 +2230,7 @@ SubscribeAction(surface, AC_Redimension, &callback);

    Messages can be deleted from the queue by setting the Type to -1. There is no need to provide buffer information when deleting a message.

    If Data is defined, its size should equal that of the data already set against the message. The size will be trimmed if it exceeds that of the existing message, as this function cannot expand the size of the queue.

    - + Operation successful. A search routine in this function failed. Access to a shared memory block was denied. @@ -2240,7 +2242,7 @@ SubscribeAction(surface, AC_Redimension, &callback); UpdateTimer System Modify or remove a subscription created by SubscribeTimer(). - ERROR UpdateTimer(APTR Subscription, DOUBLE Interval) + ERR UpdateTimer(APTR Subscription, DOUBLE Interval) The timer subscription to modify. The new interval for the timer (measured in seconds), or zero to remove. @@ -2248,7 +2250,7 @@ SubscribeAction(surface, AC_Redimension, &callback);

    This function complements SubscribeTimer. It can change the interval for an existing timer subscription, or remove it if the Interval is set to zero.

    - + Operation successful. A search routine in this function failed. Part of the system is unreachable due to a persistent lock. @@ -2260,7 +2262,7 @@ SubscribeAction(surface, AC_Redimension, &callback); WaitForObjects Messages Process incoming messages while waiting on objects to complete their activities. - ERROR WaitForObjects(PMF Flags, LONG TimeOut, struct ObjectSignal * ObjectSignals) + ERR WaitForObjects(PMF Flags, LONG TimeOut, struct ObjectSignal * ObjectSignals) Optional flags are specified here (clients should set a value of zero). A time-out value measured in milliseconds. If this value is negative then no time-out applies and the function will not return until an incoming message or signal breaks it. @@ -2270,7 +2272,7 @@ SubscribeAction(surface, AC_Redimension, &callback);

    The WaitForObjects() function acts as a front-end to ProcessMessages, with the capability of being able to wait for a series of objects that must signal an end to their activities. An object can be signalled via the Signal() action. Termination of a monitored object is also treated as a signal. The function will return once ALL of the objects are signalled or a time-out occurs.

    Note that if an object has been signalled prior to entry to this function, its signal flag will be cleared and the object will not be monitored.

    - + Operation successful. General failure. Function call missing argument value(s) @@ -2290,7 +2292,7 @@ SubscribeAction(surface, AC_Redimension, &callback);

    This function waits for a period of time as specified by the Seconds and MicroSeconds arguments. While waiting, your task will continue to process incoming messages in order to prevent the process' message queue from developing a back-log.

    -

    WaitTime() can return earlier than the indicated timeout if a message handler returns ERR_Terminate, or if a MSGID_QUIT message is sent to the task's message queue.

    +

    WaitTime() can return earlier than the indicated timeout if a message handler returns ERR::Terminate, or if a MSGID_QUIT message is sent to the task's message queue.

    @@ -2462,32 +2464,32 @@ SubscribeAction(surface, AC_Redimension, &callback); The Y field is a fixed coordinate. The YOffset field is a fixed coordinate. The Z field is a fixed coordinate. - Synonym for FIXED_HEIGHT | RELATIVE_HEIGHT - Synonym for FIXED_HEIGHT | RELATIVE_HEIGHT | FIXED_Y_OFFSET | RELATIVE_Y_OFFSET - Synonym for FIXED_WIDTH | RELATIVE_WIDTH | FIXED_X_OFFSET | RELATIVE_X_OFFSET | FIXED_X | RELATIVE_X - The CenterX field is a relative size to this object's parent. - The CenterY field is a relative size to this object's parent. - The Depth field is a relative size to this object's parent. - The Height field is relative to this object's parent. - Synonym for RELATIVE_RADIUS_X | RELATIVE_RADIUS_Y - The RadiusX field is a relative size to this object's parent. - The RadiusY field is a relative size to this object's parent. - The Width field is relative to this object's parent. - The X field is relative to this object's parent. - The XOffset field is relative to this object's parent. - The Y field is relative to this object's parent. - The YOffset field is relative to this object's parent. - The Z field is a relative coordinate to this object's parent. + Synonym for FIXED_HEIGHT | SCALED_HEIGHT + Synonym for FIXED_HEIGHT | SCALED_HEIGHT | FIXED_Y_OFFSET | SCALED_Y_OFFSET + Synonym for FIXED_WIDTH | SCALED_WIDTH | FIXED_X_OFFSET | SCALED_X_OFFSET | FIXED_X | SCALED_X + The CenterX field is scaled to this object's parent. + The CenterY field is scaled to this object's parent. + The Depth field is scaled to this object's parent. + The Height field is scaled to this object's parent. + Synonym for SCALED_RADIUS_X | SCALED_RADIUS_Y + The RadiusX field is scaled to this object's parent. + The RadiusY field is a scaled size to this object's parent. + The Width field is scaled to this object's parent. + The X field is scaled to this object's parent. + The XOffset field is scaled to this object's parent. + The Y field is scaled to this object's parent. + The YOffset field is scaled to this object's parent. + The Z field is a scaled coordinate to this object's parent. Synonym for STATUS_CHANGE_H | STATUS_CHANGE_V - Synonym for FIXED_HEIGHT | RELATIVE_HEIGHT | FIXED_Y_OFFSET | RELATIVE_Y_OFFSET | FIXED_Y | RELATIVE_Y - Synonym for FIXED_WIDTH | RELATIVE_WIDTH - Synonym for FIXED_WIDTH | RELATIVE_WIDTH | FIXED_X_OFFSET | RELATIVE_X_OFFSET - Synonym for FIXED_X | RELATIVE_X - Synonym for FIXED_X_OFFSET | RELATIVE_X_OFFSET - Synonym for FIXED_Y | RELATIVE_Y - Synonym for FIXED_Y_OFFSET | RELATIVE_Y_OFFSET + Synonym for FIXED_HEIGHT | SCALED_HEIGHT | FIXED_Y_OFFSET | SCALED_Y_OFFSET | FIXED_Y | SCALED_Y + Synonym for FIXED_WIDTH | SCALED_WIDTH + Synonym for FIXED_WIDTH | SCALED_WIDTH | FIXED_X_OFFSET | SCALED_X_OFFSET + Synonym for FIXED_X | SCALED_X + Synonym for FIXED_X_OFFSET | SCALED_X_OFFSET + Synonym for FIXED_Y | SCALED_Y + Synonym for FIXED_Y_OFFSET | SCALED_Y_OFFSET @@ -2562,7 +2564,6 @@ SubscribeAction(surface, AC_Redimension, &callback); Supplementary, can be used with longs (for IDs) or pointers Synonym for LONG | OBJECT Synonym for PTR | OBJECT - Supplementary, indicates integer or float value is a percentage. Pointer (32 or 64 bit). Synonym for SYSTEM Synonym for POINTER @@ -2580,6 +2581,7 @@ SubscribeAction(surface, AC_Redimension, &callback); Supplementary, if a long type then format is 0xAARRGGBB, if pointer then refers to an RGB structure. Synonym for READ | INIT Synonym for READ | WRITE + Supplementary, indicates a float value for multiplicative scaling. Synonym for STRING Pointer to a string. Synonym for STR | RESULT @@ -2651,13 +2653,10 @@ SubscribeAction(surface, AC_Redimension, &callback); - Value is an absolute horizontal coordinate that corresponds to a page area (usually the display or touchpad). - Value is an absolute vertical coordinate that corresponds to a page area (usually the display or touchpad). - As for ANALOG_X, this type covers a second analog stick if present. - As for ANALOG_Y, this type covers a second analog stick if present. + The X, Y values are defined as absolute coordinates, relative to the top-left of the display. + As for ANALOG_XY, this type covers a second analog stick if present. As for ANALOG_Z, this type covers a second analog stick if present. - Horizontal position for the default analog control (on gamepads this is the left analog control). Analog values range between -1.0 and 1.0. A value of zero indicates that the control is at rest. - Vertical position for the default analog control. + Position for the default analog control (on gamepads this is the left analog control). Analog values range between -1.0 and 1.0. A value of zero indicates that the control is at rest. 3D or yoke position for the default analog control. A negative value indicates that the control has been pulled out and a positive value indicates that it has been pushed in. Left mouse button, XBox A button, PS square button. Value is pressure sensitive, ranging between 0 - 1.0 (0 is released, 1.0 is fully depressed). Non-specific button assignment. @@ -2671,18 +2670,15 @@ SubscribeAction(surface, AC_Redimension, &callback); Non-specific button assignment. Gamepad select button - value is 0 or 1. Gamepad start button - value is 0 or 1. - Controller tilted on the X axis (left/right). Value indicates angle, -ve = left, +ve = right - Controller tilted on the Y axis (up/down). Value indicates angle -ve = pull/up, +ve = push/down + This message is sent by the input system when the mouse pointer enters an area for the first time. The message value refers to the object ID of the container being monitored for movement. + This message is sent by the input system when the mouse pointer leaves an area. The message value refers to the object ID of the container being monitored for movement. + Controller tilted on the X/Y axis. Value indicates angle, -ve = left, +ve = right Controller is rising or falling. Value expressed as 'speed', - Horizontal digital movement from a relative location. Value is +/- n, where n is the number of units moved horizontally. Mouse movement will normally exceed a value of 1, whereas gamepad movement is limited to a value of +/- 1 except in the case of successive presses. - Vertical digital movement from a relative location. + Digital movement from a relative location. Value is +/- n, where n is the number of units moved horizontally. Mouse movement will normally exceed a value of 1, whereas gamepad movement is limited to a value of +/- 1 except in the case of successive presses. Recently supplied input occurred at the edge of the display. - This message is sent by the input system when the mouse pointer enters a surface for the first time. The message value refers to the surface ID, which will be the same as the recipient. Gamepad left-hand bumper 1 (top) - pressure sensitive value from 0 - 1.0. Gamepad left-hand bumper 2 (lower) - pressure sensitive value from 0 - 1.0. - This message is sent by the input system when the mouse pointer leaves a surface. The message value refers to the ID of the surface that has been left, which will be the same as the recipient. - For pen-based input, this type indicates the horizontal tilt of the pen device. - For pen-based input, this type indicates the vertical tilt of the pen device. A value of 0 indicates that the pen is laid flat with nib at the bottom, 0.5 is 90 degrees, 1.0 is laid flat with nib at the top. + For pen-based input, this type indicates the vertical tilt of the pen device. A value of 0 indicates that the pen is laid flat with nib at the bottom, 0.5 is 90 degrees, 1.0 is laid flat with nib at the top. Amount of pressure applied, ranges from 0 (none) to 1.0 (normal) and possibly higher if user presses hard enough Gamepad right-hand bumper 1 (top) - pressure sensitive value from 0 - 1.0. Gamepad right-hand bumper 2 (lower) - pressure sensitive value from 0 - 1.0. @@ -2696,12 +2692,12 @@ SubscribeAction(surface, AC_Redimension, &callback); Analog movement (ranging from -1.0 to 1.0) Cursor has been anchored with LockCursor() Input is a physical button or switch + Crossing events manage the entering and leaving of an area. Set by the input system if the Type is a button and the button has been clicked in quick succession so as to be classed as a double-click. D-Pad or digital joystick source (restricted to +/- 1) Set if sufficient movement occurred between the original click and its point of release (usually requires a 3 or more pixel difference). This special flag is set by the input system if the pointer is click-dragging an object at the time of the event. - Extended movement information. This covers all types of movement that are unconnected to coordinate positioning - mouse wheel movement and pen tilt are two such examples. - Device feedback - e.g. vibration, tilt + Extended or indirect movement information. This covers all types of movement that are unconnected to coordinate positioning - mouse wheel movement and pen tilt are two such examples. X/Y coordinate movement only. Movement such as the wheel mouse spinning is not covered by this type as it does not influence the coordinate system. Input is a repeated entry (i.e. user is holding down a button and a repetition timer is being triggered) Indicates to the receiver of this message that it is not the primary/original recipient @@ -2909,7 +2905,7 @@ SubscribeAction(surface, AC_Redimension, &callback); - Limits the routine to checking the file cache for the existence of the file. If found, the relevant cache entry is returned. The open count is not incremented by this action (it is therefore unnecessary to follow-up with a call to UnloadFile()). If no up-to-date cache entry is available, ERR_Search is returned. + Limits the routine to checking the file cache for the existence of the file. If found, the relevant cache entry is returned. The open count is not incremented by this action (it is therefore unnecessary to follow-up with a call to UnloadFile()). If no up-to-date cache entry is available, ERR::Search is returned. @@ -2985,7 +2981,7 @@ SubscribeAction(surface, AC_Redimension, &callback); The default behaviour - this will add the message to the end of the queue. The Type parameter refers to a unique message ID rather than a message type for this call. - If the Type parameter matches a message already inside the queue, the new message will not be added and the function will immediately return with ERR_Okay. + If the Type parameter matches a message already inside the queue, the new message will not be added and the function will immediately return with ERR::Okay. If the Type parameter matches a message already inside the queue, the data for that message will be deleted, then the new message will be added to the end of the queue. Wait before inserting the message if the queue is at maximum capacity. @@ -3030,7 +3026,7 @@ SubscribeAction(surface, AC_Redimension, &callback); The object switched from the base-class to a sub-class during initialisation. The object has been signalled and is awaiting processing. The object is subscribed to a timer interval. - Use to allocate an object that has a guaranteed unique name. This will prevent code from shadowing any object that exists with the same name, which can be imperative when creating shared objects. If it is discovered that an identically named object exists, NewObject() will return ERR_ObjectExists. This flag works in conjunction with the Name argument. + Use to allocate an object that has a guaranteed unique name. This will prevent code from shadowing any object that exists with the same name, which can be imperative when creating shared objects. If it is discovered that an identically named object exists, NewObject() will return ERR::ObjectExists. This flag works in conjunction with the Name argument. An object created with this flag will not be tracked back to the object that created it. @@ -3184,7 +3180,7 @@ SubscribeAction(surface, AC_Redimension, &callback); Ignores file extensions for the purpose of file name matching. For use on host systems that use case-insensitive file systems such as Windows; this option checks that the discovered file is a case-sensitive match to the Path. - If the volume referenced by Path is traced to another volume that is reserved by a virtual file system driver, ERR_VirtualVolume is returned. The volume is still resolved as far as possible and the resulting path will be returned by this function. + If the volume referenced by Path is traced to another volume that is reserved by a virtual file system driver, ERR::VirtualVolume is returned. The volume is still resolved as far as possible and the resulting path will be returned by this function. Do not perform more than one iteration when resolving the source file path. Do not test for the existence of the targeted file or folder during the resolution process. Use the PATH environment variable to resolve the file name in the Path parameter. @@ -3280,9 +3276,8 @@ SubscribeAction(surface, AC_Redimension, &callback); - + - @@ -3369,13 +3364,13 @@ SubscribeAction(surface, AC_Redimension, &callback); - Year - Month 1 to 12 - Day 1 to 31 - Hour 0 to 23 - Minute 0 to 59 - Second 0 to 59 - TimeZone -13 to +13 + Year + Month 1 to 12 + Day 1 to 31 + Hour 0 to 23 + Minute 0 to 59 + Second 0 to 59 + TimeZone -13 to +13 @@ -3398,9 +3393,9 @@ SubscribeAction(surface, AC_Redimension, &callback); An option to complement the field type. Can be a pointer or an integer value - A virtual function that will retrieve the value for this field. + A virtual function that will retrieve the value for this field. A virtual function that will set the value for this field. - An internal function for writing to this field. + An internal function for writing to this field. The English name for the field, e.g. "Width" Provides a fast way of finding fields, e.g. FID_WIDTH Field offset within the object @@ -3411,7 +3406,7 @@ SubscribeAction(surface, AC_Redimension, &callback); The name of the field, e.g. "Width" void GetField(*Object, APTR Result); - ERROR SetField(*Object, APTR Value); + ERR SetField(*Object, APTR Value); Can be a pointer or an integer value Special flags that describe the field @@ -3542,7 +3537,7 @@ SubscribeAction(surface, AC_Redimension, &callback); - The value associated with the Type + The value(s) associated with the Type PreciseTime() of the recorded input The hardware device that this event originated from (note: This ID can be to a private/inaccessible object, the point is that the ID is unique) Broad descriptors for the given Type. Automatically defined when delivered to the pointer object diff --git a/docs/xml/modules/display.xml b/docs/xml/modules/display.xml index b62b776b2..209e71a6d 100644 --- a/docs/xml/modules/display.xml +++ b/docs/xml/modules/display.xml @@ -8,7 +8,7 @@ 1 stable gfx - Paul Manias 2003-2023 + Paul Manias 2003-2024 Bitmap Clipboard @@ -41,15 +41,15 @@ CheckIfChild Surfaces Checks if a surface is a child of another particular surface. - ERROR gfxCheckIfChild(OBJECTID Parent, OBJECTID Child) + ERR gfxCheckIfChild(OBJECTID Parent, OBJECTID Child) The surface that is assumed to be the parent. The child surface to check. -

    This function checks if a surface identified by the Child value is the child of the surface identified by the Parent value. ERR_True is returned if the surface is confirmed as being a child of the parent, or if the Child and Parent values are equal. All other return codes indicate false or failure.

    +

    This function checks if a surface identified by the Child value is the child of the surface identified by the Parent value. ERR::True is returned if the surface is confirmed as being a child of the parent, or if the Child and Parent values are equal. All other return codes indicate false or failure.

    - + Operation successful. The result is false. Invalid arguments passed to function. @@ -61,7 +61,7 @@ CopyArea Bitmap Copies a rectangular area from one bitmap to another. - ERROR gfxCopyArea(objBitmap * Bitmap, objBitmap * Dest, BAF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) + ERR gfxCopyArea(objBitmap * Bitmap, objBitmap * Dest, BAF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) The source bitmap. Pointer to the destination bitmap. @@ -77,9 +77,9 @@

    This function copies rectangular areas from one bitmap to another. It performs a straight region-copy only, using the fastest method available. Bitmaps may be of a different type (e.g. bit depth), however this will result in performance penalties. The copy process will respect the clipping region defined in both the source and destination bitmap objects.

    If the TRANSPARENT flag is set in the source object, all colours that match the ColourIndex field will be ignored in the copy operation.

    To enable dithering, pass BAF::DITHER in the Flags argument. The drawing algorithm will use dithering if the source needs to be down-sampled to the target bitmap's bit depth. To enable alpha blending, set BAF::BLEND (the source bitmap will also need to have the BMF::ALPHA_CHANNEL flag set to indicate that an alpha channel is available).

    -

    The quality of 32-bit alpha blending can be improved by selecting the BAF::LINEAR flag. This enables an additional computation whereby each RGB value is converted to linear sRGB colour space before performing the blend. The discernible value of using this option largely depends on the level of opaqueness of either bitmap. Note that this option is not usable if either bitmap is already in a linear colourspace (ERR_InvalidState will be returned if that is the case).

    +

    The quality of 32-bit alpha blending can be improved by selecting the BAF::LINEAR flag. This enables an additional computation whereby each RGB value is converted to linear sRGB colour space before performing the blend. The discernible value of using this option largely depends on the level of opaqueness of either bitmap. Note that this option is not usable if either bitmap is already in a linear colourspace (ERR::InvalidState will be returned if that is the case).

    - + Operation successful. A mis-match has been detected that prevents further processing. Object was in an incorrect state for the operation. @@ -91,7 +91,7 @@ CopyRawBitmap Bitmap Copies graphics data from an arbitrary surface to a bitmap. - ERROR gfxCopyRawBitmap(struct BitmapSurfaceV2 * Surface, objBitmap * Bitmap, CSRF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) + ERR gfxCopyRawBitmap(struct BitmapSurfaceV2 * Surface, objBitmap * Bitmap, CSRF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) Description of the surface source. Destination bitmap. @@ -107,7 +107,7 @@

    This function will copy data from a described surface to a destination bitmap object. You are required to provide the function with a full description of the source in a BitmapSurface structure.

    The X, Y, Width and Height parameters define the area from the source that you wish to copy. The XDest and YDest parameters define the top left corner that you will blit the graphics to in the destination.

    - + Operation successful. Invalid arguments passed to function. Function call missing argument value(s) @@ -118,7 +118,7 @@ CopySurface Surfaces Copies surface graphics data into any bitmap object - ERROR gfxCopySurface(OBJECTID Surface, objBitmap * Bitmap, BDF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) + ERR gfxCopySurface(OBJECTID Surface, objBitmap * Bitmap, BDF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) The ID of the surface object to copy from. Must reference a target Bitmap object. @@ -133,7 +133,7 @@

    This function will copy the graphics data from any surface object to a target Bitmap. This is the fastest and most convenient way to get graphics information out of any surface. As surfaces are buffered, it is guaranteed that the result will not be obscured by any overlapping surfaces that are on the display.

    - + Operation successful. A search routine in this function failed. Access to a shared memory block was denied. @@ -196,7 +196,7 @@ ExposeSurface Surfaces Exposes the content of a surface to the display. - ERROR gfxExposeSurface(OBJECTID Surface, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags) + ERR gfxExposeSurface(OBJECTID Surface, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags) The ID of the surface object that will be exposed. The horizontal coordinate of the area to expose. @@ -208,7 +208,7 @@

    This expose routine will expose all content within a defined surface area, copying it to the display. This will include all child surfaces that intersect with the region being exposed if you set the EXF::CHILDREN flag.

    - + Operation successful. A search routine in this function failed. Access to a shared memory block was denied. @@ -276,7 +276,7 @@ Alpha = CFUnpackAlpha(Format,Colour) GetCursorInfo Cursor Retrieves graphics information from the active mouse cursor. - ERROR gfxGetCursorInfo(struct CursorInfo * Info, LONG Size) + ERR gfxGetCursorInfo(struct CursorInfo * Info, LONG Size) Pointer to a CursorInfo structure. The byte-size of the Info structure. @@ -286,7 +286,7 @@ Alpha = CFUnpackAlpha(Format,Colour)

    If there is no cursor (e.g. this is likely on touch-screen devices) then all field values will be set to zero.

    Note: If the hardware cursor is monochrome, the bits-per-pixel setting will be set to 2 on return. This does not indicate a 4 colour cursor image; rather colour 0 is the mask, 1 is the foreground colour (black), 2 is the background colour (white) and 3 is an XOR pixel. When creating the bitmap, always set the palette to the RGB values that are wanted. The mask colour for the bitmap must refer to colour index 0.

    - + Operation successful. This request is not supported. Function call missing argument value(s) @@ -297,15 +297,15 @@ Alpha = CFUnpackAlpha(Format,Colour) GetCursorPos Cursor Returns the coordinates of the UI pointer. - ERROR gfxGetCursorPos(DOUBLE * X, DOUBLE * Y) + ERR gfxGetCursorPos(DOUBLE * X, DOUBLE * Y) - 32-bit variable that will store the pointer's horizontal coordinate. - 32-bit variable that will store the pointer's vertical coordinate. + Variable that will store the pointer's horizontal coordinate. + Variable that will store the pointer's vertical coordinate. -

    This function is used to retrieve the current coordinates of the user interface pointer. If the device is touch-screen based then the coordinates will reflect the last position that a touch event occurred.

    +

    This function will return the current coordinates of the mouse cursor. If the device is touch-screen based then the coordinates will reflect the last position that a touch event occurred.

    - + Operation successful. An attempt to gain exclusive access to a shared object failed. @@ -315,7 +315,7 @@ Alpha = CFUnpackAlpha(Format,Colour) GetDisplayInfo Display Retrieves display information. - ERROR gfxGetDisplayInfo(OBJECTID Display, struct DisplayInfoV3 ** Info) + ERR gfxGetDisplayInfo(OBJECTID Display, struct DisplayInfoV3 ** Info) Object ID of the display to be analysed. This reference will receive a pointer to a DISPLAYINFO structure. @@ -324,7 +324,7 @@ Alpha = CFUnpackAlpha(Format,Colour)

    The GetDisplayInfo() function returns information about a display, which includes information such as its size and bit depth. If the system is running on a hosted display (e.g. Windows or X11) then GetDisplayInfo() can also be used to retrieve information about the default monitor by using a Display of zero.

    The resulting DISPLAYINFO structure values remain good until the next call to this function, at which point they will be overwritten.

    - + Operation successful. A call to AllocMemory() failed to create a new memory block. Function call missing argument value(s) @@ -352,7 +352,7 @@ Alpha = CFUnpackAlpha(Format,Colour) JET type integer. -

    This function converts JET integer constants to their string equivalent.

    +

    This function converts JET integer constants to their string equivalent.

    A string describing the input type is returned or NULL if the Type is invalid. @@ -372,17 +372,17 @@ Alpha = CFUnpackAlpha(Format,Colour) GetRelativeCursorPos Cursor Returns the coordinates of the pointer cursor, relative to a surface object. - ERROR gfxGetRelativeCursorPos(OBJECTID Surface, DOUBLE * X, DOUBLE * Y) + ERR gfxGetRelativeCursorPos(OBJECTID Surface, DOUBLE * X, DOUBLE * Y) Unique ID of the surface that the coordinates need to be relative to. - 32-bit variable that will store the pointer's horizontal coordinate. - 32-bit variable that will store the pointer's vertical coordinate. + Variable that will store the pointer's horizontal coordinate. + Variable that will store the pointer's vertical coordinate.

    This function is used to retrieve the current coordinates of the pointer cursor. The coordinates are relative to the surface object that is specified in the Surface argument.

    The X and Y parameters will not be set if a failure occurs.

    - + Operation successful. An attempt to gain exclusive access to a shared object failed. @@ -392,7 +392,7 @@ Alpha = CFUnpackAlpha(Format,Colour) GetSurfaceCoords Surfaces Returns the dimensions of a surface. - ERROR gfxGetSurfaceCoords(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height) + ERR gfxGetSurfaceCoords(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height) The surface to query. If zero, the top-level display is queried. The X coordinate of the surface is returned here. @@ -405,7 +405,7 @@ Alpha = CFUnpackAlpha(Format,Colour)

    GetSurfaceCoords() retrieves the dimensions that describe a surface object's area as X, Y, Width and Height. This is the fastest way to retrieve surface dimensions when access to the object structure is not already available.

    - + Operation successful. A search routine in this function failed. Access to a shared memory block was denied. @@ -416,7 +416,7 @@ Alpha = CFUnpackAlpha(Format,Colour) GetSurfaceFlags Surfaces Retrieves the Flags field from a surface. - ERROR gfxGetSurfaceFlags(OBJECTID Surface, RNF * Flags) + ERR gfxGetSurfaceFlags(OBJECTID Surface, RNF * Flags) The surface to query. If zero, the top-level surface is queried. The flags value is returned here. @@ -425,7 +425,7 @@ Alpha = CFUnpackAlpha(Format,Colour)

    This function returns the current Flags field from a surface. It provides the same result as reading the field directly, however it is considered advantageous in circumstances where the overhead of locking a surface object for a read operation is undesirable.

    For information on the available flags, please refer to the Flags field of the Surface class.

    - + Operation successful. Access to a shared memory block was denied. Function call missing argument value(s) @@ -436,7 +436,7 @@ Alpha = CFUnpackAlpha(Format,Colour) GetSurfaceInfo Surfaces Retrieves display information for any surface object without having to access it directly. - ERROR gfxGetSurfaceInfo(OBJECTID Surface, struct SurfaceInfoV2 ** Info) + ERR gfxGetSurfaceInfo(OBJECTID Surface, struct SurfaceInfoV2 ** Info) The unique ID of a surface to query. If zero, the root surface is returned. This parameter will receive a SurfaceInfo pointer that describes the Surface object. @@ -444,7 +444,7 @@ Alpha = CFUnpackAlpha(Format,Colour)

    GetSurfaceInfo() is used for quickly retrieving basic information from surfaces, allowing the client to bypass the AccessObject() function. The resulting structure values are good only up until the next call to this function, at which point those values will be overwritten.

    - + Operation successful. A search routine in this function failed. Invalid arguments passed to function. @@ -467,7 +467,7 @@ Alpha = CFUnpackAlpha(Format,Colour) GetVisibleArea Surfaces Returns the visible region of a surface. - ERROR gfxGetVisibleArea(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height) + ERR gfxGetVisibleArea(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height) The surface to query. If zero, the top-level display will be queried. The X coordinate of the visible area. @@ -480,7 +480,7 @@ Alpha = CFUnpackAlpha(Format,Colour)

    The GetVisibleArea() function returns the visible area of a surface, which is based on its position within its parent surfaces. The resulting coordinates are relative to point 0,0 of the queried surface. If the surface is not obscured, then the resulting coordinates will be (0,0),(Width,Height).

    - + Operation successful. A search routine in this function failed. Access to a shared memory block was denied. @@ -491,7 +491,7 @@ Alpha = CFUnpackAlpha(Format,Colour) LockBitmap Surfaces Returns a bitmap that represents the video area covered by the surface object. - ERROR gfxLockBitmap(OBJECTID Surface, objBitmap ** Bitmap, LVF * Info) + ERR gfxLockBitmap(OBJECTID Surface, objBitmap ** Bitmap, LVF * Info) Object ID of the surface object that you want to lock. The resulting bitmap will be returned in this parameter. @@ -501,7 +501,7 @@ Alpha = CFUnpackAlpha(Format,Colour)

    Use the LockBitmap() function to gain direct access to the bitmap information of a surface object. Because the layering buffer will be inaccessible to the UI whilst you retain the lock, you must keep your access time to an absolute minimum or desktop performance may suffer.

    Repeated calls to this function will nest. To release a surface bitmap, call the UnlockBitmap function.

    - + Operation successful. Invalid arguments passed to function. @@ -511,7 +511,7 @@ Alpha = CFUnpackAlpha(Format,Colour) LockCursor Cursor Anchors the cursor so that it cannot move without explicit movement signals. - ERROR gfxLockCursor(OBJECTID Surface) + ERR gfxLockCursor(OBJECTID Surface) Refers to the surface object that the pointer should send movement signals to. @@ -519,7 +519,7 @@ Alpha = CFUnpackAlpha(Format,Colour)

    The LockCursor() function will lock the current pointer position and pass UserMovement signals to the surface referenced in the Surface parameter. The pointer will not move unless the SetCursorPos function is called. The anchor is granted on a time-limited basis. It is necessary to reissue the anchor every time that a UserMovement signal is intercepted. Failure to reissue the anchor will return the pointer to its normal state, typically within 200 microseconds.

    The anchor can be released at any time by calling the UnlockCursor function.

    - + Operation successful. This request is not supported. An attempt to gain exclusive access to a shared object failed. @@ -564,7 +564,7 @@ Alpha = CFUnpackAlpha(Format,Colour) Resample Bitmap Resamples a bitmap by dithering it to a new set of colour masks. - ERROR gfxResample(objBitmap * Bitmap, struct ColourFormat * ColourFormat) + ERR gfxResample(objBitmap * Bitmap, struct ColourFormat * ColourFormat) The bitmap object to be resampled. The new colour format to be applied to the bitmap. @@ -573,7 +573,7 @@ Alpha = CFUnpackAlpha(Format,Colour)

    The Resample() function provides a means for resampling a bitmap to a new colour format without changing the actual bit depth of the image. It uses dithering so as to retain the quality of the image when down-sampling. This function is generally used to 'pre-dither' true colour bitmaps in preparation for copying to bitmaps with lower colour quality.

    You are required to supply a ColourFormat structure that describes the colour format that you would like to apply to the bitmap's image data.

    - + Operation successful. Function call missing argument value(s) @@ -583,7 +583,7 @@ Alpha = CFUnpackAlpha(Format,Colour) RestoreCursor Cursor Returns the pointer image to its original state. - ERROR gfxRestoreCursor(PTC Cursor, OBJECTID Owner) + ERR gfxRestoreCursor(PTC Cursor, OBJECTID Owner) The cursor image that the pointer will be restored to (0 for the default). The ownership ID that was given in the initial call to SetCursor(). @@ -592,7 +592,7 @@ Alpha = CFUnpackAlpha(Format,Colour)

    Use the RestoreCursor() function to undo an earlier call to SetCursor. It is necessary to provide the same OwnerID that was used in the original call to SetCursor.

    To release ownership of the cursor without changing the current cursor image, use a Cursor setting of PTC::NOCHANGE.

    - + Operation successful. Invalid arguments passed to function. @@ -638,7 +638,7 @@ Alpha = CFUnpackAlpha(Format,Colour) SetCursor Cursor Sets the cursor image and can anchor the pointer to any surface. - ERROR gfxSetCursor(OBJECTID Surface, CRF Flags, PTC Cursor, CSTRING Name, OBJECTID Owner) + ERR gfxSetCursor(OBJECTID Surface, CRF Flags, PTC Cursor, CSTRING Name, OBJECTID Owner) Refers to the surface object that the pointer should anchor itself to, if the RESTRICT flag is used. Otherwise, this parameter can be set to a surface that the new cursor image should be limited to. The object referred to here must be publicly accessible to all tasks. Optional flags that affect the cursor. @@ -653,7 +653,7 @@ Alpha = CFUnpackAlpha(Format,Colour)

    The Owner parameter is used as a locking mechanism to prevent the cursor from being changed whilst it is locked. We recommend that it is set to an object ID such as the program's task ID. As the owner, the cursor remains under your program's control until RestoreCursor is called.

    - + Operation successful. Invalid arguments passed to function. This request is not supported. @@ -666,7 +666,7 @@ Alpha = CFUnpackAlpha(Format,Colour) SetCursorPos Cursor Changes the position of the pointer cursor. - ERROR gfxSetCursorPos(DOUBLE X, DOUBLE Y) + ERR gfxSetCursorPos(DOUBLE X, DOUBLE Y) The new horizontal coordinate for the pointer. The new vertical coordinate for the pointer. @@ -674,7 +674,7 @@ Alpha = CFUnpackAlpha(Format,Colour)

    Changes the position of the pointer cursor using coordinates relative to the entire display.

    - + Operation successful. An attempt to gain exclusive access to a shared object failed. @@ -684,7 +684,7 @@ Alpha = CFUnpackAlpha(Format,Colour) SetCustomCursor Cursor Sets the cursor to a customised bitmap image. - ERROR gfxSetCustomCursor(OBJECTID Surface, CRF Flags, objBitmap * Bitmap, LONG HotX, LONG HotY, OBJECTID Owner) + ERR gfxSetCustomCursor(OBJECTID Surface, CRF Flags, objBitmap * Bitmap, LONG HotX, LONG HotY, OBJECTID Owner) Refers to the surface object that the pointer should restrict itself to, if the RESTRICT flag is used. Otherwise, this parameter can be set to a surface that the new cursor image should be limited to. The object referred to here must be publicly accessible to all tasks. Optional flags affecting the cursor are set here. @@ -716,7 +716,7 @@ Alpha = CFUnpackAlpha(Format,Colour) }
    - + Operation successful. Invalid arguments passed to function. This request is not supported. @@ -728,7 +728,7 @@ Alpha = CFUnpackAlpha(Format,Colour) SetHostOption Display Alter options associated with the host display system. - ERROR gfxSetHostOption(HOST Option, LARGE Value) + ERR gfxSetHostOption(HOST Option, LARGE Value) One of TRAY_ICON, TASKBAR or STICK_TO_FRONT. The value to be applied to the option. @@ -736,7 +736,7 @@ Alpha = CFUnpackAlpha(Format,Colour)

    For internal usage only.

    - + Operation successful. @@ -761,7 +761,7 @@ Alpha = CFUnpackAlpha(Format,Colour) StartCursorDrag Cursor Attaches an item to the cursor for the purpose of drag and drop. - ERROR gfxStartCursorDrag(OBJECTID Source, LONG Item, CSTRING Datatypes, OBJECTID Surface) + ERR gfxStartCursorDrag(OBJECTID Source, LONG Item, CSTRING Datatypes, OBJECTID Surface) Refers to an object that is managing the source data. A custom number that represents the item being dragged from the source. @@ -775,7 +775,7 @@ Alpha = CFUnpackAlpha(Format,Colour)

    The Surface argument allows for a composite surface to be dragged by the mouse cursor as a graphical representation of the source item. It is recommended that the graphic be 32x32 pixels in size and no bigger than 64x64 pixels. The Surface will be hidden on completion of the drag and drop operation.

    If the call to StartCursorDrag() is successful, the mouse cursor will operate in drag and drop mode. The UserMovement and UserClickRelease actions normally reported from the SystemPointer will now include the JD_DRAGITEM flag in the ButtonFlags parameter. When the user releases the primary mouse button, the drag and drop operation will stop and the DragDrop action will be passed to the surface immediately underneath the mouse cursor. Objects that are monitoring for the DragDrop action on that surface can then contact the Source object with a DataFeed DragDropRequest. The resulting data is then passed to the requesting object with a DragDropResult on the DataFeed.

    - + Operation successful. Resource is in use. General failure. @@ -788,7 +788,7 @@ Alpha = CFUnpackAlpha(Format,Colour) SubscribeInput Input Subscribe to incoming input messages for any active surface object. - ERROR gfxSubscribeInput(FUNCTION * Callback, OBJECTID SurfaceFilter, JTYPE Mask, OBJECTID DeviceFilter, LONG * Handle) + ERR gfxSubscribeInput(FUNCTION * Callback, OBJECTID SurfaceFilter, JTYPE Mask, OBJECTID DeviceFilter, LONG * Handle) Reference to a callback function that will receive input messages. Optional. Only the input messages that match the given surface ID will be received. @@ -801,7 +801,7 @@ Alpha = CFUnpackAlpha(Format,Colour)

    The client is required to remove the subscription with UnsubscribeInput once tracking is no longer required.

    Input events can be filtered so that they are received in relation to surfaces and devices. An input mask can also be applied so that only certain types of events are received.

    A callback is required for receiving the input events. The following C++ code illustrates a method for processing events in the callback:

    -
    ERROR consume_input_events(const InputEvent *Events, LONG Handle)
    +
    ERR consume_input_events(const InputEvent *Events, LONG Handle)
     {
        for (auto e=Events; e; e=e->Next) {
           if (((e->Flags & JTYPE::BUTTON) != JTYPE::NIL) and (e->Value > 0)) {
    @@ -809,16 +809,17 @@ Alpha  = CFUnpackAlpha(Format,Colour)
           }
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     

    All processable events are referenced in the InputEvent structure in the Events parameter.

    -

    JET constants are as follows and take note of ENTERED_SURFACE and LEFT_SURFACE which are software generated and not a device event:

    +

    +JET constants are as follows and take note of CROSSED_IN and CROSSED_OUT which are software generated and not a device event:

    -

    The JTYPE values for the Flags field are as follows. Note that these flags also serve as input masks for the SubscribeInput() function, so to receive a message of the given type the appropriate JTYPE flag must have been set in the original subscription call.

    +

    The JTYPE values for the Flags field are as follows. Note that these flags also serve as input masks for the SubscribeInput() function, so to receive a message of the given type the appropriate JTYPE flag must have been set in the original subscription call.

    - + Operation successful. Function call missing argument value(s) @@ -841,7 +842,7 @@ Alpha = CFUnpackAlpha(Format,Colour) UnlockBitmap Surfaces Unlocks any earlier call to gfxLockBitmap(). - ERROR gfxUnlockBitmap(OBJECTID Surface, objBitmap * Bitmap) + ERR gfxUnlockBitmap(OBJECTID Surface, objBitmap * Bitmap) The ID of the surface object that you are releasing. Pointer to the bitmap structure returned earlier by LockBitmap(). @@ -849,7 +850,7 @@ Alpha = CFUnpackAlpha(Format,Colour)

    Call the UnlockBitmap() function to release a surface object from earlier calls to LockBitmap.

    - + Operation successful. Function call missing argument value(s) @@ -859,14 +860,14 @@ Alpha = CFUnpackAlpha(Format,Colour) UnlockCursor Cursor Undoes an earlier call to LockCursor() - ERROR gfxUnlockCursor(OBJECTID Surface) + ERR gfxUnlockCursor(OBJECTID Surface) Refers to the surface object used for calling LockCursor().

    Call this function to undo any earlier calls to LockCursor() and return the mouse pointer to its regular state.

    - + Operation successful. There is no exclusive lock on this object. An attempt to gain exclusive access to a shared object failed. @@ -878,14 +879,14 @@ Alpha = CFUnpackAlpha(Format,Colour) UnsubscribeInput Input Removes an input subscription. - ERROR gfxUnsubscribeInput(LONG Handle) + ERR gfxUnsubscribeInput(LONG Handle) Reference to a handle returned by SubscribeInput().

    This function removes an input subscription that has been created with SubscribeInput.

    - + Operation successful. A search routine in this function failed. Function call missing argument value(s) @@ -896,7 +897,7 @@ Alpha = CFUnpackAlpha(Format,Colour) WindowHook Surfaces Adds a function hook for receiving window messages from a host desktop. - ERROR gfxWindowHook(OBJECTID SurfaceID, WH Event, FUNCTION * Callback) + ERR gfxWindowHook(OBJECTID SurfaceID, WH Event, FUNCTION * Callback) A hosted surface to be monitored. A window hook event. @@ -905,7 +906,7 @@ Alpha = CFUnpackAlpha(Format,Colour)

    Adds a function hook for receiving window events from a host desktop.

    - + Operation successful. Function call missing argument value(s) diff --git a/docs/xml/modules/document.xml b/docs/xml/modules/document.xml deleted file mode 100644 index 09088dee5..000000000 --- a/docs/xml/modules/document.xml +++ /dev/null @@ -1,140 +0,0 @@ - - - - - - Document - module - 1 - Paul Manias © 2005-2023 - - Document - - - - - CharLength - Returns the length of any character or escape code in a document data stream. - LONG docCharLength(objDocument * Document, LONG Index) - - The document to query. - The byte index of the character to inspect. - - -

    This function will compute the byte-length of any UTF-8 character sequence or escape code in a document's data stream.

    -
    - The length of the character is returned, or 0 if an error occurs. -
    - - - - Bottom border edge. - Left border edge. - Right border edge. - Top border edge. - - - - This read-only flag is set if the object has been disabled through the Disable action. - Allow direct keyboard input and document editing. - Turn off debug output produced during document layout and processing - useful on refresh for example. - Do not display scrollbars if the page exceeds the size of the view. - System-keys provide standard key support for Ctrl-C, Ctrl-X etc. Set this flag to turn them off. - This flag forces overwrite mode when the user enters information through the keyboard. If the flag is not set, then insert mode is used. - Turn off all security measures - may only be set prior to initialisation. - - - - The user has interacted with a hyperlink. This event can be cancelled by returning ERR_Skip. - The source file path has changed. Useful for detecting when the user has left the page. - - - - - - - - - - - - - - - - - - - - Anchor objects to the text. - - Print all text in caps. - - Do not wrap the text. - All white-space is taken into account. - Synonym for BOLD | UNDERLINE | ITALIC | CAPS - - - - - - - - - - - - - - - - - Version of this DocStyle structure - The document object that this style originates from - Pointer to the current font object. Indicates face, style etc, but not simple attributes like colour - Foreground colour (colour of the font) - Underline colour for the font, if active - Font style flags (FSO) - - - - - - - - - - - - - - - - - - All key-values associated with the link. - - - - - - - - - Font lookup - FSO flags - Font colour - - - - - - - - - A major font change has occurred (e.g. face, point size) - A minor style change has occurred (e.g. font colour) - - - -
    diff --git a/docs/xml/modules/fluid.xml b/docs/xml/modules/fluid.xml index f0545a7d6..a805e6b0f 100644 --- a/docs/xml/modules/fluid.xml +++ b/docs/xml/modules/fluid.xml @@ -9,7 +9,7 @@ 1 beta fl - Paul Manias © 2006-2023 + Paul Manias © 2006-2024 diff --git a/docs/xml/modules/font.xml b/docs/xml/modules/font.xml index fe680e7e1..db55853cb 100644 --- a/docs/xml/modules/font.xml +++ b/docs/xml/modules/font.xml @@ -6,7 +6,7 @@ Font module 1 - Paul Manias © 1998-2023 + Paul Manias © 1998-2024 Font @@ -15,66 +15,29 @@ CharWidth Returns the width of a character. - LONG fntCharWidth(objFont * Font, ULONG Char, ULONG KChar, LONG * Kerning) + LONG fntCharWidth(objFont * Font, ULONG Char) The font to use for calculating the character width. A unicode character. - A unicode character to use for calculating the font kerning (optional). - The resulting kerning value (optional). -

    This function will return the pixel width of a font character. The character is specified as a unicode value in the Char parameter. Kerning values can also be returned, which affect the position of the character along the horizontal. The previous character in the word is set in KChar and the kerning value will be returned in the Kerning parameter. If kerning information is not required, set the KChar and Kerning parameters to zero.

    +

    This function will return the pixel width of a bitmap font character. The character is specified as a unicode value in the Char parameter.

    +

    The font's GlyphSpacing value is not used in calculating the character width.

    The pixel width of the character will be returned.
    - - ConvertCoords - Converts pixel coordinates into equivalent column and row positions in font strings. - ERROR fntConvertCoords(objFont * Font, CSTRING String, LONG X, LONG Y, LONG * Column, LONG * Row, LONG * ByteColumn, LONG * BytePos, LONG * CharX) - - An initialised font object. - Either point to a string for inspection or set to NULL to inspect the string currently in the font's String field. - The horizontal coordinate to translate into a column position. - The vertical coordinate to translate into a row position. - This result parameter will be updated to reflect the calculated character position, with consideration to the UTF-8 standard. May be NULL if not required. - This result parameter will be updated to reflect the calculated row position. May be NULL if not required. - This result parameter will be updated to reflect the absolute column byte position within the given row. May be NULL if not required. - This result parameter will be updated to reflect the absolute byte position with the font String. May be NULL if not required. - This result parameter will be reflect the X coordinate of the character to which the (X, Y) coordinates are resolved. May be NULL if not required. - - -

    This function is used to convert pixel coordinates within a font String into the equivalent Row and Column character positions. If the coordinate values that are supplied are in excess of the String dimensions, the Column and Row results will be automatically restricted to their maximum value. For instance, if the Y argument is set to 280 and the String consists of 15 rows amounting to 150 pixels in height, the Row value will be returned as 15.

    -

    Negative coordinate values are not permitted.

    -
    - - Operation successful. - Invalid arguments passed to function. - A required field value is undefined. - -
    - - - FreetypeHandle - Returns a handle to the FreeType library. - APTR fntFreetypeHandle() - -

    This function returns a direct handle to the internal FreeType library. It is intended that this handle should only be used by existing projects that are based on FreeType and need access to its functionality. References to FreeType functions can be obtained by loading the Font module and then calling the ResolveSymbol method to retrieve function names, e.g. "FT_Open_Face".

    -
    - A handle to the FreeType library will be returned. -
    - GetList Returns a list of all available system fonts. - ERROR fntGetList(struct FontList ** Result) + ERR fntGetList(struct FontList ** Result) The font list is returned here. -

    This function returns a linked list of all available system fonts.

    +

    This function returns a linked list of all available system fonts. The list must be terminated once it is no longer required.

    - + Operation successful. An attempt to gain exclusive access to a shared object failed. Function call missing argument value(s) @@ -82,59 +45,55 @@
    - InstallFont - Installs a new font. - ERROR fntInstallFont(CSTRING Files) - - A list of the font files that are to be installed must be specified here. If there is more than one data file, separate each file name with a semi-colon. - + RefreshFonts + Refreshes the system font list with up-to-date font information. + ERR fntRefreshFonts() -

    The InstallFont() function is used to install new fonts on a system running Parasol. While it is possible for users to download new font files and install them by hand, this is a process that is too difficult for novices and is open to mistakes on the part of the user. By using a program that uses the InstallFont() function, the installation process can take place automatically.

    -

    To install a new font, you only need to know the location of the font file(s). The rest of the information about the font will be derived after an analysis of the data.

    -

    Once this function is called, the data files will be copied into the correct sub-directory and the font registration files will be updated to reflect the presence of the new font. The font will be available immediately thereafter, so there is no need to reset the system to acknowledge the presence of the font.

    +

    This function scans the fonts: volume and refreshes the font database.

    +

    Refreshing fonts can take an extensive amount of time as each font file needs to be completely analysed for information. The fonts:fonts.cfg file will be re-written on completion to reflect current font settings.

    - + Operation successful. - This request is not supported. - Function call missing argument value(s) + An attempt to gain exclusive access to a shared object failed.
    - RemoveFont - Removes an installed font from the system. - ERROR fntRemoveFont(CSTRING Name) + ResolveFamilyName + Convert a CSV family string to a single family name. + ERR fntResolveFamilyName(CSTRING String, CSTRING * Result) - The name of the font face (family name) that is to be removed. + A CSV family string to resolve. + The nominated family name is returned in this parameter. -

    RemoveFont() will remove any font that is installed in the system. Once a font has been removed, the data is permanently destroyed and it cannot be recovered. To remove a font, specify its family name only. All associated styles for that font will be deleted.

    -

    This function may fail if attempting to remove a font that is currently in use.

    +

    Use ResolveFamilyName() to convert complex CSV family strings to a single family name. The provided String will be parsed in sequence, with priority given from left to right. If a single asterisk is used to terminate the list, it is guaranteed that the system default will be returned if no valid match is made.

    +

    It is valid for individual names to utilise the common wildcards ? and * to make a match. E.g. Times New * would be able to match to Times New Roman if available.

    - + Operation successful. - Invalid arguments passed to function. - Deletion of a folder or file failed (e.g. permissions, read-only media). + A search routine in this function failed. + An attempt to gain exclusive access to a shared object failed. + A call to GetField() failed to retrieve a field value. + Function call missing argument value(s)
    SelectFont - Searches for a 'best fitting' font file based on select criteria. - ERROR fntSelectFont(CSTRING Name, CSTRING Style, LONG Point, FTF Flags, CSTRING * Path) + Searches for a 'best fitting' font file, based on family name and style. + ERR fntSelectFont(CSTRING Name, CSTRING Style, CSTRING * Path, FMETA * Meta) - The name of a font face, or multiple faces in CSV format. Using camel-case for each word is compulsory. + The name of a font face to search for (case insensitive). The required style, e.g. Bold or Italic. Using camel-case for each word is compulsory. - Preferred point size. - Optional flags. The location of the best-matching font file is returned in this parameter. + Optional, returns additional meta information about the font file. -

    This function searches for the closest matching font based on the details provided by the client. The details that can be searched for include the name, point size and style of the desired font.

    -

    It is possible to list multiple faces in order of their preference in the Name parameter. For instance Sans Serif,Source Sans,* will give preference to Sans Serif and will look for Source Sans if the first choice font is unavailable. The use of the * wildcard indicates that the default system font should be used in the event that neither of the other choices are available. Note that omitting this wildcard will raise the likelihood of ERR_Search being returned in the event that neither of the preferred choices are available.

    -

    Flags that alter the search behaviour are FTF::PREFER_SCALED, FTF::PREFER_FIXED and FTF::ALLOW_SCALE.

    +

    This function resolves a font family Name and Style to a font file path. It works on a best efforts basis; the Name must exist but the Style is a non-mandatory preference.

    +

    The resulting Path must be freed once it is no longer required.

    - + Operation successful. A search routine in this function failed. An attempt to gain exclusive access to a shared object failed. @@ -142,38 +101,6 @@
    - - SetDefaultSize - Sets the default font size for the application. - DOUBLE fntSetDefaultSize(DOUBLE Size) - - The new default point size. - - -

    This function is used to set the default font size for the application. This will affect fonts that you create with proportional sizes (e.g. a point size of 150% and a default point of 10 would result in a 15 point font). Also, Font objects with no preset size will be set to the default size.

    -

    Please note that the default size is defined by the global style value on the xpath /interface/@fontsize. This can also be overridden by the user's style preference. We recommend against an application calling SetDefaultSize() unless the interface design makes it a necessity (for instance if the user has poor eyesight, restricting the font size may have usability implications).

    -
    - The previous font size is returned. -
    - - - StringSize - Calculates the exact dimensions of a font string, giving respect to word wrapping. - void fntStringSize(objFont * Font, CSTRING String, LONG Chars, LONG Wrap, LONG * Width, LONG * Rows) - - An initialised font object. - The string to be analysed. - The number of characters (not bytes, so consider UTF-8 serialisation) to be used in calculating the string length. FSS constants can also be used here. - The pixel position at which word wrapping occurs. If zero or less, wordwrap is disabled. - The width of the longest line will be returned in this parameter. - The number of calculated rows will be returned in this parameter. - - -

    This function calculates the width and height of a String (in pixels and rows respectively). It takes into account the font object's current settings and accepts a boundary in the Wrap argument for calculating word wrapping. The routine takes into account any line feeds that may already exist in the String.

    -

    A character limit can be specified in the Chars argument. If this argument is set to FSS_ALL, all characters in String will be used in the calculation. If set to FSS_LINE, the routine will terminate when the first line feed or word-wrap is encountered and the Rows value will reflect the byte position of the word at which the wrapping boundary was encountered.

    -
    -
    - StringWidth Returns the pixel width of any given string in relation to a font's settings. @@ -191,28 +118,31 @@ + + The font should not appear in any named list shown to the user. + The Freetype hinter should be used. + The light version of the Freetype hinter should be used. + The hinting information provided by the font should be given preference. + The font is scalable (assume fixed otherwise). + This is a scalable font featuring variable metrics. + + Process all characters. Terminate operation at the first line feed or word-wrap. - Allows switching to a suitable scalable font if a fixed point size is unavailable. Equivalent to ending a font face with the '*' wildcard. - Smooth the edges of scalable fonts. The Font's Y coordinate is the base line. Font is described as having a bold weight (read only). - Clip words by adding dots to the end of the string. Underline the font with a double-sized line, using the colour defined in UnderlineRGB. Font is described as using italics (read only). - The loaded font is embedded with kerning information (read only). - Glyphs are drawn directly to the target bitmap unblended. - A fixed size font (monochrome, no transforms) is preferred to the equivalent scalable font. - A scaled font is preferred over the equivalent fixed size font. - Quick anti-aliasing is useful for games and can be enabled if the background is black. - A fixed size font is required and not a scalable font. - A scaled font is required and not a fixed size font. - This is set if the font is scalable, otherwise assume fixed. - Smooth the edges of scalable fonts. + + + + The Freetype hinter will be forcibly imposed. + The light version of the Freetype hinter will be forcibly imposed. + The hinting information provided by the font will be given preference. @@ -220,11 +150,14 @@ Pointer to the next entry in the list. The name of the font face. + Reference to another font Name if this is an alias. Pointer to an array of fixed point sizes supported by the font. Supported styles are listed here in CSV format. + For variable fonts, lists all supported axis codes in CSV format TRUE if the font is scalable. - Do not use. - Do not use. + TRUE if the font has variable metrics. + Hinting options + TRUE if the font should be hidden from user font lists. diff --git a/docs/xml/modules/module.xsl b/docs/xml/modules/module.xsl index c58a87a2e..cd9910f14 100644 --- a/docs/xml/modules/module.xsl +++ b/docs/xml/modules/module.xsl @@ -173,7 +173,6 @@
  • Audio
  • Core
  • Display
  • -
  • Document
  • Fluid
  • Font
  • Network
  • diff --git a/docs/xml/modules/network.xml b/docs/xml/modules/network.xml index b0d4a4375..9f454f26f 100644 --- a/docs/xml/modules/network.xml +++ b/docs/xml/modules/network.xml @@ -8,7 +8,7 @@ 1 stable net - Paul Manias © 2005-2023 + Paul Manias © 2005-2024 ClientSocket NetLookup @@ -72,7 +72,7 @@ SetSSL Alters SSL settings on an initialised NetSocket object. - ERROR netSetSSL(objNetSocket * NetSocket, ...) + ERR netSetSSL(objNetSocket * NetSocket, ...) The target NetSocket object. Series of tags terminated by TAGEND. @@ -81,7 +81,7 @@

    Use the SetSSL() function to send SSL commands to a NetSocket object. The following table illustrates the commands that are currently available:

    If a failure occurs when executing a command, the execution of all further commands is aborted and the error code is returned immediately.

    - + Operation successful. Function call missing argument value(s) @@ -103,7 +103,7 @@ StrToAddress Converts an IP Address in string form to an IPAddress structure. - ERROR netStrToAddress(CSTRING String, struct IPAddress * Address) + ERR netStrToAddress(CSTRING String, struct IPAddress * Address) A null-terminated string containing the IP Address in dotted format. Must point to an IPAddress structure that will be filled in. @@ -116,7 +116,7 @@ if (!StrToAddress("127.0.0.1", &addr)) { }
    - + Operation successful. General failure. Invalid arguments passed to function. diff --git a/docs/xml/modules/vector.xml b/docs/xml/modules/vector.xml index c6af4e70e..7c479df38 100644 --- a/docs/xml/modules/vector.xml +++ b/docs/xml/modules/vector.xml @@ -6,7 +6,7 @@ Vector module 1 - Paul Manias © 2010-2023 + Paul Manias © 2010-2024 BlurFX ColourFX @@ -29,6 +29,7 @@ VectorEllipse VectorFilter VectorGradient + VectorGroup VectorImage VectorPath VectorPattern @@ -46,7 +47,7 @@ ApplyPath Copy a pre-generated or custom path to a VectorPath object. - ERROR vecApplyPath(APTR Path, OBJECTPTR VectorPath) + ERR vecApplyPath(APTR Path, OBJECTPTR VectorPath) The source path to be copied. The target VectorPath object. @@ -55,7 +56,7 @@

    Any path originating from GeneratePath, GenerateEllipse or GenerateRectangle can be applied to a VectorPath object by calling ApplyPath(). The source Path can then be deallocated with FreePath if it is no longer required.

    This method is particularly useful when paths need to be generated or changed in real-time and the alternative of processing the path as a string is detrimental to performance.

    - + Operation successful. Function call missing argument value(s) @@ -79,6 +80,23 @@
    + + CharWidth + Returns the width of a character. + DOUBLE vecCharWidth(APTR FontHandle, ULONG Char, ULONG KChar, DOUBLE * Kerning) + + The font to use for calculating the character width. + A 32-bit unicode character. + A unicode character to use for calculating the font kerning (optional). + The resulting kerning value (optional). + + +

    This function will return the pixel width of a font character. The character is specified as a unicode value in the Char parameter. Kerning values can also be returned, which affect the position of the character along the horizontal. The previous character in the word is set in KChar and the kerning value will be returned in the Kerning parameter. If kerning information is not required, set the KChar and Kerning parameters to zero.

    +

    The font's GlyphSpacing value is not used in calculating the character width.

    +
    + The pixel width of the character will be returned. +
    + ClosePath Close the path by connecting the beginning and end points. @@ -129,7 +147,7 @@ DrawPath Draws a vector path to a target bitmap. - ERROR vecDrawPath(objBitmap * Bitmap, APTR Path, DOUBLE StrokeWidth, OBJECTPTR StrokeStyle, OBJECTPTR FillStyle) + ERR vecDrawPath(objBitmap * Bitmap, APTR Path, DOUBLE StrokeWidth, OBJECTPTR StrokeStyle, OBJECTPTR FillStyle) Pointer to a target Bitmap object. The vector path to render. @@ -141,7 +159,24 @@

    Use DrawPath() to draw a generated path to a Bitmap, using customised fill and stroke definitions. This functionality provides an effective alternative to configuring vector scenes for situations where only simple vector shapes are required. However, it is limited in that advanced rendering options and effects are not available to the client.

    A StrokeStyle and/or FillStyle will be required to render the path. Valid styles are allocated and configured using recognised vector style objects, specifically from the classes VectorImage, VectorPattern and VectorGradient. If a fill or stroke operation is not required, set the relevant parameter to NULL.

    - + + Operation successful. + Function call missing argument value(s) + +
    + + + FlushMatrix + Flushes matrix changes to a vector. + ERR vecFlushMatrix(struct VectorMatrix * Matrix) + + The matrix to be flushed. + + +

    If the matrices values of a vector have been directly modified by the client, the changes will need to be flushed in order to have those changes reflected on the display. This needs to be done before the next draw cycle.

    +

    Note that if the client uses API functions to modify a VectorMatrix, a call to FlushMatrix() is unnecessary as the vector will have already been marked for an update.

    +
    + Operation successful. Function call missing argument value(s) @@ -162,7 +197,7 @@ GenerateEllipse Generates an elliptical path. - ERROR vecGenerateEllipse(DOUBLE CX, DOUBLE CY, DOUBLE RX, DOUBLE RY, LONG Vertices, APTR * Path) + ERR vecGenerateEllipse(DOUBLE CX, DOUBLE CY, DOUBLE RX, DOUBLE RY, LONG Vertices, APTR * Path) Horizontal center point of the ellipse. Vertical center point of the ellipse. @@ -174,7 +209,7 @@

    Use GenerateEllipse() to create an elliptical path suitable for passing to vector functions that receive a Path parameter. The path must be manually deallocated with FreePath once it is no longer required.

    - + Operation successful. A call to AllocMemory() failed to create a new memory block. Function call missing argument value(s) @@ -184,7 +219,7 @@ GeneratePath Generates a path from an SVG path command sequence, or an empty path for custom configuration. - ERROR vecGeneratePath(CSTRING Sequence, APTR * Path) + ERR vecGeneratePath(CSTRING Sequence, APTR * Path) The command sequence to process. If no sequence is specified then the path will be empty. A pointer variable that will receive the resulting path. @@ -207,7 +242,7 @@ Z: Close Path

    The use of lower case characters will indicate that the provided coordinates are relative (based on the coordinate of the previous command).

    If the Sequence is NULL then an empty path resource will be generated. This path will be suitable for passing to path modifying functions such as MoveTo and LineTo for custom path generation.

    - + Operation successful. A call to AllocMemory() failed to create a new memory block. Function call missing argument value(s) @@ -217,7 +252,7 @@ Z: Close Path GenerateRectangle Generate a rectangular path at (x,y) with size (width,height). - ERROR vecGenerateRectangle(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height, APTR * Path) + ERR vecGenerateRectangle(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height, APTR * Path) The horizontal position of the rectangle. The vertical position of the rectangle. @@ -228,13 +263,52 @@ Z: Close Path

    Use GenerateRectangle() to create a rectangular path suitable for passing to vector functions that receive a Path parameter. The path must be manually deallocated with FreePath once it is no longer required.

    - + Operation successful. A call to AllocMemory() failed to create a new memory block. Function call missing argument value(s)
    + + GetFontHandle + Returns a handle for a given font family. + ERR vecGetFontHandle(CSTRING Family, CSTRING Style, LONG Weight, LONG Size, APTR * Handle) + + The name of the font family to access. + The preferred style to choose from the family. Use "Regular" or NULL for the default. + Equivalent to CSS font-weight; a value of 400 or 0 will equate to normal. + The font-size, measured in pixels @ 72 DPI. + The resulting font handle is returned here. + + +

    For a given font family and size, this function will return a handle that can be passed to font querying functions.

    +

    The handle is deterministic and permanent, remaining valid for the lifetime of the program.

    +
    + + Operation successful. + Invalid arguments passed to function. + Function call missing argument value(s) + +
    + + + GetFontMetrics + Returns a set of display metric values for a font. + ERR vecGetFontMetrics(APTR Handle, struct FontMetrics * Info) + + A font handle obtained from GetFontHandle(). + The font metrics for the Handle will be stored here. + + +

    Call GetFontMetrics() to retrieve a basic set of display metrics measured in pixels (adjusted to the display's DPI) for a given font.

    +
    + + Operation successful. + Function call missing argument value(s) + +
    + GetVertex Retrieve the coordinates of the current vertex. @@ -282,7 +356,7 @@ Z: Close Path Multiply Combines a matrix with a series of matrix values. - ERROR vecMultiply(struct VectorMatrix * Matrix, DOUBLE ScaleX, DOUBLE ShearY, DOUBLE ShearX, DOUBLE ScaleY, DOUBLE TranslateX, DOUBLE TranslateY) + ERR vecMultiply(struct VectorMatrix * Matrix, DOUBLE ScaleX, DOUBLE ShearY, DOUBLE ShearX, DOUBLE ScaleY, DOUBLE TranslateX, DOUBLE TranslateY) The target transformation matrix. Matrix value A. @@ -295,7 +369,7 @@ Z: Close Path

    This function uses matrix multiplication to combine a set of values with a VectorMatrix structure.

    - + Operation successful. Function call missing argument value(s) @@ -304,7 +378,7 @@ Z: Close Path MultiplyMatrix Combines a source matrix with a target. - ERROR vecMultiplyMatrix(struct VectorMatrix * Target, struct VectorMatrix * Source) + ERR vecMultiplyMatrix(struct VectorMatrix * Target, struct VectorMatrix * Source) The target transformation matrix. The source transformation matrix. @@ -312,7 +386,7 @@ Z: Close Path

    This function uses matrix multiplication to combine a Source matrix with a Target.

    - + Operation successful. Function call missing argument value(s) @@ -321,7 +395,7 @@ Z: Close Path ParseTransform Parse an SVG transformation string and apply the values to a matrix. - ERROR vecParseTransform(struct VectorMatrix * Matrix, CSTRING Transform) + ERR vecParseTransform(struct VectorMatrix * Matrix, CSTRING Transform) The target transformation matrix. The transform to apply, expressed as a string instruction. @@ -331,7 +405,7 @@ Z: Close Path

    The string must be written using SVG guidelines for the transform attribute. For example, skewX(20) rotate(45 50 50) would be valid. Transform instructions are applied in reverse, as per the standard.

    Note that any existing transforms applied to the matrix will be cancelled as a result of calling this function. If existing matrix values need to be retained, create a fresh matrix and use Multiply to combine them.

    - + Operation successful. Function call missing argument value(s) @@ -339,22 +413,21 @@ Z: Close Path ReadPainter - Parses a painter string into its colour, gradient and image values. - ERROR vecReadPainter(objVectorScene * Scene, CSTRING IRI, struct FRGB * RGB, objVectorGradient ** Gradient, objVectorImage ** Image, objVectorPattern ** Pattern) + Parses a painter string to its colour, gradient, pattern or image value. + ERR vecReadPainter(objVectorScene * Scene, CSTRING IRI, struct VectorPainter * Painter, CSTRING * Result) Optional. Required if url() references are to be resolved. The IRI string to be translated. - A colour will be returned here if specified in the IRI. - A VectorGradient will be returned here if specified in the IRI. - A VectorImage will be returned here if specified in the IRI. - A VectorPattern will be returned here if specified in the IRI. + This VectorPainter structure will store the deserialised result. + Optional pointer for storing the end of the parsed IRI string. NULL is returned if there is no further content to parse. -

    This function will parse an SVG style IRI into its equivalent internal lookup values. The results can then be processed for rendering a stroke or fill operation in the chosen style.

    -

    Colours can be referenced using one of three methods. Colour names such as orange and red are accepted. Hexadecimal RGB values are supported in the format #RRGGBBAA. Floating point RGB is supported as rgb(r,g,b,a) whereby the component values range between 0.0 and 1.0.

    +

    This function will parse an SVG style IRI into its equivalent logical values. The results can then be processed for rendering a stroke or fill operation in the chosen style.

    +

    Colours can be referenced using one of three methods. Colour names such as orange and red are accepted. Hexadecimal RGB values are supported in the format #RRGGBBAA. Floating point RGB is supported as rgb(r,g,b,a) whereby the component values range between 0.0 and 255.0.

    A Gradient, Image or Pattern can be referenced using the 'url(#name)' format, where the 'name' is a definition that has been registered with the provided Scene object. If Scene is NULL then it will not be possible to find the reference. Any failure to lookup a reference will be silently discarded.

    +

    A VectorPainter structure must be provided by the client and will be used to store the final result. All pointers that are returned will remain valid as long as the provided Scene exists with its registered painter definitions. An optional Result string can store a reference to the character up to which the IRI was parsed.

    - + Operation successful. General failure. Function call missing argument value(s) @@ -364,14 +437,14 @@ Z: Close Path ResetMatrix Resets a transformation matrix to its default state. - ERROR vecResetMatrix(struct VectorMatrix * Matrix) + ERR vecResetMatrix(struct VectorMatrix * Matrix) The target transformation matrix.

    Call ResetMatrix() to reset a transformation matrix to its default state, undoing all former transform operations.

    - + Operation successful. Function call missing argument value(s) @@ -393,7 +466,7 @@ Z: Close Path Rotate Applies a rotation transformation to a matrix. - ERROR vecRotate(struct VectorMatrix * Matrix, DOUBLE Angle, DOUBLE CenterX, DOUBLE CenterY) + ERR vecRotate(struct VectorMatrix * Matrix, DOUBLE Angle, DOUBLE CenterX, DOUBLE CenterY) The target transformation matrix. Angle of rotation, in degrees. @@ -403,7 +476,7 @@ Z: Close Path

    This function will apply a rotation transformation to a matrix. By default, rotation will occur around point (0,0) unless CenterX and CenterY values are specified.

    - + Operation successful. Function call missing argument value(s) @@ -412,7 +485,7 @@ Z: Close Path Scale Scale the size of the vector by (x,y) - ERROR vecScale(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y) + ERR vecScale(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y) The target transformation matrix. The scale factor on the x-axis. @@ -423,7 +496,7 @@ Z: Close Path

    Scaling is relative to position (0,0). If the width and height of the vector path needs to be transformed without affecting its top-left position, the client must translate the path to (0,0) around its center point. The path should then be scaled before being transformed back to its original top-left coordinate.

    The scale operation can also be used to flip a vector path if negative values are used. For instance, a value of -1.0 on the x axis would result in a 1:1 flip across the horizontal.

    - + Operation successful. Function call missing argument value(s) @@ -432,7 +505,7 @@ Z: Close Path Skew Skews the matrix along the horizontal and/or vertical axis. - ERROR vecSkew(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y) + ERR vecSkew(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y) The target transformation matrix. The angle to skew along the horizontal. @@ -441,7 +514,7 @@ Z: Close Path

    The Skew function applies a skew transformation to the horizontal and/or vertical axis of the matrix. Valid X and Y values are in the range of -90 < Angle < 90.

    - + Operation successful. A specified number is outside of the valid range. Function call missing argument value(s) @@ -480,10 +553,26 @@ Z: Close Path
    + + StringWidth + Calculate the pixel width of a UTF-8 string, for a given font. + DOUBLE vecStringWidth(APTR FontHandle, CSTRING String, LONG Chars) + + A font handle obtained from GetFontHandle(). + Pointer to a null-terminated string. + The maximum number of unicode characters to process in calculating the string width. Set to -1 for all chars. + + +

    This function calculates the pixel width of a string, in relation to a known font. The function takes into account any line-feeds that are encountered, so if the String contains multiple lines, then the width of the longest line will be returned.

    +

    The font's kerning specifications will be taken into account when computing the distance between glyphs.

    +
    + The pixel width of the string is returned. +
    + Translate Translates the vector by (X,Y). - ERROR vecTranslate(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y) + ERR vecTranslate(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y) The target transformation matrix. Translation along the x-axis. @@ -492,7 +581,7 @@ Z: Close Path

    This function will translate the matrix in the direction of the provided (X,Y) values.

    - + Operation successful. Function call missing argument value(s) @@ -630,7 +719,7 @@ Z: Close Path Synonym for FINAL_PATH | BASE_PATH | TRANSFORM The base path (shape of the vector) must be recalculated. - The final path will need to be recalculated, so as to take transforms and/or relative coordinates into account. + The final path will need to be recalculated, so as to take transforms and/or scaled coordinates into account. The transform matrix must be recalculated. This includes movement, e.g. changing the CX,CY of an ellipse. @@ -652,6 +741,11 @@ Z: Close Path The transformation step will not be applied to the vector's path. + + Apply fill instructions when drawing the clipping path(s). + Apply stroke instructions when drawing the clipping path(s). + + Inherit the colour space option from the parent vector. Linear RGB is the default colour space for SVG and produces the best results. @@ -663,6 +757,11 @@ Z: Close Path The vector holds the user's input focus. + + Scale X/Y values independently and in relation to the width/height of the parent viewport. + Scale X/Y values on a 1:1 basis, in relation to the diagonal of the parent viewport. + + This rule determines the 'insideness' of a point on the canvas by drawing a ray from that point to infinity in any direction and counting the number of path segments from the given shape that the ray crosses. If this number is odd, the point is inside; if even, the point is outside. The rule is inherited from the parent vector(s). @@ -679,15 +778,15 @@ Z: Close Path X2 is fixed Y1 is fixed Y2 is fixed - CX is relative - CY is relative - FX is relative - FY is relative - Radius is relative - X1 is relative - X2 is relative - Y1 is relative - Y2 is relative + CX is scaled + CY is scaled + FX is scaled + FY is scaled + Radius is scaled + X1 is scaled + X2 is scaled + Y1 is scaled + Y2 is scaled @@ -808,13 +907,14 @@ Z: Close Path Enable overlining of the text. Turns on overwrite mode (if off, insert mode is enabled). Rasterise glyphs to a texture cache for very fast rendering. This feature is not compatible with scalable graphics conventions. + Hide all characters from the UI by using generic symbols in place of glyphs. Enable underlining of the text. - Coordinates are relative to the object's bounding box. + Coordinates are scaled to the object's bounding box. - Coordinates are relative to the current viewport. + Coordinates are scaled to the current viewport. @@ -831,6 +931,13 @@ Z: Close Path + + Capitalised font height + Vertical advance from one line to the next + Height from the baseline to the top of the font, including accents. + Height from the baseline to the bottom of the font + + An offset in the range of 0 - 1.0 A floating point RGB value. @@ -843,12 +950,11 @@ Z: Close Path The command type (PE value) - Private Equivalent to the large-arc-flag in SVG, it ensures that the arc follows the longest drawing path when TRUE. Equivalent to the sweep-flag in SVG, it inverts the default behaviour in generating arc paths. Private - The targeted X coordinate (absolute or relative) for the command - The targeted Y coordinate (absolute or relative) for the command + The targeted X coordinate (absolute or scaled) for the command + The targeted Y coordinate (absolute or scaled) for the command Private Private The X2 coordinate for curve commands, or RX for arcs @@ -874,11 +980,18 @@ Z: Close Path Matrix value F + + A VectorPattern object, suitable for pattern based fills. + A VectorImage object, suitable for image fills. + A VectorGradient object, suitable for gradient fills. + A single RGB colour definition, suitable for block colour fills. + + The X coordinate of this point. The Y coordinate of this point. - TRUE if the X value is relative to its viewport (between 0 and 1.0). - TRUE if the Y value is relative to its viewport (between 0 and 1.0). + TRUE if the X value is scaled to its viewport (between 0 and 1.0). + TRUE if the Y value is scaled to its viewport (between 0 and 1.0). diff --git a/examples/benchmark_particles.fluid b/examples/benchmark_particles.fluid index eadc1104b..38fc73a15 100644 --- a/examples/benchmark_particles.fluid +++ b/examples/benchmark_particles.fluid @@ -56,7 +56,7 @@ function updateTime(elapsed) totalTime = totalTime / #glTimes local fps = 1000000 / totalTime - if glFPS then glFPS.string = string.format('Render Time: %.2fms, FPS: %.0f', totalTime/1000, fps) end + if glFPS then glFPS.string = string.format('FPS: %.0f', fps) end if (#glTimes >= 50) and (fps > glBestFPS) then glBestFPS = fps @@ -157,6 +157,16 @@ function timer(Subscriber, Elapsed, Current) glViewport.acDraw() updateTime(glScene.renderTime) + + if (math.round(Current / 1000000) % 4 == 0) then + if not glPrinted then + glPrinted = true + print('Best frame rate: ' .. math.round(glBestFPS)) + glBestFPS = 0 + end + else + glPrinted = false + end end ---------------------------------------------------------------------------------------------------------------------- @@ -257,5 +267,3 @@ end glWindow:show() processing.sleep() - - print('Best frame rate: ' .. math.round(glBestFPS)) diff --git a/examples/dialog.fluid b/examples/dialog.fluid new file mode 100644 index 000000000..f89ffdc2b --- /dev/null +++ b/examples/dialog.fluid @@ -0,0 +1,35 @@ +--[[ +Dialog test +--]] + + require 'gui/dialog' + + gui.dialog.message({ + modal = true, + image = 'items/warning', + title = 'Hamlet has a question', + message = 'To be or not to be?', + userInput = 'That is the question', + checkboxLabel = '\'Tis nobler to suffer', + quit = true, + options = { + { id=1, text='To be', icon='items/checkmark' }, + { id=2, text='Not to be', icon='items/cancel' } + }, + feedback = function(Dialog, Response, State) + if Response then + print('User selected option ' .. Response.id) + end + if State then + if State.input then + print('User entered string: ' .. State.input) + end + if State.checkbox then + print('User activated the checkbox') + end + end + end + }) + + processing.sleep() -- Will sleep until the window sends MSGID_QUIT + diff --git a/examples/keyboard.fluid b/examples/keyboard.fluid index 52606023e..3a4d67340 100644 --- a/examples/keyboard.fluid +++ b/examples/keyboard.fluid @@ -10,7 +10,7 @@ A basic demonstration of receiving keyboard input from a viewport. local viewport = win:clientViewport({ aspectRatio = ARF_MEET }) local text = viewport.new('VectorText', { - string='Press a key', face='Open Sans', fontSize=60, y=50, x=10, fill='rgb(0,0,0)' + string='Press a key', face='Noto Sans', fontSize=60, y=50, x=10, fill='rgb(0,0,0)' }) -- Create a keyboard subscription to the window's main viewport. The applied function will be called every time diff --git a/examples/view_svg.fluid b/examples/view_svg.fluid index bb547b743..b41e09b21 100644 --- a/examples/view_svg.fluid +++ b/examples/view_svg.fluid @@ -7,6 +7,11 @@ Example: parasol view_svg.fluid file=[Path] require 'gui' require 'gui/window' + if not arg('file') then + print('Usage: file=[Path]') + return + end + glWindow = gui.window({ center = true, width = arg('width', 800), @@ -18,14 +23,7 @@ Example: parasol view_svg.fluid file=[Path] }) glScene = glWindow.scene - glViewport = glScene.new('VectorViewport', { - aspectRatio = ARF_MEET, x=glWindow.client.left, y=glWindow.client.top, xOffset=glWindow.client.right, yOffset=glWindow.client.bottom - }) - - if not arg('file') then - print('Usage: file=[Path]') - return - end + glViewport = glWindow:clientViewport({ aspectRatio = ARF_MEET }) if mSys.AnalysePath(arg('file')) != ERR_Okay then error('Unable to load file ' .. arg('file')) @@ -35,15 +33,10 @@ Example: parasol view_svg.fluid file=[Path] -- Check if this is a fixed size SVG (default is scaled) - local scaled = true if (glViewport.width == glScene.viewport.width) and (glViewport.height == glScene.viewport.height) then - scaled = true + glScaled = true else - scaled = false - end - - svg.frameCallback = function(SVG) - glWindow.surface.acDraw() + glScaled = false end if (svg.frameRate < 60) then svg.frameRate = 60 end @@ -54,6 +47,6 @@ Example: parasol view_svg.fluid file=[Path] glWindow:setTitle(arg('file')) glWindow:show() ------------------------------------------------------------------------------- +---------------------------------------------------------------------------------------------------------------------- processing.sleep() diff --git a/examples/widgets.fluid b/examples/widgets.fluid index 2f11cc62c..85e9ffa61 100644 --- a/examples/widgets.fluid +++ b/examples/widgets.fluid @@ -125,10 +125,10 @@ end end) local text = viewport.new('vectortext', { - x=win.margins.left, y=y, string='Parasol interfaces are drawn using real-time vector graphics', face='Open Sans', fontSize=20, fill='rgb(0,0,0)', textflags='!editable' + x=win.margins.left, y=y, string='Parasol interfaces are drawn using real-time vector graphics', face='Noto Sans', fontSize=20, fill='rgb(0,0,0)', textflags='!editable' }) - text.y = y + text.font.height - y = y + text.font.height + 14 + text.y = y + text.fontSize + y = y + text.fontSize + 14 local msgButton = gui.button({ target = viewport, @@ -140,7 +140,7 @@ end activate = function(Widget) gui.dialog.message({ modal = true, - image = 'icons:items/warning', + image = 'items/warning', title = 'Hamlet has a question', message = 'To be or not to be?', userInput = 'That is the question', @@ -211,7 +211,7 @@ end if (not Accepted) then print('Dialog was cancelled.') else - print("The user selected '" .. Dialog.face .. "', size " .. Dialog.size .. ", style '" .. Dialog.style .. "'") + print("The user selected '" .. Dialog.face .. "', size " .. Dialog.pointSize .. ", style '" .. Dialog.style .. "'") print("This can be compacted to '" .. Dialog.compactFace .. "'") end end diff --git a/include/parasol/main.h b/include/parasol/main.h index 31f2d1a23..3262031b6 100644 --- a/include/parasol/main.h +++ b/include/parasol/main.h @@ -33,26 +33,28 @@ namespace pf { +DEFINE_ENUM_FLAG_OPERATORS(ERR) + template class ScopedAccessMemory { // C++ wrapper for automatically releasing shared memory public: LONG id; T *ptr; - ERROR error; + ERR error; ScopedAccessMemory(LONG ID, MEM Flags, LONG Milliseconds = 5000) { id = ID; error = AccessMemory(ID, Flags, Milliseconds, (APTR *)&ptr); } - ~ScopedAccessMemory() { if (!error) ReleaseMemory(ptr); } + ~ScopedAccessMemory() { if (error IS ERR::Okay) ReleaseMemory(ptr); } - bool granted() { return error == ERR_Okay; } + bool granted() { return error == ERR::Okay; } void release() { - if (!error) { + if (error IS ERR::Okay) { ReleaseMemory(ptr); - error = ERR_NotLocked; + error = ERR::NotLocked; } } }; @@ -76,13 +78,35 @@ template deferred_call Defer(F&& f) { return deferred_call(std::forward(f)); } +//******************************************************************************************************************** +// Deleter for use with std::unique_ptr to free objects correctly on destruction. Note that these always assume that +// the object pointer remains safe (cannot be deleted by external factors). +// +// E.g. std::unique_ptr> viewport; + +template struct DeleteObject { + void operator()(T *Object) const { if (Object) FreeResource(Object->UID); } +}; + +// Simplify the creation of unique pointers with the destructor + +template std::unique_ptr make_unique_object(T *Object) { + return std::unique_ptr(Object, DeleteObject{}); +} + +// Variant for std::shared_ptr + +template std::shared_ptr make_shared_object(T *Object) { + return std::shared_ptr(Object, DeleteObject{}); +} + //******************************************************************************************************************** // Scoped object locker. Use granted() to confirm that the lock has been granted. template class ScopedObjectLock { // C++ wrapper for automatically releasing an object public: - ERROR error; + ERR error; T *obj; ScopedObjectLock(OBJECTID ObjectID, LONG Milliseconds = 3000) { @@ -94,26 +118,126 @@ class ScopedObjectLock { // C++ wrapper for automatically releasing an object obj = (T *)Object; } - ScopedObjectLock() { obj = NULL; error = ERR_NotLocked; } - ~ScopedObjectLock() { if (!error) ReleaseObject((OBJECTPTR)obj); } - bool granted() { return error == ERR_Okay; } + ScopedObjectLock() { obj = NULL; error = ERR::NotLocked; } + ~ScopedObjectLock() { if (error IS ERR::Okay) ReleaseObject((OBJECTPTR)obj); } + bool granted() { return error == ERR::Okay; } T * operator->() { return obj; }; // Promotes underlying methods and fields T * & operator*() { return obj; }; // To allow object pointer referencing when calling functions }; //******************************************************************************************************************** -// Resource guard for any allocation that can be freed with FreeResource() +// Resource guard for any allocation that can be freed with FreeResource(). Retains the resource ID rather than the +// pointer to ensure that termination is safe even if the original resource gets terminated elsewhere. // // Usage: pf::GuardedResource resource(thing) template -class GuardedResource { // C++ wrapper for terminating resources when scope is lost +class GuardedResource { + private: + MEMORYID id; + public: + GuardedResource(T Resource) { + static_assert(std::is_pointer::value, "The resource value must be a pointer"); + id = ((LONG *)Resource)[-2]; + } + ~GuardedResource() { FreeResource(id); } +}; + +//******************************************************************************************************************** +// The object equivalent of GuardedResource. Also guarantees safety for object termination. + +template +class GuardedObject { private: - T *resource; + C * count; // Count of GuardedObjects accessing the same resource. Can be LONG (non-threaded) or std::atomic_int + T * object; + public: - GuardedResource(T Resource) { resource = Resource; } - ~GuardedResource() { FreeResource(resource); } + OBJECTID id; // Object UID + + // Constructors + + GuardedObject() : count(new C(1)), object(NULL), id(0) { } + + GuardedObject(T *Object) : count(new C(1)), object(Object), id(Object->UID) { + static_assert(std::is_base_of_v, "The resource value must belong to BaseClass"); + } + + GuardedObject(const GuardedObject &other) { // Copy constructor + if (other.object) { + object = other.object; + count = other.count; + count[0]++; + } + else { // If the other object is undefined then use a default state + object = NULL; + id = 0; + count = new C(1); + } + } + + GuardedObject(GuardedObject &&other) { // Move constructor + id = other.id; + object = other.object; + count = other.count; + other.count = NULL; + } + + // Destructor + + ~GuardedObject() { + if (!count) return; // The count can be empty if this GuardedObject was moved + + if (!--count[0]) { + if (id) FreeResource(id); + delete count; + } + } + + // Assignments + + GuardedObject & operator = (const GuardedObject &other) { // Copy assignment + if (this == &other) return *this; + if (!--count[0]) delete count; + if (other.object) { + object = other.object; + count = other.count; + count[0]++; + } + else { // If the other object is undefined then we reset our state with no count inheritance. + object = NULL; + id = 0; + count[0] = 1; + } + return *this; + } + + GuardedObject & operator = (GuardedObject &&other) { // Move assignment + if (this == &other) return *this; + if (!--count[0]) delete count; + id = other.id; + object = other.object; + count = other.count; + other.count = NULL; + return *this; + } + + // Public methods + + inline void set(T *Object) { // set() requires caution as the object reference is modified without adjusting the counter + if (!Object) return; + else if (count[0] IS 1) { + object = Object; + id = Object->UID; + } + else { pf::Log log(__FUNCTION__); log.warning(ERR::InUse); } + } + + constexpr bool empty() { return !object; } + + T * operator->() { return object; }; // Promotes underlying methods and fields + T * & operator*() { return object; }; // To allow object pointer referencing when calling functions }; //******************************************************************************************************************** @@ -152,6 +276,9 @@ inline FieldValue Location(const std::string &Value) { return FieldValue(FID_Loc constexpr FieldValue Args(CSTRING Value) { return FieldValue(FID_Args, Value); } inline FieldValue Args(const std::string &Value) { return FieldValue(FID_Args, Value.c_str()); } +constexpr FieldValue Fill(CSTRING Value) { return FieldValue(FID_Fill, Value); } +inline FieldValue Fill(const std::string &Value) { return FieldValue(FID_Fill, Value.c_str()); } + constexpr FieldValue Statement(CSTRING Value) { return FieldValue(FID_Statement, Value); } inline FieldValue Statement(const std::string &Value) { return FieldValue(FID_Statement, Value.c_str()); } @@ -182,6 +309,11 @@ inline FieldValue FileDescription(const std::string &Value) { return FieldValue( constexpr FieldValue FileHeader(CSTRING Value) { return FieldValue(FID_FileHeader, Value); } inline FieldValue FileHeader(const std::string &Value) { return FieldValue(FID_FileHeader, Value.c_str()); } +constexpr FieldValue FontSize(DOUBLE Value) { return FieldValue(FID_FontSize, Value); } +constexpr FieldValue FontSize(LONG Value) { return FieldValue(FID_FontSize, Value); } +constexpr FieldValue FontSize(CSTRING Value) { return FieldValue(FID_FontSize, Value); } +inline FieldValue FontSize(const std::string &Value) { return FieldValue(FID_FontSize, Value.c_str()); } + constexpr FieldValue ArchiveName(CSTRING Value) { return FieldValue(FID_ArchiveName, Value); } inline FieldValue ArchiveName(const std::string &Value) { return FieldValue(FID_ArchiveName, Value.c_str()); } @@ -205,6 +337,12 @@ constexpr FieldValue Point(LONG Value) { return FieldValue(FID_Point, Value); } constexpr FieldValue Point(CSTRING Value) { return FieldValue(FID_Point, Value); } inline FieldValue Point(const std::string &Value) { return FieldValue(FID_Point, Value.c_str()); } +constexpr FieldValue Points(CSTRING Value) { return FieldValue(FID_Points, Value); } +inline FieldValue Points(const std::string &Value) { return FieldValue(FID_Points, Value.c_str()); } + +constexpr FieldValue Pretext(CSTRING Value) { return FieldValue(FID_Pretext, Value); } +inline FieldValue Pretext(const std::string &Value) { return FieldValue(FID_Pretext, Value.c_str()); } + constexpr FieldValue Acceleration(DOUBLE Value) { return FieldValue(FID_Acceleration, Value); } constexpr FieldValue Actions(CPTR Value) { return FieldValue(FID_Actions, Value); } constexpr FieldValue AmtColours(LONG Value) { return FieldValue(FID_AmtColours, Value); } @@ -216,14 +354,17 @@ constexpr FieldValue Category(CCF Value) { return FieldValue(FID_Category, LONG( constexpr FieldValue ClassID(LONG Value) { return FieldValue(FID_ClassID, Value); } constexpr FieldValue ClassVersion(DOUBLE Value) { return FieldValue(FID_ClassVersion, Value); } constexpr FieldValue Closed(bool Value) { return FieldValue(FID_Closed, (Value ? 1 : 0)); } +constexpr FieldValue Cursor(PTC Value) { return FieldValue(FID_Cursor, LONG(Value)); } constexpr FieldValue DataFlags(MEM Value) { return FieldValue(FID_DataFlags, LONG(Value)); } constexpr FieldValue DoubleClick(DOUBLE Value) { return FieldValue(FID_DoubleClick, Value); } constexpr FieldValue Feedback(CPTR Value) { return FieldValue(FID_Feedback, Value); } constexpr FieldValue Fields(const FieldArray *Value) { return FieldValue(FID_Fields, Value, FD_ARRAY); } constexpr FieldValue Flags(LONG Value) { return FieldValue(FID_Flags, Value); } +constexpr FieldValue Font(OBJECTPTR Value) { return FieldValue(FID_Font, Value); } constexpr FieldValue HostScene(OBJECTPTR Value) { return FieldValue(FID_HostScene, Value); } constexpr FieldValue Incoming(CPTR Value) { return FieldValue(FID_Incoming, Value); } constexpr FieldValue Input(CPTR Value) { return FieldValue(FID_Input, Value); } +constexpr FieldValue LineLimit(LONG Value) { return FieldValue(FID_LineLimit, Value); } constexpr FieldValue Listener(LONG Value) { return FieldValue(FID_Listener, Value); } constexpr FieldValue MatrixColumns(LONG Value) { return FieldValue(FID_MatrixColumns, Value); } constexpr FieldValue MatrixRows(LONG Value) { return FieldValue(FID_MatrixRows, Value); } @@ -242,9 +383,13 @@ constexpr FieldValue Routine(CPTR Value) { return FieldValue(FID_Routine, Value) constexpr FieldValue Size(LONG Value) { return FieldValue(FID_Size, Value); } constexpr FieldValue Speed(DOUBLE Value) { return FieldValue(FID_Speed, Value); } constexpr FieldValue StrokeWidth(DOUBLE Value) { return FieldValue(FID_StrokeWidth, Value); } +constexpr FieldValue Surface(OBJECTID Value) { return FieldValue(FID_Surface, Value); } constexpr FieldValue Target(OBJECTID Value) { return FieldValue(FID_Target, Value); } +constexpr FieldValue Target(OBJECTPTR Value) { return FieldValue(FID_Target, Value); } constexpr FieldValue UserData(CPTR Value) { return FieldValue(FID_UserData, Value); } constexpr FieldValue Version(DOUBLE Value) { return FieldValue(FID_Version, Value); } +constexpr FieldValue Viewport(OBJECTID Value) { return FieldValue(FID_Viewport, Value); } +constexpr FieldValue Viewport(OBJECTPTR Value) { return FieldValue(FID_Viewport, Value); } constexpr FieldValue WheelSpeed(DOUBLE Value) { return FieldValue(FID_WheelSpeed, Value); } constexpr FieldValue WindowHandle(APTR Value) { return FieldValue(FID_WindowHandle, Value); } constexpr FieldValue WindowHandle(LONG Value) { return FieldValue(FID_WindowHandle, Value); } @@ -297,27 +442,27 @@ template FieldValue PageHeight(T Value) { } template FieldValue Radius(T Value) { - static_assert(std::is_arithmetic::value || std::is_class_v, "Radius value must be numeric"); + static_assert(std::is_arithmetic::value || std::is_base_of_v, "Radius value must be numeric"); return FieldValue(FID_Radius, Value); } template FieldValue CenterX(T Value) { - static_assert(std::is_arithmetic::value || std::is_class_v, "CenterX value must be numeric"); + static_assert(std::is_arithmetic::value || std::is_base_of_v, "CenterX value must be numeric"); return FieldValue(FID_CenterX, Value); } template FieldValue CenterY(T Value) { - static_assert(std::is_arithmetic::value || std::is_class_v, "CenterY value must be numeric"); + static_assert(std::is_arithmetic::value || std::is_base_of_v, "CenterY value must be numeric"); return FieldValue(FID_CenterY, Value); } template FieldValue FX(T Value) { - static_assert(std::is_arithmetic::value || std::is_class_v, "FX value must be numeric"); + static_assert(std::is_arithmetic::value || std::is_base_of_v, "FX value must be numeric"); return FieldValue(FID_FX, Value); } template FieldValue FY(T Value) { - static_assert(std::is_arithmetic::value || std::is_class_v, "FY value must be numeric"); + static_assert(std::is_arithmetic::value || std::is_base_of_v, "FY value must be numeric"); return FieldValue(FID_FY, Value); } @@ -352,42 +497,52 @@ template FieldValue ViewHeight(T Value) { } template FieldValue Width(T Value) { - static_assert(std::is_arithmetic::value || std::is_class_v, "Width value must be numeric"); + static_assert(std::is_arithmetic::value || std::is_base_of_v, "Width value must be numeric"); return FieldValue(FID_Width, Value); } template FieldValue Height(T Value) { - static_assert(std::is_arithmetic::value || std::is_class_v, "Height value must be numeric"); + static_assert(std::is_arithmetic::value || std::is_base_of_v, "Height value must be numeric"); return FieldValue(FID_Height, Value); } template FieldValue X(T Value) { - static_assert(std::is_arithmetic::value || std::is_class_v, "X value must be numeric"); + static_assert(std::is_arithmetic::value || std::is_base_of_v, "X value must be numeric"); return FieldValue(FID_X, Value); } +template FieldValue XOffset(T Value) { + static_assert(std::is_arithmetic::value || std::is_base_of_v, "XOffset value must be numeric"); + return FieldValue(FID_XOffset, Value); +} + template FieldValue Y(T Value) { - static_assert(std::is_arithmetic::value || std::is_class_v, "Y value must be numeric"); + static_assert(std::is_arithmetic::value || std::is_base_of_v, "Y value must be numeric"); return FieldValue(FID_Y, Value); } +template FieldValue YOffset(T Value) { + static_assert(std::is_arithmetic::value || std::is_base_of_v, "YOffset value must be numeric"); + return FieldValue(FID_YOffset, Value); +} + template FieldValue X1(T Value) { - static_assert(std::is_arithmetic::value || std::is_class_v, "X1 value must be numeric"); + static_assert(std::is_arithmetic::value || std::is_base_of_v, "X1 value must be numeric"); return FieldValue(FID_X1, Value); } template FieldValue Y1(T Value) { - static_assert(std::is_arithmetic::value || std::is_class_v, "Y1 value must be numeric"); + static_assert(std::is_arithmetic::value || std::is_base_of_v, "Y1 value must be numeric"); return FieldValue(FID_Y1, Value); } template FieldValue X2(T Value) { - static_assert(std::is_arithmetic::value || std::is_class_v, "X2 value must be numeric"); + static_assert(std::is_arithmetic::value || std::is_base_of_v, "X2 value must be numeric"); return FieldValue(FID_X2, Value); } template FieldValue Y2(T Value) { - static_assert(std::is_arithmetic::value || std::is_class_v, "Y2 value must be numeric"); + static_assert(std::is_arithmetic::value || std::is_base_of_v, "Y2 value must be numeric"); return FieldValue(FID_Y2, Value); } diff --git a/include/parasol/modules/audio.h b/include/parasol/modules/audio.h index ee4ac7acc..d920b3fd4 100644 --- a/include/parasol/modules/audio.h +++ b/include/parasol/modules/audio.h @@ -1,7 +1,7 @@ #pragma once // Name: audio.h -// Copyright: Paul Manias © 2002-2023 +// Copyright: Paul Manias © 2002-2024 // Generator: idl-c #include @@ -178,48 +178,48 @@ struct sndAddStream { FUNCTION Callback; FUNCTION OnStop; SFM SampleFormat; LONG struct sndBeep { LONG Pitch; LONG Duration; LONG Volume; }; struct sndSetVolume { LONG Index; CSTRING Name; SVF Flags; LONG Channel; DOUBLE Volume; }; -INLINE ERROR sndOpenChannels(APTR Ob, LONG Total, LONG * Result) { +INLINE ERR sndOpenChannels(APTR Ob, LONG Total, LONG * Result) noexcept { struct sndOpenChannels args = { Total, (LONG)0 }; - ERROR error = Action(MT_SndOpenChannels, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_SndOpenChannels, (OBJECTPTR)Ob, &args); if (Result) *Result = args.Result; return(error); } -INLINE ERROR sndCloseChannels(APTR Ob, LONG Handle) { +INLINE ERR sndCloseChannels(APTR Ob, LONG Handle) noexcept { struct sndCloseChannels args = { Handle }; return(Action(MT_SndCloseChannels, (OBJECTPTR)Ob, &args)); } -INLINE ERROR sndAddSample(APTR Ob, FUNCTION OnStop, SFM SampleFormat, APTR Data, LONG DataSize, struct AudioLoop * Loop, LONG LoopSize, LONG * Result) { +INLINE ERR sndAddSample(APTR Ob, FUNCTION OnStop, SFM SampleFormat, APTR Data, LONG DataSize, struct AudioLoop * Loop, LONG LoopSize, LONG * Result) noexcept { struct sndAddSample args = { OnStop, SampleFormat, Data, DataSize, Loop, LoopSize, (LONG)0 }; - ERROR error = Action(MT_SndAddSample, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_SndAddSample, (OBJECTPTR)Ob, &args); if (Result) *Result = args.Result; return(error); } -INLINE ERROR sndRemoveSample(APTR Ob, LONG Handle) { +INLINE ERR sndRemoveSample(APTR Ob, LONG Handle) noexcept { struct sndRemoveSample args = { Handle }; return(Action(MT_SndRemoveSample, (OBJECTPTR)Ob, &args)); } -INLINE ERROR sndSetSampleLength(APTR Ob, LONG Sample, LARGE Length) { +INLINE ERR sndSetSampleLength(APTR Ob, LONG Sample, LARGE Length) noexcept { struct sndSetSampleLength args = { Sample, Length }; return(Action(MT_SndSetSampleLength, (OBJECTPTR)Ob, &args)); } -INLINE ERROR sndAddStream(APTR Ob, FUNCTION Callback, FUNCTION OnStop, SFM SampleFormat, LONG SampleLength, LONG PlayOffset, struct AudioLoop * Loop, LONG LoopSize, LONG * Result) { +INLINE ERR sndAddStream(APTR Ob, FUNCTION Callback, FUNCTION OnStop, SFM SampleFormat, LONG SampleLength, LONG PlayOffset, struct AudioLoop * Loop, LONG LoopSize, LONG * Result) noexcept { struct sndAddStream args = { Callback, OnStop, SampleFormat, SampleLength, PlayOffset, Loop, LoopSize, (LONG)0 }; - ERROR error = Action(MT_SndAddStream, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_SndAddStream, (OBJECTPTR)Ob, &args); if (Result) *Result = args.Result; return(error); } -INLINE ERROR sndBeep(APTR Ob, LONG Pitch, LONG Duration, LONG Volume) { +INLINE ERR sndBeep(APTR Ob, LONG Pitch, LONG Duration, LONG Volume) noexcept { struct sndBeep args = { Pitch, Duration, Volume }; return(Action(MT_SndBeep, (OBJECTPTR)Ob, &args)); } -INLINE ERROR sndSetVolume(APTR Ob, LONG Index, CSTRING Name, SVF Flags, LONG Channel, DOUBLE Volume) { +INLINE ERR sndSetVolume(APTR Ob, LONG Index, CSTRING Name, SVF Flags, LONG Channel, DOUBLE Volume) noexcept { struct sndSetVolume args = { Index, Name, Flags, Channel, Volume }; return(Action(MT_SndSetVolume, (OBJECTPTR)Ob, &args)); } @@ -242,78 +242,78 @@ class objAudio : public BaseClass { // Action stubs - inline ERROR activate() { return Action(AC_Activate, this, NULL); } - inline ERROR deactivate() { return Action(AC_Deactivate, this, NULL); } - inline ERROR init() { return InitObject(this); } - inline ERROR saveSettings() { return Action(AC_SaveSettings, this, NULL); } - inline ERROR saveToObject(OBJECTPTR Dest, CLASSID ClassID = 0) { + inline ERR activate() noexcept { return Action(AC_Activate, this, NULL); } + inline ERR deactivate() noexcept { return Action(AC_Deactivate, this, NULL); } + inline ERR init() noexcept { return InitObject(this); } + inline ERR saveSettings() noexcept { return Action(AC_SaveSettings, this, NULL); } + inline ERR saveToObject(OBJECTPTR Dest, CLASSID ClassID = 0) noexcept { struct acSaveToObject args = { Dest, { ClassID } }; return Action(AC_SaveToObject, this, &args); } // Customised field setting - inline ERROR setOutputRate(const LONG Value) { + inline ERR setOutputRate(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[1]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setInputRate(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setInputRate(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->InputRate = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setQuality(const LONG Value) { + inline ERR setQuality(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[5]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setFlags(const ADF Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setFlags(const ADF Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setBitDepth(const LONG Value) { + inline ERR setBitDepth(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[9]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setPeriods(const LONG Value) { + inline ERR setPeriods(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[10]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setPeriodSize(const LONG Value) { + inline ERR setPeriodSize(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[11]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - template inline ERROR setDevice(T && Value) { + template inline ERR setDevice(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[15]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setMasterVolume(const DOUBLE Value) { + inline ERR setMasterVolume(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[14]; return field->WriteValue(target, field, FD_DOUBLE, &Value, 1); } - inline ERROR setMute(const LONG Value) { + inline ERR setMute(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[7]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setStereo(const LONG Value) { + inline ERR setStereo(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[6]; return field->WriteValue(target, field, FD_LONG, &Value, 1); @@ -353,154 +353,155 @@ class objSound : public BaseClass { // Action stubs - inline ERROR activate() { return Action(AC_Activate, this, NULL); } - inline ERROR deactivate() { return Action(AC_Deactivate, this, NULL); } - inline ERROR disable() { return Action(AC_Disable, this, NULL); } - inline ERROR enable() { return Action(AC_Enable, this, NULL); } - inline ERROR getVar(CSTRING FieldName, STRING Buffer, LONG Size) { + inline ERR activate() noexcept { return Action(AC_Activate, this, NULL); } + inline ERR deactivate() noexcept { return Action(AC_Deactivate, this, NULL); } + inline ERR disable() noexcept { return Action(AC_Disable, this, NULL); } + inline ERR enable() noexcept { return Action(AC_Enable, this, NULL); } + inline ERR getVar(CSTRING FieldName, STRING Buffer, LONG Size) noexcept { struct acGetVar args = { FieldName, Buffer, Size }; - ERROR error = Action(AC_GetVar, this, &args); - if ((error) and (Buffer)) Buffer[0] = 0; + auto error = Action(AC_GetVar, this, &args); + if ((error != ERR::Okay) and (Buffer)) Buffer[0] = 0; return error; } - inline ERROR init() { return InitObject(this); } - template ERROR read(APTR Buffer, T Size, U *Result) { + inline ERR init() noexcept { return InitObject(this); } + template ERR read(APTR Buffer, T Size, U *Result) noexcept { static_assert(std::is_integral::value, "Result value must be an integer type"); static_assert(std::is_integral::value, "Size value must be an integer type"); - ERROR error; const LONG bytes = (Size > 0x7fffffff) ? 0x7fffffff : Size; struct acRead read = { (BYTE *)Buffer, bytes }; - if (!(error = Action(AC_Read, this, &read))) *Result = static_cast(read.Result); - else *Result = 0; - return error; + if (auto error = Action(AC_Read, this, &read); error IS ERR::Okay) { + *Result = static_cast(read.Result); + return ERR::Okay; + } + else { *Result = 0; return error; } } - template ERROR read(APTR Buffer, T Size) { + template ERR read(APTR Buffer, T Size) noexcept { static_assert(std::is_integral::value, "Size value must be an integer type"); const LONG bytes = (Size > 0x7fffffff) ? 0x7fffffff : Size; struct acRead read = { (BYTE *)Buffer, bytes }; return Action(AC_Read, this, &read); } - inline ERROR saveToObject(OBJECTPTR Dest, CLASSID ClassID = 0) { + inline ERR saveToObject(OBJECTPTR Dest, CLASSID ClassID = 0) noexcept { struct acSaveToObject args = { Dest, { ClassID } }; return Action(AC_SaveToObject, this, &args); } - inline ERROR seek(DOUBLE Offset, SEEK Position = SEEK::CURRENT) { + inline ERR seek(DOUBLE Offset, SEEK Position = SEEK::CURRENT) noexcept { struct acSeek args = { Offset, Position }; return Action(AC_Seek, this, &args); } - inline ERROR seekStart(DOUBLE Offset) { return seek(Offset, SEEK::START); } - inline ERROR seekEnd(DOUBLE Offset) { return seek(Offset, SEEK::END); } - inline ERROR seekCurrent(DOUBLE Offset) { return seek(Offset, SEEK::CURRENT); } - inline ERROR acSetVar(CSTRING FieldName, CSTRING Value) { + inline ERR seekStart(DOUBLE Offset) noexcept { return seek(Offset, SEEK::START); } + inline ERR seekEnd(DOUBLE Offset) noexcept { return seek(Offset, SEEK::END); } + inline ERR seekCurrent(DOUBLE Offset) noexcept { return seek(Offset, SEEK::CURRENT); } + inline ERR acSetVar(CSTRING FieldName, CSTRING Value) noexcept { struct acSetVar args = { FieldName, Value }; return Action(AC_SetVar, this, &args); } // Customised field setting - inline ERROR setVolume(const DOUBLE Value) { + inline ERR setVolume(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[14]; return field->WriteValue(target, field, FD_DOUBLE, &Value, 1); } - inline ERROR setPan(const DOUBLE Value) { + inline ERR setPan(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[4]; return field->WriteValue(target, field, FD_DOUBLE, &Value, 1); } - inline ERROR setPosition(const LARGE Value) { + inline ERR setPosition(const LARGE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[16]; return field->WriteValue(target, field, FD_LARGE, &Value, 1); } - inline ERROR setPriority(const LONG Value) { + inline ERR setPriority(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[13]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setLength(const LONG Value) { + inline ERR setLength(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[3]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setOctave(const LONG Value) { + inline ERR setOctave(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[10]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setFlags(const SDF Value) { + inline ERR setFlags(const SDF Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[8]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setFrequency(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setFrequency(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Frequency = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setPlayback(const LONG Value) { + inline ERR setPlayback(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[15]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setCompression(const LONG Value) { + inline ERR setCompression(const LONG Value) noexcept { this->Compression = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setBytesPerSecond(const LONG Value) { + inline ERR setBytesPerSecond(const LONG Value) noexcept { this->BytesPerSecond = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setBitsPerSample(const LONG Value) { + inline ERR setBitsPerSample(const LONG Value) noexcept { this->BitsPerSample = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setAudio(const OBJECTID Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setAudio(OBJECTID Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->AudioID = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setLoopStart(const LONG Value) { + inline ERR setLoopStart(const LONG Value) noexcept { this->LoopStart = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setLoopEnd(const LONG Value) { + inline ERR setLoopEnd(const LONG Value) noexcept { this->LoopEnd = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setStream(const STREAM Value) { + inline ERR setStream(const STREAM Value) noexcept { this->Stream = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setOnStop(FUNCTION Value) { + inline ERR setOnStop(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[11]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } - template inline ERROR setPath(T && Value) { + template inline ERR setPath(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[21]; return field->WriteValue(target, field, 0x08800500, to_cstring(Value), 1); } - template inline ERROR setNote(T && Value) { + template inline ERR setNote(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[20]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); @@ -516,50 +517,50 @@ class objSound : public BaseClass { struct AudioBase { #ifndef PARASOL_STATIC - ERROR (*_MixContinue)(objAudio * Audio, LONG Handle); - ERROR (*_MixFrequency)(objAudio * Audio, LONG Handle, LONG Frequency); - ERROR (*_MixMute)(objAudio * Audio, LONG Handle, LONG Mute); - ERROR (*_MixPan)(objAudio * Audio, LONG Handle, DOUBLE Pan); - ERROR (*_MixPlay)(objAudio * Audio, LONG Handle, LONG Position); - ERROR (*_MixRate)(objAudio * Audio, LONG Handle, LONG Rate); - ERROR (*_MixSample)(objAudio * Audio, LONG Handle, LONG Sample); - ERROR (*_MixStop)(objAudio * Audio, LONG Handle); - ERROR (*_MixStopLoop)(objAudio * Audio, LONG Handle); - ERROR (*_MixVolume)(objAudio * Audio, LONG Handle, DOUBLE Volume); - ERROR (*_MixStartSequence)(objAudio * Audio, LONG Handle); - ERROR (*_MixEndSequence)(objAudio * Audio, LONG Handle); + ERR (*_MixContinue)(objAudio * Audio, LONG Handle); + ERR (*_MixFrequency)(objAudio * Audio, LONG Handle, LONG Frequency); + ERR (*_MixMute)(objAudio * Audio, LONG Handle, LONG Mute); + ERR (*_MixPan)(objAudio * Audio, LONG Handle, DOUBLE Pan); + ERR (*_MixPlay)(objAudio * Audio, LONG Handle, LONG Position); + ERR (*_MixRate)(objAudio * Audio, LONG Handle, LONG Rate); + ERR (*_MixSample)(objAudio * Audio, LONG Handle, LONG Sample); + ERR (*_MixStop)(objAudio * Audio, LONG Handle); + ERR (*_MixStopLoop)(objAudio * Audio, LONG Handle); + ERR (*_MixVolume)(objAudio * Audio, LONG Handle, DOUBLE Volume); + ERR (*_MixStartSequence)(objAudio * Audio, LONG Handle); + ERR (*_MixEndSequence)(objAudio * Audio, LONG Handle); #endif // PARASOL_STATIC }; #ifndef PRV_AUDIO_MODULE #ifndef PARASOL_STATIC extern struct AudioBase *AudioBase; -inline ERROR sndMixContinue(objAudio * Audio, LONG Handle) { return AudioBase->_MixContinue(Audio,Handle); } -inline ERROR sndMixFrequency(objAudio * Audio, LONG Handle, LONG Frequency) { return AudioBase->_MixFrequency(Audio,Handle,Frequency); } -inline ERROR sndMixMute(objAudio * Audio, LONG Handle, LONG Mute) { return AudioBase->_MixMute(Audio,Handle,Mute); } -inline ERROR sndMixPan(objAudio * Audio, LONG Handle, DOUBLE Pan) { return AudioBase->_MixPan(Audio,Handle,Pan); } -inline ERROR sndMixPlay(objAudio * Audio, LONG Handle, LONG Position) { return AudioBase->_MixPlay(Audio,Handle,Position); } -inline ERROR sndMixRate(objAudio * Audio, LONG Handle, LONG Rate) { return AudioBase->_MixRate(Audio,Handle,Rate); } -inline ERROR sndMixSample(objAudio * Audio, LONG Handle, LONG Sample) { return AudioBase->_MixSample(Audio,Handle,Sample); } -inline ERROR sndMixStop(objAudio * Audio, LONG Handle) { return AudioBase->_MixStop(Audio,Handle); } -inline ERROR sndMixStopLoop(objAudio * Audio, LONG Handle) { return AudioBase->_MixStopLoop(Audio,Handle); } -inline ERROR sndMixVolume(objAudio * Audio, LONG Handle, DOUBLE Volume) { return AudioBase->_MixVolume(Audio,Handle,Volume); } -inline ERROR sndMixStartSequence(objAudio * Audio, LONG Handle) { return AudioBase->_MixStartSequence(Audio,Handle); } -inline ERROR sndMixEndSequence(objAudio * Audio, LONG Handle) { return AudioBase->_MixEndSequence(Audio,Handle); } +inline ERR sndMixContinue(objAudio * Audio, LONG Handle) { return AudioBase->_MixContinue(Audio,Handle); } +inline ERR sndMixFrequency(objAudio * Audio, LONG Handle, LONG Frequency) { return AudioBase->_MixFrequency(Audio,Handle,Frequency); } +inline ERR sndMixMute(objAudio * Audio, LONG Handle, LONG Mute) { return AudioBase->_MixMute(Audio,Handle,Mute); } +inline ERR sndMixPan(objAudio * Audio, LONG Handle, DOUBLE Pan) { return AudioBase->_MixPan(Audio,Handle,Pan); } +inline ERR sndMixPlay(objAudio * Audio, LONG Handle, LONG Position) { return AudioBase->_MixPlay(Audio,Handle,Position); } +inline ERR sndMixRate(objAudio * Audio, LONG Handle, LONG Rate) { return AudioBase->_MixRate(Audio,Handle,Rate); } +inline ERR sndMixSample(objAudio * Audio, LONG Handle, LONG Sample) { return AudioBase->_MixSample(Audio,Handle,Sample); } +inline ERR sndMixStop(objAudio * Audio, LONG Handle) { return AudioBase->_MixStop(Audio,Handle); } +inline ERR sndMixStopLoop(objAudio * Audio, LONG Handle) { return AudioBase->_MixStopLoop(Audio,Handle); } +inline ERR sndMixVolume(objAudio * Audio, LONG Handle, DOUBLE Volume) { return AudioBase->_MixVolume(Audio,Handle,Volume); } +inline ERR sndMixStartSequence(objAudio * Audio, LONG Handle) { return AudioBase->_MixStartSequence(Audio,Handle); } +inline ERR sndMixEndSequence(objAudio * Audio, LONG Handle) { return AudioBase->_MixEndSequence(Audio,Handle); } #else extern "C" { -extern ERROR sndMixContinue(objAudio * Audio, LONG Handle); -extern ERROR sndMixFrequency(objAudio * Audio, LONG Handle, LONG Frequency); -extern ERROR sndMixMute(objAudio * Audio, LONG Handle, LONG Mute); -extern ERROR sndMixPan(objAudio * Audio, LONG Handle, DOUBLE Pan); -extern ERROR sndMixPlay(objAudio * Audio, LONG Handle, LONG Position); -extern ERROR sndMixRate(objAudio * Audio, LONG Handle, LONG Rate); -extern ERROR sndMixSample(objAudio * Audio, LONG Handle, LONG Sample); -extern ERROR sndMixStop(objAudio * Audio, LONG Handle); -extern ERROR sndMixStopLoop(objAudio * Audio, LONG Handle); -extern ERROR sndMixVolume(objAudio * Audio, LONG Handle, DOUBLE Volume); -extern ERROR sndMixStartSequence(objAudio * Audio, LONG Handle); -extern ERROR sndMixEndSequence(objAudio * Audio, LONG Handle); +extern ERR sndMixContinue(objAudio * Audio, LONG Handle); +extern ERR sndMixFrequency(objAudio * Audio, LONG Handle, LONG Frequency); +extern ERR sndMixMute(objAudio * Audio, LONG Handle, LONG Mute); +extern ERR sndMixPan(objAudio * Audio, LONG Handle, DOUBLE Pan); +extern ERR sndMixPlay(objAudio * Audio, LONG Handle, LONG Position); +extern ERR sndMixRate(objAudio * Audio, LONG Handle, LONG Rate); +extern ERR sndMixSample(objAudio * Audio, LONG Handle, LONG Sample); +extern ERR sndMixStop(objAudio * Audio, LONG Handle); +extern ERR sndMixStopLoop(objAudio * Audio, LONG Handle); +extern ERR sndMixVolume(objAudio * Audio, LONG Handle, DOUBLE Volume); +extern ERR sndMixStartSequence(objAudio * Audio, LONG Handle); +extern ERR sndMixEndSequence(objAudio * Audio, LONG Handle); } #endif // PARASOL_STATIC #endif diff --git a/include/parasol/modules/core.h b/include/parasol/modules/core.h index cc8322739..51f0f5c15 100644 --- a/include/parasol/modules/core.h +++ b/include/parasol/modules/core.h @@ -1,7 +1,7 @@ #pragma once // Name: core.h -// Copyright: Paul Manias 1996-2023 +// Copyright: Paul Manias 1996-2024 // Generator: idl-c #include @@ -17,6 +17,11 @@ #include #include #include +#include +#endif + +#if defined(_DEBUG) && defined(__linux__) + #include #endif #ifndef DEFINE_ENUM_FLAG_OPERATORS @@ -330,7 +335,7 @@ enum class JTYPE : ULONG { SECONDARY = 0x00000001, ANCHORED = 0x00000002, DRAGGED = 0x00000004, - FEEDBACK = 0x00000008, + CROSSING = 0x00000008, DIGITAL = 0x00000010, ANALOG = 0x00000020, EXT_MOVEMENT = 0x00000040, @@ -347,51 +352,43 @@ DEFINE_ENUM_FLAG_OPERATORS(JTYPE) enum class JET : LONG { NIL = 0, - DIGITAL_X = 1, - DIGITAL_Y = 2, - BUTTON_1 = 3, - LMB = 3, - BUTTON_2 = 4, - RMB = 4, - BUTTON_3 = 5, - MMB = 5, - BUTTON_4 = 6, - BUTTON_5 = 7, - BUTTON_6 = 8, - BUTTON_7 = 9, - BUTTON_8 = 10, - BUTTON_9 = 11, - BUTTON_10 = 12, - TRIGGER_LEFT = 13, - TRIGGER_RIGHT = 14, - BUTTON_START = 15, - BUTTON_SELECT = 16, - LEFT_BUMPER_1 = 17, - LEFT_BUMPER_2 = 18, - RIGHT_BUMPER_1 = 19, - RIGHT_BUMPER_2 = 20, - ANALOG_X = 21, - ANALOG_Y = 22, - ANALOG_Z = 23, - ANALOG2_X = 24, - ANALOG2_Y = 25, - ANALOG2_Z = 26, - WHEEL = 27, - WHEEL_TILT = 28, - PEN_TILT_VERTICAL = 29, - PEN_TILT_HORIZONTAL = 30, - ABS_X = 31, - ABS_Y = 32, - ENTERED_SURFACE = 33, - ENTERED = 33, - LEFT_SURFACE = 34, - LEFT = 34, - PRESSURE = 35, - DEVICE_TILT_X = 36, - DEVICE_TILT_Y = 37, - DEVICE_TILT_Z = 38, - DISPLAY_EDGE = 39, - END = 40, + DIGITAL_XY = 1, + BUTTON_1 = 2, + LMB = 2, + BUTTON_2 = 3, + RMB = 3, + BUTTON_3 = 4, + MMB = 4, + BUTTON_4 = 5, + BUTTON_5 = 6, + BUTTON_6 = 7, + BUTTON_7 = 8, + BUTTON_8 = 9, + BUTTON_9 = 10, + BUTTON_10 = 11, + TRIGGER_LEFT = 12, + TRIGGER_RIGHT = 13, + BUTTON_START = 14, + BUTTON_SELECT = 15, + LEFT_BUMPER_1 = 16, + LEFT_BUMPER_2 = 17, + RIGHT_BUMPER_1 = 18, + RIGHT_BUMPER_2 = 19, + ANALOG_XY = 20, + ANALOG_Z = 21, + ANALOG2_XY = 22, + ANALOG2_Z = 23, + WHEEL = 24, + WHEEL_TILT = 25, + PEN_TILT_XY = 26, + ABS_XY = 27, + CROSSED_IN = 28, + CROSSED_OUT = 29, + PRESSURE = 30, + DEVICE_TILT_XY = 31, + DEVICE_TILT_Z = 32, + DISPLAY_EDGE = 33, + END = 34, }; // Field descriptors. @@ -433,7 +430,7 @@ enum class JET : LONG { #define FD_SYNONYM 0x00020000 #define FD_UNSIGNED 0x00040000 #define FD_RGB 0x00080000 -#define FD_PERCENTAGE 0x00200000 +#define FD_SCALED 0x00200000 #define FD_WORD 0x00400000 #define FD_STR 0x00800000 #define FD_STRING 0x00800000 @@ -489,43 +486,43 @@ enum class PTC : LONG { END = 25, }; -#define DMF_RELATIVE_X 0x00000001 -#define DMF_RELATIVE_Y 0x00000002 +#define DMF_SCALED_X 0x00000001 +#define DMF_SCALED_Y 0x00000002 #define DMF_FIXED_X 0x00000004 #define DMF_X 0x00000005 #define DMF_FIXED_Y 0x00000008 #define DMF_Y 0x0000000a -#define DMF_RELATIVE_X_OFFSET 0x00000010 -#define DMF_RELATIVE_Y_OFFSET 0x00000020 +#define DMF_SCALED_X_OFFSET 0x00000010 +#define DMF_SCALED_Y_OFFSET 0x00000020 #define DMF_FIXED_X_OFFSET 0x00000040 #define DMF_X_OFFSET 0x00000050 #define DMF_FIXED_Y_OFFSET 0x00000080 #define DMF_Y_OFFSET 0x000000a0 #define DMF_FIXED_HEIGHT 0x00000100 #define DMF_FIXED_WIDTH 0x00000200 -#define DMF_RELATIVE_HEIGHT 0x00000400 +#define DMF_SCALED_HEIGHT 0x00000400 #define DMF_HEIGHT 0x00000500 #define DMF_HEIGHT_FLAGS 0x000005a0 #define DMF_VERTICAL_FLAGS 0x000005aa -#define DMF_RELATIVE_WIDTH 0x00000800 +#define DMF_SCALED_WIDTH 0x00000800 #define DMF_WIDTH 0x00000a00 #define DMF_WIDTH_FLAGS 0x00000a50 #define DMF_HORIZONTAL_FLAGS 0x00000a55 #define DMF_FIXED_DEPTH 0x00001000 -#define DMF_RELATIVE_DEPTH 0x00002000 +#define DMF_SCALED_DEPTH 0x00002000 #define DMF_FIXED_Z 0x00004000 -#define DMF_RELATIVE_Z 0x00008000 -#define DMF_RELATIVE_RADIUS_X 0x00010000 +#define DMF_SCALED_Z 0x00008000 +#define DMF_SCALED_RADIUS_X 0x00010000 #define DMF_FIXED_RADIUS_X 0x00020000 -#define DMF_RELATIVE_CENTER_X 0x00040000 -#define DMF_RELATIVE_CENTER_Y 0x00080000 +#define DMF_SCALED_CENTER_X 0x00040000 +#define DMF_SCALED_CENTER_Y 0x00080000 #define DMF_FIXED_CENTER_X 0x00100000 #define DMF_FIXED_CENTER_Y 0x00200000 #define DMF_STATUS_CHANGE_H 0x00400000 #define DMF_STATUS_CHANGE_V 0x00800000 #define DMF_STATUS_CHANGE 0x00c00000 -#define DMF_RELATIVE_RADIUS_Y 0x01000000 -#define DMF_RELATIVE_RADIUS 0x01010000 +#define DMF_SCALED_RADIUS_Y 0x01000000 +#define DMF_SCALED_RADIUS 0x01010000 #define DMF_FIXED_RADIUS_Y 0x02000000 #define DMF_FIXED_RADIUS 0x02020000 @@ -736,10 +733,9 @@ enum class VLF : ULONG { CRITICAL = 0x00000008, INFO = 0x00000010, API = 0x00000020, - EXTAPI = 0x00000040, - DEBUG = 0x00000080, - TRACE = 0x00000100, - FUNCTION = 0x00000200, + DETAIL = 0x00000040, + TRACE = 0x00000080, + FUNCTION = 0x00000100, }; DEFINE_ENUM_FLAG_OPERATORS(VLF) @@ -1337,21 +1333,21 @@ struct dcKeyEntry { }; struct dcDeviceInput { - DOUBLE Value; // The value associated with the Type - LARGE Timestamp; // PreciseTime() of the recorded input - OBJECTID DeviceID; // The hardware device that this event originated from (note: This ID can be to a private/inaccessible object, the point is that the ID is unique) - JTYPE Flags; // Broad descriptors for the given Type. Automatically defined when delivered to the pointer object - JET Type; // JET constant + DOUBLE Values[2]; // The value(s) associated with the Type + LARGE Timestamp; // PreciseTime() of the recorded input + OBJECTID DeviceID; // The hardware device that this event originated from (note: This ID can be to a private/inaccessible object, the point is that the ID is unique) + JTYPE Flags; // Broad descriptors for the given Type. Automatically defined when delivered to the pointer object + JET Type; // JET constant }; struct DateTime { - LONG Year; // Year - LONG Month; // Month 1 to 12 - LONG Day; // Day 1 to 31 - LONG Hour; // Hour 0 to 23 - LONG Minute; // Minute 0 to 59 - LONG Second; // Second 0 to 59 - LONG TimeZone; // TimeZone -13 to +13 + WORD Year; // Year + BYTE Month; // Month 1 to 12 + BYTE Day; // Day 1 to 31 + BYTE Hour; // Hour 0 to 23 + BYTE Minute; // Minute 0 to 59 + BYTE Second; // Second 0 to 59 + BYTE TimeZone; // TimeZone -13 to +13 }; struct HSV { @@ -1417,6 +1413,7 @@ struct ClipRectangle { LONG Right; // Right-most coordinate LONG Bottom; // Bottom coordinate ClipRectangle() { } + ClipRectangle(LONG Value) : Left(Value), Top(Value), Right(Value), Bottom(Value) { } ClipRectangle(LONG pLeft, LONG pTop, LONG pRight, LONG pBottom) : Left(pLeft), Top(pTop), Right(pRight), Bottom(pBottom) { } int width() const { return Right - Left; } int height() const { return Bottom - Top; } @@ -1430,7 +1427,6 @@ struct Edges { }; #define AHASH_ACTIVATE 0xdbaf4876 -#define AHASH_ACCESSOBJECT 0xbcf3b98e #define AHASH_CLEAR 0x0f3b6d8c #define AHASH_FREEWARNING 0xb903ddbd #define AHASH_COPYDATA 0x47b0d1fa @@ -1440,7 +1436,6 @@ struct Edges { #define AHASH_FLUSH 0x0f71fd67 #define AHASH_FOCUS 0x0f735645 #define AHASH_FREE 0x7c96f087 -#define AHASH_RELEASEOBJECT 0x9e22661d #define AHASH_GETVAR 0xff87a74e #define AHASH_DRAGDROP 0xf69e8a58 #define AHASH_HIDE 0x7c97e2df @@ -1491,6 +1486,8 @@ struct Edges { #endif typedef const std::vector> STRUCTS; +typedef std::map KEYVALUE; +typedef std::map CONST_KEYVALUE; #ifndef STRINGIFY #define STRINGIFY(x) #x @@ -1501,7 +1498,7 @@ typedef const std::vector> STRUCTS; #ifdef PARASOL_STATIC __export void CloseCore(void); -__export ERROR OpenCore(struct OpenInfo *, struct CoreBase **); +__export ERR OpenCore(struct OpenInfo *, struct CoreBase **); #else __export struct ModHeader ModHeader; #endif @@ -1598,12 +1595,12 @@ struct OpenInfo { CSTRING SystemPath; // OPF::SYSTEM_PATH CSTRING ModulePath; // OPF::MODULE_PATH CSTRING RootPath; // OPF::ROOT_PATH - struct OpenTag *Options; // OPF::OPTIONS Typecast to va_list (defined in stdarg.h) + OpenTag *Options; // OPF::OPTIONS Typecast to va_list (defined in stdarg.h) OPF Flags; // OPF::flags need to be set for fields that have been defined in this structure. LONG MaxDepth; // OPF::MAX_DEPTH LONG Detail; // OPF::DETAIL LONG ArgCount; // OPF::ARGS - ERROR Error; // OPF::ERROR + ERR Error; // OPF::ERROR }; // Flags for defining fields, methods, actions and functions. CLASSDEF's can only be used in field definitions for @@ -1653,7 +1650,7 @@ struct OpenInfo { #define FDF_INTEGRAL (FD_POINTER|FD_INTEGRAL) // Field refers to an integral object #define FDF_STRING (FD_POINTER|FD_STRING) // Field points to a string. NB: Ideally want to remove the FD_POINTER as it should be redundant #define FDF_STR (FDF_STRING) -#define FDF_PERCENTAGE FD_PERCENTAGE +#define FDF_SCALED FD_SCALED #define FDF_FLAGS FD_FLAGS // Field contains flags #define FDF_ALLOC FD_ALLOC // Field is a dynamic allocation - either a memory block or object #define FDF_LOOKUP FD_LOOKUP // Lookup names for values in this field @@ -1683,13 +1680,11 @@ struct OpenInfo { #define TLARGE 0x0400000000000000LL #define TFUNCTION 0x0200000000000000LL #define TSTR 0x0080000000000000LL -#define TRELATIVE 0x0020000000000000LL #define TARRAY 0x0000100000000000LL -#define TPERCENT TRELATIVE +#define TSCALE 0x0020000000000000LL #define TAGEND 0LL #define TAGDIVERT -1LL #define TSTRING TSTR -#define TREL TRELATIVE #define nextutf8(str) if (*(str)) for (++(str); (*(str) & 0xc0) IS 0x80; (str)++); @@ -1706,22 +1701,36 @@ struct FieldValue { APTR Pointer; CPTR CPointer; DOUBLE Double; - PERCENT Percent; + SCALE Percent; LARGE Large; LONG Long; }; //std::string not included as not compatible with constexpr - constexpr FieldValue(ULONG pFID, CSTRING pValue) : FieldID(pFID), Type(FD_STRING), String(pValue) { }; - constexpr FieldValue(ULONG pFID, LONG pValue) : FieldID(pFID), Type(FD_LONG), Long(pValue) { }; - constexpr FieldValue(ULONG pFID, LARGE pValue) : FieldID(pFID), Type(FD_LARGE), Large(pValue) { }; - constexpr FieldValue(ULONG pFID, DOUBLE pValue) : FieldID(pFID), Type(FD_DOUBLE), Double(pValue) { }; - constexpr FieldValue(ULONG pFID, PERCENT pValue) : FieldID(pFID), Type(FD_DOUBLE|FD_PERCENTAGE), Percent(pValue) { }; - constexpr FieldValue(ULONG pFID, APTR pValue) : FieldID(pFID), Type(FD_POINTER), Pointer(pValue) { }; - constexpr FieldValue(ULONG pFID, CPTR pValue) : FieldID(pFID), Type(FD_POINTER), CPointer(pValue) { }; + constexpr FieldValue(ULONG pFID, CSTRING pValue) : FieldID(pFID), Type(FD_STRING), String(pValue) { }; + constexpr FieldValue(ULONG pFID, LONG pValue) : FieldID(pFID), Type(FD_LONG), Long(pValue) { }; + constexpr FieldValue(ULONG pFID, LARGE pValue) : FieldID(pFID), Type(FD_LARGE), Large(pValue) { }; + constexpr FieldValue(ULONG pFID, DOUBLE pValue) : FieldID(pFID), Type(FD_DOUBLE), Double(pValue) { }; + constexpr FieldValue(ULONG pFID, SCALE pValue) : FieldID(pFID), Type(FD_DOUBLE|FD_SCALED), Percent(pValue) { }; + constexpr FieldValue(ULONG pFID, const FUNCTION &pValue) : FieldID(pFID), Type(FDF_FUNCTIONPTR), CPointer(&pValue) { }; + constexpr FieldValue(ULONG pFID, const FUNCTION *pValue) : FieldID(pFID), Type(FDF_FUNCTIONPTR), CPointer(pValue) { }; + constexpr FieldValue(ULONG pFID, APTR pValue) : FieldID(pFID), Type(FD_POINTER), Pointer(pValue) { }; + constexpr FieldValue(ULONG pFID, CPTR pValue) : FieldID(pFID), Type(FD_POINTER), CPointer(pValue) { }; constexpr FieldValue(ULONG pFID, CPTR pValue, LONG pCustom) : FieldID(pFID), Type(pCustom), CPointer(pValue) { }; }; + +class FloatRect { + public: + DOUBLE X; // Left-most coordinate + DOUBLE Y; // Top coordinate + DOUBLE Width; // Right-most coordinate + DOUBLE Height; // Bottom coordinate + FloatRect() { } + FloatRect(DOUBLE Value) : X(Value), Y(Value), Width(Value), Height(Value) { } + FloatRect(DOUBLE pX, DOUBLE pY, DOUBLE pWidth, DOUBLE pHeight) : X(pX), Y(pY), Width(pWidth), Height(pHeight) { } +}; + } #include // memset() @@ -1732,8 +1741,8 @@ struct ObjectSignal { }; struct ResourceManager { - CSTRING Name; // The name of the resource. - ERROR (*Free)(APTR); // A function that will remove the resource's content when terminated. + CSTRING Name; // The name of the resource. + ERR (*Free)(APTR); // A function that will remove the resource's content when terminated. }; typedef struct pfBase64Decode { @@ -1762,19 +1771,19 @@ struct Function { }; struct ModHeader { - MHF Flags; // Special flags, type of function table wanted from the Core - CSTRING Definitions; // Module definition string, usable by run-time languages such as Fluid - ERROR (*Init)(OBJECTPTR, struct CoreBase *); // A one-off initialisation routine for when the module is first opened. - void (*Close)(OBJECTPTR); // A function that will be called each time the module is closed. - ERROR (*Open)(OBJECTPTR); // A function that will be called each time the module is opened. - ERROR (*Expunge)(void); // Reference to an expunge function to terminate the module. - CSTRING Name; // Name of the module + MHF Flags; // Special flags, type of function table wanted from the Core + CSTRING Definitions; // Module definition string, usable by run-time languages such as Fluid + ERR (*Init)(OBJECTPTR, struct CoreBase *); // A one-off initialisation routine for when the module is first opened. + void (*Close)(OBJECTPTR); // A function that will be called each time the module is closed. + ERR (*Open)(OBJECTPTR); // A function that will be called each time the module is opened. + ERR (*Expunge)(void); // Reference to an expunge function to terminate the module. + CSTRING Name; // Name of the module STRUCTS *StructDefs; class RootModule *Root; - ModHeader(ERROR (*pInit)(OBJECTPTR, struct CoreBase *), + ModHeader(ERR (*pInit)(OBJECTPTR, struct CoreBase *), void (*pClose)(OBJECTPTR), - ERROR (*pOpen)(OBJECTPTR), - ERROR (*pExpunge)(void), + ERR (*pOpen)(OBJECTPTR), + ERR (*pExpunge)(void), CSTRING pDef, STRUCTS *pStructs, CSTRING pName) { @@ -1793,7 +1802,7 @@ struct ModHeader { struct FieldArray { CSTRING Name; // The name of the field, e.g. "Width" APTR GetField; // void GetField(*Object, APTR Result); - APTR SetField; // ERROR SetField(*Object, APTR Value); + APTR SetField; // ERR SetField(*Object, APTR Value); MAXINT Arg; // Can be a pointer or an integer value ULONG Flags; // Special flags that describe the field template FieldArray(CSTRING pName, ULONG pFlags, G pGetField = NULL, S pSetField = NULL, T pArg = 0) : @@ -1834,7 +1843,7 @@ struct ActionArray { struct MethodEntry { LONG MethodID; // Unique method identifier - APTR Routine; // The method entry point, defined as ERROR (*Routine)(OBJECTPTR, APTR); + APTR Routine; // The method entry point, defined as ERR (*Routine)(OBJECTPTR, APTR); CSTRING Name; // Name of the method const struct FunctionField * Args; // List of parameters accepted by the method LONG Size; // Total byte-size of all accepted parameters when they are assembled as a C structure. @@ -1960,15 +1969,15 @@ struct FileFeedback { }; struct Field { - MAXINT Arg; // An option to complement the field type. Can be a pointer or an integer value - ERROR (*GetValue)(APTR, APTR); // A virtual function that will retrieve the value for this field. - APTR SetValue; // A virtual function that will set the value for this field. - ERROR (*WriteValue)(OBJECTPTR, struct Field *, LONG, const void *, LONG); // An internal function for writing to this field. - CSTRING Name; // The English name for the field, e.g. "Width" - ULONG FieldID; // Provides a fast way of finding fields, e.g. FID_WIDTH - UWORD Offset; // Field offset within the object - UWORD Index; // Field array index - ULONG Flags; // Special flags that describe the field + MAXINT Arg; // An option to complement the field type. Can be a pointer or an integer value + ERR (*GetValue)(APTR, APTR); // A virtual function that will retrieve the value for this field. + APTR SetValue; // A virtual function that will set the value for this field. + ERR (*WriteValue)(OBJECTPTR, struct Field *, LONG, const void *, LONG); // An internal function for writing to this field. + CSTRING Name; // The English name for the field, e.g. "Width" + ULONG FieldID; // Provides a fast way of finding fields, e.g. FID_WIDTH + UWORD Offset; // Field offset within the object + UWORD Index; // Field array index + ULONG Flags; // Special flags that describe the field }; struct ScriptArg { // For use with scExec @@ -2000,105 +2009,105 @@ struct ScriptArg { // For use with scExec struct CoreBase { #ifndef PARASOL_STATIC - ERROR (*_AccessMemory)(MEMORYID Memory, MEM Flags, LONG MilliSeconds, APTR Result); - ERROR (*_Action)(LONG Action, OBJECTPTR Object, APTR Parameters); + ERR (*_AccessMemory)(MEMORYID Memory, MEM Flags, LONG MilliSeconds, APTR Result); + ERR (*_Action)(LONG Action, OBJECTPTR Object, APTR Parameters); void (*_ActionList)(struct ActionTable ** Actions, LONG * Size); - ERROR (*_ActionMsg)(LONG Action, OBJECTID Object, APTR Args); + ERR (*_ActionMsg)(LONG Action, OBJECTID Object, APTR Args); CSTRING (*_ResolveClassID)(CLASSID ID); LONG (*_AllocateID)(IDTYPE Type); - ERROR (*_AllocMemory)(LONG Size, MEM Flags, APTR Address, MEMORYID * ID); - ERROR (*_AccessObject)(OBJECTID Object, LONG MilliSeconds, APTR Result); - ERROR (*_CheckAction)(OBJECTPTR Object, LONG Action); - ERROR (*_CheckMemoryExists)(MEMORYID ID); - ERROR (*_CheckObjectExists)(OBJECTID Object); - ERROR (*_InitObject)(OBJECTPTR Object); - ERROR (*_VirtualVolume)(CSTRING Name, ...); + ERR (*_AllocMemory)(LONG Size, MEM Flags, APTR Address, MEMORYID * ID); + ERR (*_AccessObject)(OBJECTID Object, LONG MilliSeconds, APTR Result); + ERR (*_CheckAction)(OBJECTPTR Object, LONG Action); + ERR (*_CheckMemoryExists)(MEMORYID ID); + ERR (*_CheckObjectExists)(OBJECTID Object); + ERR (*_InitObject)(OBJECTPTR Object); + ERR (*_VirtualVolume)(CSTRING Name, ...); OBJECTPTR (*_CurrentContext)(void); - ERROR (*_GetFieldArray)(OBJECTPTR Object, FIELD Field, APTR Result, LONG * Elements); + ERR (*_GetFieldArray)(OBJECTPTR Object, FIELD Field, APTR Result, LONG * Elements); LONG (*_AdjustLogLevel)(LONG Adjust); - ERROR (*_ReadFileToBuffer)(CSTRING Path, APTR Buffer, LONG BufferSize, LONG * Result); - ERROR (*_FindObject)(CSTRING Name, CLASSID ClassID, FOF Flags, OBJECTID * ObjectID); + ERR (*_ReadFileToBuffer)(CSTRING Path, APTR Buffer, LONG BufferSize, LONG * Result); + ERR (*_FindObject)(CSTRING Name, CLASSID ClassID, FOF Flags, OBJECTID * ObjectID); objMetaClass * (*_FindClass)(CLASSID ClassID); - ERROR (*_AnalysePath)(CSTRING Path, LOC * Type); + ERR (*_AnalysePath)(CSTRING Path, LOC * Type); LONG (*_UTF8Copy)(CSTRING Src, STRING Dest, LONG Chars, LONG Size); - ERROR (*_FreeResource)(MEMORYID ID); + ERR (*_FreeResource)(MEMORYID ID); CLASSID (*_GetClassID)(OBJECTID Object); OBJECTID (*_GetOwnerID)(OBJECTID Object); - ERROR (*_GetField)(OBJECTPTR Object, FIELD Field, APTR Result); - ERROR (*_GetFieldVariable)(OBJECTPTR Object, CSTRING Field, STRING Buffer, LONG Size); - ERROR (*_CompareFilePaths)(CSTRING PathA, CSTRING PathB); + ERR (*_GetField)(OBJECTPTR Object, FIELD Field, APTR Result); + ERR (*_GetFieldVariable)(OBJECTPTR Object, CSTRING Field, STRING Buffer, LONG Size); + ERR (*_CompareFilePaths)(CSTRING PathA, CSTRING PathB); const struct SystemState * (*_GetSystemState)(void); - ERROR (*_ListChildren)(OBJECTID Object, pf::vector * List); - ERROR (*_Base64Decode)(struct pfBase64Decode * State, CSTRING Input, LONG InputSize, APTR Output, LONG * Written); - ERROR (*_RegisterFD)(HOSTHANDLE FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR) , APTR Data); - ERROR (*_ResolvePath)(CSTRING Path, RSF Flags, STRING * Result); - ERROR (*_MemoryIDInfo)(MEMORYID ID, struct MemInfo * MemInfo, LONG Size); - ERROR (*_MemoryPtrInfo)(APTR Address, struct MemInfo * MemInfo, LONG Size); - ERROR (*_NewObject)(LARGE ClassID, NF Flags, APTR Object); - void (*_NotifySubscribers)(OBJECTPTR Object, LONG Action, APTR Args, ERROR Error); - ERROR (*_StrReadLocale)(CSTRING Key, CSTRING * Value); + ERR (*_ListChildren)(OBJECTID Object, pf::vector * List); + ERR (*_Base64Decode)(struct pfBase64Decode * State, CSTRING Input, LONG InputSize, APTR Output, LONG * Written); + ERR (*_RegisterFD)(HOSTHANDLE FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR) , APTR Data); + ERR (*_ResolvePath)(CSTRING Path, RSF Flags, STRING * Result); + ERR (*_MemoryIDInfo)(MEMORYID ID, struct MemInfo * MemInfo, LONG Size); + ERR (*_MemoryPtrInfo)(APTR Address, struct MemInfo * MemInfo, LONG Size); + ERR (*_NewObject)(LARGE ClassID, NF Flags, APTR Object); + void (*_NotifySubscribers)(OBJECTPTR Object, LONG Action, APTR Args, ERR Error); + ERR (*_StrReadLocale)(CSTRING Key, CSTRING * Value); CSTRING (*_UTF8ValidEncoding)(CSTRING String, CSTRING Encoding); - ERROR (*_ProcessMessages)(PMF Flags, LONG TimeOut); - ERROR (*_IdentifyFile)(CSTRING Path, CLASSID * Class, CLASSID * SubClass); - ERROR (*_ReallocMemory)(APTR Memory, ULONG Size, APTR Address, MEMORYID * ID); - ERROR (*_GetMessage)(LONG Type, MSF Flags, APTR Buffer, LONG Size); - ERROR (*_ReleaseMemory)(MEMORYID MemoryID); + ERR (*_ProcessMessages)(PMF Flags, LONG TimeOut); + ERR (*_IdentifyFile)(CSTRING Path, CLASSID * Class, CLASSID * SubClass); + ERR (*_ReallocMemory)(APTR Memory, ULONG Size, APTR Address, MEMORYID * ID); + ERR (*_GetMessage)(LONG Type, MSF Flags, APTR Buffer, LONG Size); + ERR (*_ReleaseMemory)(MEMORYID MemoryID); CLASSID (*_ResolveClassName)(CSTRING Name); - ERROR (*_SendMessage)(LONG Type, MSF Flags, APTR Data, LONG Size); - ERROR (*_SetOwner)(OBJECTPTR Object, OBJECTPTR Owner); + ERR (*_SendMessage)(LONG Type, MSF Flags, APTR Data, LONG Size); + ERR (*_SetOwner)(OBJECTPTR Object, OBJECTPTR Owner); OBJECTPTR (*_SetContext)(OBJECTPTR Object); - ERROR (*_SetField)(OBJECTPTR Object, FIELD Field, ...); + ERR (*_SetField)(OBJECTPTR Object, FIELD Field, ...); CSTRING (*_FieldName)(ULONG FieldID); - ERROR (*_ScanDir)(struct DirInfo * Info); - ERROR (*_SetName)(OBJECTPTR Object, CSTRING Name); + ERR (*_ScanDir)(struct DirInfo * Info); + ERR (*_SetName)(OBJECTPTR Object, CSTRING Name); void (*_LogReturn)(void); - ERROR (*_StrCompare)(CSTRING String1, CSTRING String2, LONG Length, STR Flags); - ERROR (*_SubscribeAction)(OBJECTPTR Object, LONG Action, FUNCTION * Callback); - ERROR (*_SubscribeEvent)(LARGE Event, FUNCTION * Callback, APTR Custom, APTR Handle); - ERROR (*_SubscribeTimer)(DOUBLE Interval, FUNCTION * Callback, APTR Subscription); - ERROR (*_UpdateTimer)(APTR Subscription, DOUBLE Interval); - ERROR (*_UnsubscribeAction)(OBJECTPTR Object, LONG Action); + ERR (*_StrCompare)(CSTRING String1, CSTRING String2, LONG Length, STR Flags); + ERR (*_SubscribeAction)(OBJECTPTR Object, LONG Action, FUNCTION * Callback); + ERR (*_SubscribeEvent)(LARGE Event, FUNCTION * Callback, APTR Custom, APTR Handle); + ERR (*_SubscribeTimer)(DOUBLE Interval, FUNCTION * Callback, APTR Subscription); + ERR (*_UpdateTimer)(APTR Subscription, DOUBLE Interval); + ERR (*_UnsubscribeAction)(OBJECTPTR Object, LONG Action); void (*_UnsubscribeEvent)(APTR Handle); - ERROR (*_BroadcastEvent)(APTR Event, LONG EventSize); + ERR (*_BroadcastEvent)(APTR Event, LONG EventSize); void (*_WaitTime)(LONG Seconds, LONG MicroSeconds); LARGE (*_GetEventID)(EVG Group, CSTRING SubGroup, CSTRING Event); ULONG (*_GenCRC32)(ULONG CRC, APTR Data, ULONG Length); LARGE (*_GetResource)(RES Resource); LARGE (*_SetResource)(RES Resource, LARGE Value); - ERROR (*_ScanMessages)(LONG * Handle, LONG Type, APTR Buffer, LONG Size); + ERR (*_ScanMessages)(LONG * Handle, LONG Type, APTR Buffer, LONG Size); STT (*_StrDatatype)(CSTRING String); void (*_UnloadFile)(struct CacheFile * Cache); - ERROR (*_CreateFolder)(CSTRING Path, PERMIT Permissions); - ERROR (*_LoadFile)(CSTRING Path, LDF Flags, struct CacheFile ** Cache); - ERROR (*_SetVolume)(CSTRING Name, CSTRING Path, CSTRING Icon, CSTRING Label, CSTRING Device, VOLUME Flags); - ERROR (*_DeleteVolume)(CSTRING Name); - ERROR (*_MoveFile)(CSTRING Source, CSTRING Dest, FUNCTION * Callback); - ERROR (*_UpdateMessage)(LONG Message, LONG Type, APTR Data, LONG Size); - ERROR (*_AddMsgHandler)(APTR Custom, LONG MsgType, FUNCTION * Routine, struct MsgHandler ** Handle); - ERROR (*_QueueAction)(LONG Action, OBJECTID Object, APTR Args); + ERR (*_CreateFolder)(CSTRING Path, PERMIT Permissions); + ERR (*_LoadFile)(CSTRING Path, LDF Flags, struct CacheFile ** Cache); + ERR (*_SetVolume)(CSTRING Name, CSTRING Path, CSTRING Icon, CSTRING Label, CSTRING Device, VOLUME Flags); + ERR (*_DeleteVolume)(CSTRING Name); + ERR (*_MoveFile)(CSTRING Source, CSTRING Dest, FUNCTION * Callback); + ERR (*_UpdateMessage)(LONG Message, LONG Type, APTR Data, LONG Size); + ERR (*_AddMsgHandler)(APTR Custom, LONG MsgType, FUNCTION * Routine, struct MsgHandler ** Handle); + ERR (*_QueueAction)(LONG Action, OBJECTID Object, APTR Args); LARGE (*_PreciseTime)(void); - ERROR (*_OpenDir)(CSTRING Path, RDF Flags, struct DirInfo ** Info); + ERR (*_OpenDir)(CSTRING Path, RDF Flags, struct DirInfo ** Info); OBJECTPTR (*_GetObjectPtr)(OBJECTID Object); struct Field * (*_FindField)(OBJECTPTR Object, ULONG FieldID, APTR Target); - CSTRING (*_GetErrorMsg)(ERROR Error); + CSTRING (*_GetErrorMsg)(ERR Error); struct Message * (*_GetActionMsg)(void); - ERROR (*_FuncError)(CSTRING Header, ERROR Error); - ERROR (*_SetArray)(OBJECTPTR Object, FIELD Field, APTR Array, LONG Elements); + ERR (*_FuncError)(CSTRING Header, ERR Error); + ERR (*_SetArray)(OBJECTPTR Object, FIELD Field, APTR Array, LONG Elements); ULONG (*_StrHash)(CSTRING String, LONG CaseSensitive); - ERROR (*_LockObject)(OBJECTPTR Object, LONG MilliSeconds); + ERR (*_LockObject)(OBJECTPTR Object, LONG MilliSeconds); void (*_ReleaseObject)(OBJECTPTR Object); - ERROR (*_ActionThread)(LONG Action, OBJECTPTR Object, APTR Args, FUNCTION * Callback, LONG Key); - ERROR (*_AddInfoTag)(struct FileInfo * Info, CSTRING Name, CSTRING Value); + ERR (*_ActionThread)(LONG Action, OBJECTPTR Object, APTR Args, FUNCTION * Callback, LONG Key); + ERR (*_AddInfoTag)(struct FileInfo * Info, CSTRING Name, CSTRING Value); void (*_SetDefaultPermissions)(LONG User, LONG Group, PERMIT Permissions); void (*_VLogF)(VLF Flags, const char *Header, const char *Message, va_list Args); LONG (*_Base64Encode)(struct pfBase64Encode * State, const void * Input, LONG InputSize, STRING Output, LONG OutputSize); - ERROR (*_ReadInfoTag)(struct FileInfo * Info, CSTRING Name, CSTRING * Value); - ERROR (*_SetResourcePath)(RP PathType, CSTRING Path); + ERR (*_ReadInfoTag)(struct FileInfo * Info, CSTRING Name, CSTRING * Value); + ERR (*_SetResourcePath)(RP PathType, CSTRING Path); objTask * (*_CurrentTask)(void); CSTRING (*_ResolveGroupID)(LONG Group); CSTRING (*_ResolveUserID)(LONG User); - ERROR (*_CreateLink)(CSTRING From, CSTRING To); - ERROR (*_DeleteFile)(CSTRING Path, FUNCTION * Callback); + ERR (*_CreateLink)(CSTRING From, CSTRING To); + ERR (*_DeleteFile)(CSTRING Path, FUNCTION * Callback); LONG (*_UTF8CharOffset)(CSTRING String, LONG Offset); LONG (*_UTF8Length)(CSTRING String); LONG (*_UTF8OffsetToChar)(CSTRING String, LONG Offset); @@ -2106,113 +2115,113 @@ struct CoreBase { LONG (*_UTF8CharLength)(CSTRING String); ULONG (*_UTF8ReadValue)(CSTRING String, LONG * Length); LONG (*_UTF8WriteValue)(LONG Value, STRING Buffer, LONG Size); - ERROR (*_CopyFile)(CSTRING Source, CSTRING Dest, FUNCTION * Callback); - ERROR (*_WaitForObjects)(PMF Flags, LONG TimeOut, struct ObjectSignal * ObjectSignals); + ERR (*_CopyFile)(CSTRING Source, CSTRING Dest, FUNCTION * Callback); + ERR (*_WaitForObjects)(PMF Flags, LONG TimeOut, struct ObjectSignal * ObjectSignals); #endif // PARASOL_STATIC }; #ifndef PRV_CORE_MODULE #ifndef PARASOL_STATIC extern struct CoreBase *CoreBase; -inline ERROR AccessMemory(MEMORYID Memory, MEM Flags, LONG MilliSeconds, APTR Result) { return CoreBase->_AccessMemory(Memory,Flags,MilliSeconds,Result); } -inline ERROR Action(LONG Action, OBJECTPTR Object, APTR Parameters) { return CoreBase->_Action(Action,Object,Parameters); } +inline ERR AccessMemory(MEMORYID Memory, MEM Flags, LONG MilliSeconds, APTR Result) { return CoreBase->_AccessMemory(Memory,Flags,MilliSeconds,Result); } +inline ERR Action(LONG Action, OBJECTPTR Object, APTR Parameters) { return CoreBase->_Action(Action,Object,Parameters); } inline void ActionList(struct ActionTable ** Actions, LONG * Size) { return CoreBase->_ActionList(Actions,Size); } -inline ERROR ActionMsg(LONG Action, OBJECTID Object, APTR Args) { return CoreBase->_ActionMsg(Action,Object,Args); } +inline ERR ActionMsg(LONG Action, OBJECTID Object, APTR Args) { return CoreBase->_ActionMsg(Action,Object,Args); } inline CSTRING ResolveClassID(CLASSID ID) { return CoreBase->_ResolveClassID(ID); } inline LONG AllocateID(IDTYPE Type) { return CoreBase->_AllocateID(Type); } -inline ERROR AllocMemory(LONG Size, MEM Flags, APTR Address, MEMORYID * ID) { return CoreBase->_AllocMemory(Size,Flags,Address,ID); } -inline ERROR AccessObject(OBJECTID Object, LONG MilliSeconds, APTR Result) { return CoreBase->_AccessObject(Object,MilliSeconds,Result); } -inline ERROR CheckAction(OBJECTPTR Object, LONG Action) { return CoreBase->_CheckAction(Object,Action); } -inline ERROR CheckMemoryExists(MEMORYID ID) { return CoreBase->_CheckMemoryExists(ID); } -inline ERROR CheckObjectExists(OBJECTID Object) { return CoreBase->_CheckObjectExists(Object); } -inline ERROR InitObject(OBJECTPTR Object) { return CoreBase->_InitObject(Object); } -template ERROR VirtualVolume(CSTRING Name, Args... Tags) { return CoreBase->_VirtualVolume(Name,Tags...); } +inline ERR AllocMemory(LONG Size, MEM Flags, APTR Address, MEMORYID * ID) { return CoreBase->_AllocMemory(Size,Flags,Address,ID); } +inline ERR AccessObject(OBJECTID Object, LONG MilliSeconds, APTR Result) { return CoreBase->_AccessObject(Object,MilliSeconds,Result); } +inline ERR CheckAction(OBJECTPTR Object, LONG Action) { return CoreBase->_CheckAction(Object,Action); } +inline ERR CheckMemoryExists(MEMORYID ID) { return CoreBase->_CheckMemoryExists(ID); } +inline ERR CheckObjectExists(OBJECTID Object) { return CoreBase->_CheckObjectExists(Object); } +inline ERR InitObject(OBJECTPTR Object) { return CoreBase->_InitObject(Object); } +template ERR VirtualVolume(CSTRING Name, Args... Tags) { return CoreBase->_VirtualVolume(Name,Tags...); } inline OBJECTPTR CurrentContext(void) { return CoreBase->_CurrentContext(); } -inline ERROR GetFieldArray(OBJECTPTR Object, FIELD Field, APTR Result, LONG * Elements) { return CoreBase->_GetFieldArray(Object,Field,Result,Elements); } +inline ERR GetFieldArray(OBJECTPTR Object, FIELD Field, APTR Result, LONG * Elements) { return CoreBase->_GetFieldArray(Object,Field,Result,Elements); } inline LONG AdjustLogLevel(LONG Adjust) { return CoreBase->_AdjustLogLevel(Adjust); } -inline ERROR ReadFileToBuffer(CSTRING Path, APTR Buffer, LONG BufferSize, LONG * Result) { return CoreBase->_ReadFileToBuffer(Path,Buffer,BufferSize,Result); } -inline ERROR FindObject(CSTRING Name, CLASSID ClassID, FOF Flags, OBJECTID * ObjectID) { return CoreBase->_FindObject(Name,ClassID,Flags,ObjectID); } +inline ERR ReadFileToBuffer(CSTRING Path, APTR Buffer, LONG BufferSize, LONG * Result) { return CoreBase->_ReadFileToBuffer(Path,Buffer,BufferSize,Result); } +inline ERR FindObject(CSTRING Name, CLASSID ClassID, FOF Flags, OBJECTID * ObjectID) { return CoreBase->_FindObject(Name,ClassID,Flags,ObjectID); } inline objMetaClass * FindClass(CLASSID ClassID) { return CoreBase->_FindClass(ClassID); } -inline ERROR AnalysePath(CSTRING Path, LOC * Type) { return CoreBase->_AnalysePath(Path,Type); } +inline ERR AnalysePath(CSTRING Path, LOC * Type) { return CoreBase->_AnalysePath(Path,Type); } inline LONG UTF8Copy(CSTRING Src, STRING Dest, LONG Chars, LONG Size) { return CoreBase->_UTF8Copy(Src,Dest,Chars,Size); } -inline ERROR FreeResource(MEMORYID ID) { return CoreBase->_FreeResource(ID); } +inline ERR FreeResource(MEMORYID ID) { return CoreBase->_FreeResource(ID); } inline CLASSID GetClassID(OBJECTID Object) { return CoreBase->_GetClassID(Object); } inline OBJECTID GetOwnerID(OBJECTID Object) { return CoreBase->_GetOwnerID(Object); } -inline ERROR GetField(OBJECTPTR Object, FIELD Field, APTR Result) { return CoreBase->_GetField(Object,Field,Result); } -inline ERROR GetFieldVariable(OBJECTPTR Object, CSTRING Field, STRING Buffer, LONG Size) { return CoreBase->_GetFieldVariable(Object,Field,Buffer,Size); } -inline ERROR CompareFilePaths(CSTRING PathA, CSTRING PathB) { return CoreBase->_CompareFilePaths(PathA,PathB); } +inline ERR GetField(OBJECTPTR Object, FIELD Field, APTR Result) { return CoreBase->_GetField(Object,Field,Result); } +inline ERR GetFieldVariable(OBJECTPTR Object, CSTRING Field, STRING Buffer, LONG Size) { return CoreBase->_GetFieldVariable(Object,Field,Buffer,Size); } +inline ERR CompareFilePaths(CSTRING PathA, CSTRING PathB) { return CoreBase->_CompareFilePaths(PathA,PathB); } inline const struct SystemState * GetSystemState(void) { return CoreBase->_GetSystemState(); } -inline ERROR ListChildren(OBJECTID Object, pf::vector * List) { return CoreBase->_ListChildren(Object,List); } -inline ERROR Base64Decode(struct pfBase64Decode * State, CSTRING Input, LONG InputSize, APTR Output, LONG * Written) { return CoreBase->_Base64Decode(State,Input,InputSize,Output,Written); } -inline ERROR RegisterFD(HOSTHANDLE FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR) , APTR Data) { return CoreBase->_RegisterFD(FD,Flags,Routine,Data); } -inline ERROR ResolvePath(CSTRING Path, RSF Flags, STRING * Result) { return CoreBase->_ResolvePath(Path,Flags,Result); } -inline ERROR MemoryIDInfo(MEMORYID ID, struct MemInfo * MemInfo, LONG Size) { return CoreBase->_MemoryIDInfo(ID,MemInfo,Size); } -inline ERROR MemoryPtrInfo(APTR Address, struct MemInfo * MemInfo, LONG Size) { return CoreBase->_MemoryPtrInfo(Address,MemInfo,Size); } -inline ERROR NewObject(LARGE ClassID, NF Flags, APTR Object) { return CoreBase->_NewObject(ClassID,Flags,Object); } -inline void NotifySubscribers(OBJECTPTR Object, LONG Action, APTR Args, ERROR Error) { return CoreBase->_NotifySubscribers(Object,Action,Args,Error); } -inline ERROR StrReadLocale(CSTRING Key, CSTRING * Value) { return CoreBase->_StrReadLocale(Key,Value); } +inline ERR ListChildren(OBJECTID Object, pf::vector * List) { return CoreBase->_ListChildren(Object,List); } +inline ERR Base64Decode(struct pfBase64Decode * State, CSTRING Input, LONG InputSize, APTR Output, LONG * Written) { return CoreBase->_Base64Decode(State,Input,InputSize,Output,Written); } +inline ERR RegisterFD(HOSTHANDLE FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR) , APTR Data) { return CoreBase->_RegisterFD(FD,Flags,Routine,Data); } +inline ERR ResolvePath(CSTRING Path, RSF Flags, STRING * Result) { return CoreBase->_ResolvePath(Path,Flags,Result); } +inline ERR MemoryIDInfo(MEMORYID ID, struct MemInfo * MemInfo, LONG Size) { return CoreBase->_MemoryIDInfo(ID,MemInfo,Size); } +inline ERR MemoryPtrInfo(APTR Address, struct MemInfo * MemInfo, LONG Size) { return CoreBase->_MemoryPtrInfo(Address,MemInfo,Size); } +inline ERR NewObject(LARGE ClassID, NF Flags, APTR Object) { return CoreBase->_NewObject(ClassID,Flags,Object); } +inline void NotifySubscribers(OBJECTPTR Object, LONG Action, APTR Args, ERR Error) { return CoreBase->_NotifySubscribers(Object,Action,Args,Error); } +inline ERR StrReadLocale(CSTRING Key, CSTRING * Value) { return CoreBase->_StrReadLocale(Key,Value); } inline CSTRING UTF8ValidEncoding(CSTRING String, CSTRING Encoding) { return CoreBase->_UTF8ValidEncoding(String,Encoding); } -inline ERROR ProcessMessages(PMF Flags, LONG TimeOut) { return CoreBase->_ProcessMessages(Flags,TimeOut); } -inline ERROR IdentifyFile(CSTRING Path, CLASSID * Class, CLASSID * SubClass) { return CoreBase->_IdentifyFile(Path,Class,SubClass); } -inline ERROR ReallocMemory(APTR Memory, ULONG Size, APTR Address, MEMORYID * ID) { return CoreBase->_ReallocMemory(Memory,Size,Address,ID); } -inline ERROR GetMessage(LONG Type, MSF Flags, APTR Buffer, LONG Size) { return CoreBase->_GetMessage(Type,Flags,Buffer,Size); } -inline ERROR ReleaseMemory(MEMORYID MemoryID) { return CoreBase->_ReleaseMemory(MemoryID); } +inline ERR ProcessMessages(PMF Flags, LONG TimeOut) { return CoreBase->_ProcessMessages(Flags,TimeOut); } +inline ERR IdentifyFile(CSTRING Path, CLASSID * Class, CLASSID * SubClass) { return CoreBase->_IdentifyFile(Path,Class,SubClass); } +inline ERR ReallocMemory(APTR Memory, ULONG Size, APTR Address, MEMORYID * ID) { return CoreBase->_ReallocMemory(Memory,Size,Address,ID); } +inline ERR GetMessage(LONG Type, MSF Flags, APTR Buffer, LONG Size) { return CoreBase->_GetMessage(Type,Flags,Buffer,Size); } +inline ERR ReleaseMemory(MEMORYID MemoryID) { return CoreBase->_ReleaseMemory(MemoryID); } inline CLASSID ResolveClassName(CSTRING Name) { return CoreBase->_ResolveClassName(Name); } -inline ERROR SendMessage(LONG Type, MSF Flags, APTR Data, LONG Size) { return CoreBase->_SendMessage(Type,Flags,Data,Size); } -inline ERROR SetOwner(OBJECTPTR Object, OBJECTPTR Owner) { return CoreBase->_SetOwner(Object,Owner); } +inline ERR SendMessage(LONG Type, MSF Flags, APTR Data, LONG Size) { return CoreBase->_SendMessage(Type,Flags,Data,Size); } +inline ERR SetOwner(OBJECTPTR Object, OBJECTPTR Owner) { return CoreBase->_SetOwner(Object,Owner); } inline OBJECTPTR SetContext(OBJECTPTR Object) { return CoreBase->_SetContext(Object); } -template ERROR SetField(OBJECTPTR Object, FIELD Field, Args... Tags) { return CoreBase->_SetField(Object,Field,Tags...); } +template ERR SetField(OBJECTPTR Object, FIELD Field, Args... Tags) { return CoreBase->_SetField(Object,Field,Tags...); } inline CSTRING FieldName(ULONG FieldID) { return CoreBase->_FieldName(FieldID); } -inline ERROR ScanDir(struct DirInfo * Info) { return CoreBase->_ScanDir(Info); } -inline ERROR SetName(OBJECTPTR Object, CSTRING Name) { return CoreBase->_SetName(Object,Name); } +inline ERR ScanDir(struct DirInfo * Info) { return CoreBase->_ScanDir(Info); } +inline ERR SetName(OBJECTPTR Object, CSTRING Name) { return CoreBase->_SetName(Object,Name); } inline void LogReturn(void) { return CoreBase->_LogReturn(); } -inline ERROR StrCompare(CSTRING String1, CSTRING String2, LONG Length, STR Flags) { return CoreBase->_StrCompare(String1,String2,Length,Flags); } -inline ERROR SubscribeAction(OBJECTPTR Object, LONG Action, FUNCTION * Callback) { return CoreBase->_SubscribeAction(Object,Action,Callback); } -inline ERROR SubscribeEvent(LARGE Event, FUNCTION * Callback, APTR Custom, APTR Handle) { return CoreBase->_SubscribeEvent(Event,Callback,Custom,Handle); } -inline ERROR SubscribeTimer(DOUBLE Interval, FUNCTION * Callback, APTR Subscription) { return CoreBase->_SubscribeTimer(Interval,Callback,Subscription); } -inline ERROR UpdateTimer(APTR Subscription, DOUBLE Interval) { return CoreBase->_UpdateTimer(Subscription,Interval); } -inline ERROR UnsubscribeAction(OBJECTPTR Object, LONG Action) { return CoreBase->_UnsubscribeAction(Object,Action); } +inline ERR StrCompare(CSTRING String1, CSTRING String2, LONG Length, STR Flags) { return CoreBase->_StrCompare(String1,String2,Length,Flags); } +inline ERR SubscribeAction(OBJECTPTR Object, LONG Action, FUNCTION * Callback) { return CoreBase->_SubscribeAction(Object,Action,Callback); } +inline ERR SubscribeEvent(LARGE Event, FUNCTION * Callback, APTR Custom, APTR Handle) { return CoreBase->_SubscribeEvent(Event,Callback,Custom,Handle); } +inline ERR SubscribeTimer(DOUBLE Interval, FUNCTION * Callback, APTR Subscription) { return CoreBase->_SubscribeTimer(Interval,Callback,Subscription); } +inline ERR UpdateTimer(APTR Subscription, DOUBLE Interval) { return CoreBase->_UpdateTimer(Subscription,Interval); } +inline ERR UnsubscribeAction(OBJECTPTR Object, LONG Action) { return CoreBase->_UnsubscribeAction(Object,Action); } inline void UnsubscribeEvent(APTR Handle) { return CoreBase->_UnsubscribeEvent(Handle); } -inline ERROR BroadcastEvent(APTR Event, LONG EventSize) { return CoreBase->_BroadcastEvent(Event,EventSize); } +inline ERR BroadcastEvent(APTR Event, LONG EventSize) { return CoreBase->_BroadcastEvent(Event,EventSize); } inline void WaitTime(LONG Seconds, LONG MicroSeconds) { return CoreBase->_WaitTime(Seconds,MicroSeconds); } inline LARGE GetEventID(EVG Group, CSTRING SubGroup, CSTRING Event) { return CoreBase->_GetEventID(Group,SubGroup,Event); } inline ULONG GenCRC32(ULONG CRC, APTR Data, ULONG Length) { return CoreBase->_GenCRC32(CRC,Data,Length); } inline LARGE GetResource(RES Resource) { return CoreBase->_GetResource(Resource); } inline LARGE SetResource(RES Resource, LARGE Value) { return CoreBase->_SetResource(Resource,Value); } -inline ERROR ScanMessages(LONG * Handle, LONG Type, APTR Buffer, LONG Size) { return CoreBase->_ScanMessages(Handle,Type,Buffer,Size); } +inline ERR ScanMessages(LONG * Handle, LONG Type, APTR Buffer, LONG Size) { return CoreBase->_ScanMessages(Handle,Type,Buffer,Size); } inline STT StrDatatype(CSTRING String) { return CoreBase->_StrDatatype(String); } inline void UnloadFile(struct CacheFile * Cache) { return CoreBase->_UnloadFile(Cache); } -inline ERROR CreateFolder(CSTRING Path, PERMIT Permissions) { return CoreBase->_CreateFolder(Path,Permissions); } -inline ERROR LoadFile(CSTRING Path, LDF Flags, struct CacheFile ** Cache) { return CoreBase->_LoadFile(Path,Flags,Cache); } -inline ERROR SetVolume(CSTRING Name, CSTRING Path, CSTRING Icon, CSTRING Label, CSTRING Device, VOLUME Flags) { return CoreBase->_SetVolume(Name,Path,Icon,Label,Device,Flags); } -inline ERROR DeleteVolume(CSTRING Name) { return CoreBase->_DeleteVolume(Name); } -inline ERROR MoveFile(CSTRING Source, CSTRING Dest, FUNCTION * Callback) { return CoreBase->_MoveFile(Source,Dest,Callback); } -inline ERROR UpdateMessage(LONG Message, LONG Type, APTR Data, LONG Size) { return CoreBase->_UpdateMessage(Message,Type,Data,Size); } -inline ERROR AddMsgHandler(APTR Custom, LONG MsgType, FUNCTION * Routine, struct MsgHandler ** Handle) { return CoreBase->_AddMsgHandler(Custom,MsgType,Routine,Handle); } -inline ERROR QueueAction(LONG Action, OBJECTID Object, APTR Args) { return CoreBase->_QueueAction(Action,Object,Args); } +inline ERR CreateFolder(CSTRING Path, PERMIT Permissions) { return CoreBase->_CreateFolder(Path,Permissions); } +inline ERR LoadFile(CSTRING Path, LDF Flags, struct CacheFile ** Cache) { return CoreBase->_LoadFile(Path,Flags,Cache); } +inline ERR SetVolume(CSTRING Name, CSTRING Path, CSTRING Icon, CSTRING Label, CSTRING Device, VOLUME Flags) { return CoreBase->_SetVolume(Name,Path,Icon,Label,Device,Flags); } +inline ERR DeleteVolume(CSTRING Name) { return CoreBase->_DeleteVolume(Name); } +inline ERR MoveFile(CSTRING Source, CSTRING Dest, FUNCTION * Callback) { return CoreBase->_MoveFile(Source,Dest,Callback); } +inline ERR UpdateMessage(LONG Message, LONG Type, APTR Data, LONG Size) { return CoreBase->_UpdateMessage(Message,Type,Data,Size); } +inline ERR AddMsgHandler(APTR Custom, LONG MsgType, FUNCTION * Routine, struct MsgHandler ** Handle) { return CoreBase->_AddMsgHandler(Custom,MsgType,Routine,Handle); } +inline ERR QueueAction(LONG Action, OBJECTID Object, APTR Args) { return CoreBase->_QueueAction(Action,Object,Args); } inline LARGE PreciseTime(void) { return CoreBase->_PreciseTime(); } -inline ERROR OpenDir(CSTRING Path, RDF Flags, struct DirInfo ** Info) { return CoreBase->_OpenDir(Path,Flags,Info); } +inline ERR OpenDir(CSTRING Path, RDF Flags, struct DirInfo ** Info) { return CoreBase->_OpenDir(Path,Flags,Info); } inline OBJECTPTR GetObjectPtr(OBJECTID Object) { return CoreBase->_GetObjectPtr(Object); } inline struct Field * FindField(OBJECTPTR Object, ULONG FieldID, APTR Target) { return CoreBase->_FindField(Object,FieldID,Target); } -inline CSTRING GetErrorMsg(ERROR Error) { return CoreBase->_GetErrorMsg(Error); } +inline CSTRING GetErrorMsg(ERR Error) { return CoreBase->_GetErrorMsg(Error); } inline struct Message * GetActionMsg(void) { return CoreBase->_GetActionMsg(); } -inline ERROR FuncError(CSTRING Header, ERROR Error) { return CoreBase->_FuncError(Header,Error); } -inline ERROR SetArray(OBJECTPTR Object, FIELD Field, APTR Array, LONG Elements) { return CoreBase->_SetArray(Object,Field,Array,Elements); } +inline ERR FuncError(CSTRING Header, ERR Error) { return CoreBase->_FuncError(Header,Error); } +inline ERR SetArray(OBJECTPTR Object, FIELD Field, APTR Array, LONG Elements) { return CoreBase->_SetArray(Object,Field,Array,Elements); } inline ULONG StrHash(CSTRING String, LONG CaseSensitive) { return CoreBase->_StrHash(String,CaseSensitive); } -inline ERROR LockObject(OBJECTPTR Object, LONG MilliSeconds) { return CoreBase->_LockObject(Object,MilliSeconds); } +inline ERR LockObject(OBJECTPTR Object, LONG MilliSeconds) { return CoreBase->_LockObject(Object,MilliSeconds); } inline void ReleaseObject(OBJECTPTR Object) { return CoreBase->_ReleaseObject(Object); } -inline ERROR ActionThread(LONG Action, OBJECTPTR Object, APTR Args, FUNCTION * Callback, LONG Key) { return CoreBase->_ActionThread(Action,Object,Args,Callback,Key); } -inline ERROR AddInfoTag(struct FileInfo * Info, CSTRING Name, CSTRING Value) { return CoreBase->_AddInfoTag(Info,Name,Value); } +inline ERR ActionThread(LONG Action, OBJECTPTR Object, APTR Args, FUNCTION * Callback, LONG Key) { return CoreBase->_ActionThread(Action,Object,Args,Callback,Key); } +inline ERR AddInfoTag(struct FileInfo * Info, CSTRING Name, CSTRING Value) { return CoreBase->_AddInfoTag(Info,Name,Value); } inline void SetDefaultPermissions(LONG User, LONG Group, PERMIT Permissions) { return CoreBase->_SetDefaultPermissions(User,Group,Permissions); } inline void VLogF(VLF Flags, const char *Header, const char *Message, va_list Args) { return CoreBase->_VLogF(Flags,Header,Message,Args); } inline LONG Base64Encode(struct pfBase64Encode * State, const void * Input, LONG InputSize, STRING Output, LONG OutputSize) { return CoreBase->_Base64Encode(State,Input,InputSize,Output,OutputSize); } -inline ERROR ReadInfoTag(struct FileInfo * Info, CSTRING Name, CSTRING * Value) { return CoreBase->_ReadInfoTag(Info,Name,Value); } -inline ERROR SetResourcePath(RP PathType, CSTRING Path) { return CoreBase->_SetResourcePath(PathType,Path); } +inline ERR ReadInfoTag(struct FileInfo * Info, CSTRING Name, CSTRING * Value) { return CoreBase->_ReadInfoTag(Info,Name,Value); } +inline ERR SetResourcePath(RP PathType, CSTRING Path) { return CoreBase->_SetResourcePath(PathType,Path); } inline objTask * CurrentTask(void) { return CoreBase->_CurrentTask(); } inline CSTRING ResolveGroupID(LONG Group) { return CoreBase->_ResolveGroupID(Group); } inline CSTRING ResolveUserID(LONG User) { return CoreBase->_ResolveUserID(User); } -inline ERROR CreateLink(CSTRING From, CSTRING To) { return CoreBase->_CreateLink(From,To); } -inline ERROR DeleteFile(CSTRING Path, FUNCTION * Callback) { return CoreBase->_DeleteFile(Path,Callback); } +inline ERR CreateLink(CSTRING From, CSTRING To) { return CoreBase->_CreateLink(From,To); } +inline ERR DeleteFile(CSTRING Path, FUNCTION * Callback) { return CoreBase->_DeleteFile(Path,Callback); } inline LONG UTF8CharOffset(CSTRING String, LONG Offset) { return CoreBase->_UTF8CharOffset(String,Offset); } inline LONG UTF8Length(CSTRING String) { return CoreBase->_UTF8Length(String); } inline LONG UTF8OffsetToChar(CSTRING String, LONG Offset) { return CoreBase->_UTF8OffsetToChar(String,Offset); } @@ -2220,108 +2229,108 @@ inline LONG UTF8PrevLength(CSTRING String, LONG Offset) { return CoreBase->_UTF8 inline LONG UTF8CharLength(CSTRING String) { return CoreBase->_UTF8CharLength(String); } inline ULONG UTF8ReadValue(CSTRING String, LONG * Length) { return CoreBase->_UTF8ReadValue(String,Length); } inline LONG UTF8WriteValue(LONG Value, STRING Buffer, LONG Size) { return CoreBase->_UTF8WriteValue(Value,Buffer,Size); } -inline ERROR CopyFile(CSTRING Source, CSTRING Dest, FUNCTION * Callback) { return CoreBase->_CopyFile(Source,Dest,Callback); } -inline ERROR WaitForObjects(PMF Flags, LONG TimeOut, struct ObjectSignal * ObjectSignals) { return CoreBase->_WaitForObjects(Flags,TimeOut,ObjectSignals); } +inline ERR CopyFile(CSTRING Source, CSTRING Dest, FUNCTION * Callback) { return CoreBase->_CopyFile(Source,Dest,Callback); } +inline ERR WaitForObjects(PMF Flags, LONG TimeOut, struct ObjectSignal * ObjectSignals) { return CoreBase->_WaitForObjects(Flags,TimeOut,ObjectSignals); } #else extern "C" { -extern ERROR AccessMemory(MEMORYID Memory, MEM Flags, LONG MilliSeconds, APTR Result); -extern ERROR Action(LONG Action, OBJECTPTR Object, APTR Parameters); +extern ERR AccessMemory(MEMORYID Memory, MEM Flags, LONG MilliSeconds, APTR Result); +extern ERR Action(LONG Action, OBJECTPTR Object, APTR Parameters); extern void ActionList(struct ActionTable ** Actions, LONG * Size); -extern ERROR ActionMsg(LONG Action, OBJECTID Object, APTR Args); +extern ERR ActionMsg(LONG Action, OBJECTID Object, APTR Args); extern CSTRING ResolveClassID(CLASSID ID); extern LONG AllocateID(IDTYPE Type); -extern ERROR AllocMemory(LONG Size, MEM Flags, APTR Address, MEMORYID * ID); -extern ERROR AccessObject(OBJECTID Object, LONG MilliSeconds, APTR Result); -extern ERROR CheckAction(OBJECTPTR Object, LONG Action); -extern ERROR CheckMemoryExists(MEMORYID ID); -extern ERROR CheckObjectExists(OBJECTID Object); -extern ERROR InitObject(OBJECTPTR Object); +extern ERR AllocMemory(LONG Size, MEM Flags, APTR Address, MEMORYID * ID); +extern ERR AccessObject(OBJECTID Object, LONG MilliSeconds, APTR Result); +extern ERR CheckAction(OBJECTPTR Object, LONG Action); +extern ERR CheckMemoryExists(MEMORYID ID); +extern ERR CheckObjectExists(OBJECTID Object); +extern ERR InitObject(OBJECTPTR Object); extern OBJECTPTR CurrentContext(void); -extern ERROR GetFieldArray(OBJECTPTR Object, FIELD Field, APTR Result, LONG * Elements); +extern ERR GetFieldArray(OBJECTPTR Object, FIELD Field, APTR Result, LONG * Elements); extern LONG AdjustLogLevel(LONG Adjust); -extern ERROR ReadFileToBuffer(CSTRING Path, APTR Buffer, LONG BufferSize, LONG * Result); -extern ERROR FindObject(CSTRING Name, CLASSID ClassID, FOF Flags, OBJECTID * ObjectID); +extern ERR ReadFileToBuffer(CSTRING Path, APTR Buffer, LONG BufferSize, LONG * Result); +extern ERR FindObject(CSTRING Name, CLASSID ClassID, FOF Flags, OBJECTID * ObjectID); extern objMetaClass * FindClass(CLASSID ClassID); -extern ERROR AnalysePath(CSTRING Path, LOC * Type); +extern ERR AnalysePath(CSTRING Path, LOC * Type); extern LONG UTF8Copy(CSTRING Src, STRING Dest, LONG Chars, LONG Size); -extern ERROR FreeResource(MEMORYID ID); +extern ERR FreeResource(MEMORYID ID); extern CLASSID GetClassID(OBJECTID Object); extern OBJECTID GetOwnerID(OBJECTID Object); -extern ERROR GetField(OBJECTPTR Object, FIELD Field, APTR Result); -extern ERROR GetFieldVariable(OBJECTPTR Object, CSTRING Field, STRING Buffer, LONG Size); -extern ERROR CompareFilePaths(CSTRING PathA, CSTRING PathB); +extern ERR GetField(OBJECTPTR Object, FIELD Field, APTR Result); +extern ERR GetFieldVariable(OBJECTPTR Object, CSTRING Field, STRING Buffer, LONG Size); +extern ERR CompareFilePaths(CSTRING PathA, CSTRING PathB); extern const struct SystemState * GetSystemState(void); -extern ERROR ListChildren(OBJECTID Object, pf::vector * List); -extern ERROR Base64Decode(struct pfBase64Decode * State, CSTRING Input, LONG InputSize, APTR Output, LONG * Written); -extern ERROR RegisterFD(HOSTHANDLE FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR) , APTR Data); -extern ERROR ResolvePath(CSTRING Path, RSF Flags, STRING * Result); -extern ERROR MemoryIDInfo(MEMORYID ID, struct MemInfo * MemInfo, LONG Size); -extern ERROR MemoryPtrInfo(APTR Address, struct MemInfo * MemInfo, LONG Size); -extern ERROR NewObject(LARGE ClassID, NF Flags, APTR Object); -extern void NotifySubscribers(OBJECTPTR Object, LONG Action, APTR Args, ERROR Error); -extern ERROR StrReadLocale(CSTRING Key, CSTRING * Value); +extern ERR ListChildren(OBJECTID Object, pf::vector * List); +extern ERR Base64Decode(struct pfBase64Decode * State, CSTRING Input, LONG InputSize, APTR Output, LONG * Written); +extern ERR RegisterFD(HOSTHANDLE FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR) , APTR Data); +extern ERR ResolvePath(CSTRING Path, RSF Flags, STRING * Result); +extern ERR MemoryIDInfo(MEMORYID ID, struct MemInfo * MemInfo, LONG Size); +extern ERR MemoryPtrInfo(APTR Address, struct MemInfo * MemInfo, LONG Size); +extern ERR NewObject(LARGE ClassID, NF Flags, APTR Object); +extern void NotifySubscribers(OBJECTPTR Object, LONG Action, APTR Args, ERR Error); +extern ERR StrReadLocale(CSTRING Key, CSTRING * Value); extern CSTRING UTF8ValidEncoding(CSTRING String, CSTRING Encoding); -extern ERROR ProcessMessages(PMF Flags, LONG TimeOut); -extern ERROR IdentifyFile(CSTRING Path, CLASSID * Class, CLASSID * SubClass); -extern ERROR ReallocMemory(APTR Memory, ULONG Size, APTR Address, MEMORYID * ID); -extern ERROR GetMessage(LONG Type, MSF Flags, APTR Buffer, LONG Size); -extern ERROR ReleaseMemory(MEMORYID MemoryID); +extern ERR ProcessMessages(PMF Flags, LONG TimeOut); +extern ERR IdentifyFile(CSTRING Path, CLASSID * Class, CLASSID * SubClass); +extern ERR ReallocMemory(APTR Memory, ULONG Size, APTR Address, MEMORYID * ID); +extern ERR GetMessage(LONG Type, MSF Flags, APTR Buffer, LONG Size); +extern ERR ReleaseMemory(MEMORYID MemoryID); extern CLASSID ResolveClassName(CSTRING Name); -extern ERROR SendMessage(LONG Type, MSF Flags, APTR Data, LONG Size); -extern ERROR SetOwner(OBJECTPTR Object, OBJECTPTR Owner); +extern ERR SendMessage(LONG Type, MSF Flags, APTR Data, LONG Size); +extern ERR SetOwner(OBJECTPTR Object, OBJECTPTR Owner); extern OBJECTPTR SetContext(OBJECTPTR Object); -extern ERROR SetField(OBJECTPTR Object, FIELD Field, ...); +extern ERR SetField(OBJECTPTR Object, FIELD Field, ...); extern CSTRING FieldName(ULONG FieldID); -extern ERROR ScanDir(struct DirInfo * Info); -extern ERROR SetName(OBJECTPTR Object, CSTRING Name); +extern ERR ScanDir(struct DirInfo * Info); +extern ERR SetName(OBJECTPTR Object, CSTRING Name); extern void LogReturn(void); -extern ERROR StrCompare(CSTRING String1, CSTRING String2, LONG Length, STR Flags); -extern ERROR SubscribeAction(OBJECTPTR Object, LONG Action, FUNCTION * Callback); -extern ERROR SubscribeEvent(LARGE Event, FUNCTION * Callback, APTR Custom, APTR Handle); -extern ERROR SubscribeTimer(DOUBLE Interval, FUNCTION * Callback, APTR Subscription); -extern ERROR UpdateTimer(APTR Subscription, DOUBLE Interval); -extern ERROR UnsubscribeAction(OBJECTPTR Object, LONG Action); +extern ERR StrCompare(CSTRING String1, CSTRING String2, LONG Length, STR Flags); +extern ERR SubscribeAction(OBJECTPTR Object, LONG Action, FUNCTION * Callback); +extern ERR SubscribeEvent(LARGE Event, FUNCTION * Callback, APTR Custom, APTR Handle); +extern ERR SubscribeTimer(DOUBLE Interval, FUNCTION * Callback, APTR Subscription); +extern ERR UpdateTimer(APTR Subscription, DOUBLE Interval); +extern ERR UnsubscribeAction(OBJECTPTR Object, LONG Action); extern void UnsubscribeEvent(APTR Handle); -extern ERROR BroadcastEvent(APTR Event, LONG EventSize); +extern ERR BroadcastEvent(APTR Event, LONG EventSize); extern void WaitTime(LONG Seconds, LONG MicroSeconds); extern LARGE GetEventID(EVG Group, CSTRING SubGroup, CSTRING Event); extern ULONG GenCRC32(ULONG CRC, APTR Data, ULONG Length); extern LARGE GetResource(RES Resource); extern LARGE SetResource(RES Resource, LARGE Value); -extern ERROR ScanMessages(LONG * Handle, LONG Type, APTR Buffer, LONG Size); +extern ERR ScanMessages(LONG * Handle, LONG Type, APTR Buffer, LONG Size); extern STT StrDatatype(CSTRING String); extern void UnloadFile(struct CacheFile * Cache); -extern ERROR CreateFolder(CSTRING Path, PERMIT Permissions); -extern ERROR LoadFile(CSTRING Path, LDF Flags, struct CacheFile ** Cache); -extern ERROR SetVolume(CSTRING Name, CSTRING Path, CSTRING Icon, CSTRING Label, CSTRING Device, VOLUME Flags); -extern ERROR DeleteVolume(CSTRING Name); -extern ERROR MoveFile(CSTRING Source, CSTRING Dest, FUNCTION * Callback); -extern ERROR UpdateMessage(LONG Message, LONG Type, APTR Data, LONG Size); -extern ERROR AddMsgHandler(APTR Custom, LONG MsgType, FUNCTION * Routine, struct MsgHandler ** Handle); -extern ERROR QueueAction(LONG Action, OBJECTID Object, APTR Args); +extern ERR CreateFolder(CSTRING Path, PERMIT Permissions); +extern ERR LoadFile(CSTRING Path, LDF Flags, struct CacheFile ** Cache); +extern ERR SetVolume(CSTRING Name, CSTRING Path, CSTRING Icon, CSTRING Label, CSTRING Device, VOLUME Flags); +extern ERR DeleteVolume(CSTRING Name); +extern ERR MoveFile(CSTRING Source, CSTRING Dest, FUNCTION * Callback); +extern ERR UpdateMessage(LONG Message, LONG Type, APTR Data, LONG Size); +extern ERR AddMsgHandler(APTR Custom, LONG MsgType, FUNCTION * Routine, struct MsgHandler ** Handle); +extern ERR QueueAction(LONG Action, OBJECTID Object, APTR Args); extern LARGE PreciseTime(void); -extern ERROR OpenDir(CSTRING Path, RDF Flags, struct DirInfo ** Info); +extern ERR OpenDir(CSTRING Path, RDF Flags, struct DirInfo ** Info); extern OBJECTPTR GetObjectPtr(OBJECTID Object); extern struct Field * FindField(OBJECTPTR Object, ULONG FieldID, APTR Target); -extern CSTRING GetErrorMsg(ERROR Error); +extern CSTRING GetErrorMsg(ERR Error); extern struct Message * GetActionMsg(void); -extern ERROR FuncError(CSTRING Header, ERROR Error); -extern ERROR SetArray(OBJECTPTR Object, FIELD Field, APTR Array, LONG Elements); +extern ERR FuncError(CSTRING Header, ERR Error); +extern ERR SetArray(OBJECTPTR Object, FIELD Field, APTR Array, LONG Elements); extern ULONG StrHash(CSTRING String, LONG CaseSensitive); -extern ERROR LockObject(OBJECTPTR Object, LONG MilliSeconds); +extern ERR LockObject(OBJECTPTR Object, LONG MilliSeconds); extern void ReleaseObject(OBJECTPTR Object); -extern ERROR ActionThread(LONG Action, OBJECTPTR Object, APTR Args, FUNCTION * Callback, LONG Key); -extern ERROR AddInfoTag(struct FileInfo * Info, CSTRING Name, CSTRING Value); +extern ERR ActionThread(LONG Action, OBJECTPTR Object, APTR Args, FUNCTION * Callback, LONG Key); +extern ERR AddInfoTag(struct FileInfo * Info, CSTRING Name, CSTRING Value); extern void SetDefaultPermissions(LONG User, LONG Group, PERMIT Permissions); extern void VLogF(VLF Flags, const char *Header, const char *Message, va_list Args); extern LONG Base64Encode(struct pfBase64Encode * State, const void * Input, LONG InputSize, STRING Output, LONG OutputSize); -extern ERROR ReadInfoTag(struct FileInfo * Info, CSTRING Name, CSTRING * Value); -extern ERROR SetResourcePath(RP PathType, CSTRING Path); +extern ERR ReadInfoTag(struct FileInfo * Info, CSTRING Name, CSTRING * Value); +extern ERR SetResourcePath(RP PathType, CSTRING Path); extern objTask * CurrentTask(void); extern CSTRING ResolveGroupID(LONG Group); extern CSTRING ResolveUserID(LONG User); -extern ERROR CreateLink(CSTRING From, CSTRING To); -extern ERROR DeleteFile(CSTRING Path, FUNCTION * Callback); +extern ERR CreateLink(CSTRING From, CSTRING To); +extern ERR DeleteFile(CSTRING Path, FUNCTION * Callback); extern LONG UTF8CharOffset(CSTRING String, LONG Offset); extern LONG UTF8Length(CSTRING String); extern LONG UTF8OffsetToChar(CSTRING String, LONG Offset); @@ -2329,8 +2338,8 @@ extern LONG UTF8PrevLength(CSTRING String, LONG Offset); extern LONG UTF8CharLength(CSTRING String); extern ULONG UTF8ReadValue(CSTRING String, LONG * Length); extern LONG UTF8WriteValue(LONG Value, STRING Buffer, LONG Size); -extern ERROR CopyFile(CSTRING Source, CSTRING Dest, FUNCTION * Callback); -extern ERROR WaitForObjects(PMF Flags, LONG TimeOut, struct ObjectSignal * ObjectSignals); +extern ERR CopyFile(CSTRING Source, CSTRING Dest, FUNCTION * Callback); +extern ERR WaitForObjects(PMF Flags, LONG TimeOut, struct ObjectSignal * ObjectSignals); } #endif // PARASOL_STATIC #endif @@ -2346,7 +2355,7 @@ template inline MEMORYID GetMemoryID(T &&A) { return ((MEMORYID *)A)[-2]; } -inline ERROR DeregisterFD(HOSTHANDLE Handle) { +inline ERR DeregisterFD(HOSTHANDLE Handle) { return RegisterFD(Handle, RFD::REMOVE|RFD::READ|RFD::WRITE|RFD::EXCEPT|RFD::ALWAYS_CALL, 0, 0); } @@ -2358,7 +2367,7 @@ inline APTR GetResourcePtr(RES ID) { return (APTR)(MAXINT)GetResource(ID); } inline CSTRING to_cstring(const std::string &A) { return A.c_str(); } constexpr inline CSTRING to_cstring(CSTRING A) { return A; } -template inline ERROR StrMatch(T &&A, U &&B) { +template inline ERR StrMatch(T &&A, U &&B) { return StrCompare(to_cstring(A), to_cstring(B), 0, STR::MATCH_LEN); } @@ -2382,38 +2391,51 @@ template inline LONG StrCopy(T &&Source, STRING Dest, LONG Length = 0x } #ifndef PRV_CORE_DATA +// These overloaded functions can't be used in the Core as they will confuse the compiler in key areas. -inline ERROR ReleaseMemory(const void *Address) { - if (!Address) return ERR_NullArgs; +inline ERR SubscribeAction(OBJECTPTR Object, LONG Action, FUNCTION Callback) { + return SubscribeAction(Object,Action,&Callback); +} + +inline ERR SubscribeEvent(LARGE Event, FUNCTION Callback, APTR Custom, APTR Handle) { + return SubscribeEvent(Event,&Callback,Custom,Handle); +} + +inline ERR SubscribeTimer(DOUBLE Interval, FUNCTION Callback, APTR Subscription) { + return SubscribeTimer(Interval,&Callback,Subscription); +} + +inline ERR ReleaseMemory(const void *Address) { + if (!Address) return ERR::NullArgs; return ReleaseMemory(((MEMORYID *)Address)[-2]); } -inline ERROR FreeResource(const void *Address) { - if (!Address) return ERR_NullArgs; +inline ERR FreeResource(const void *Address) { + if (!Address) return ERR::NullArgs; return FreeResource(((LONG *)Address)[-2]); } -inline ERROR AllocMemory(LONG Size, MEM Flags, APTR Address) { +inline ERR AllocMemory(LONG Size, MEM Flags, APTR Address) { return AllocMemory(Size, Flags, (APTR *)Address, NULL); } -template inline ERROR NewObject(LARGE ClassID, T **Result) { +template inline ERR NewObject(LARGE ClassID, T **Result) { return NewObject(ClassID, NF::NIL, Result); } -inline ERROR MemoryIDInfo(MEMORYID ID, struct MemInfo * MemInfo) { +inline ERR MemoryIDInfo(MEMORYID ID, struct MemInfo * MemInfo) { return MemoryIDInfo(ID,MemInfo,sizeof(struct MemInfo)); } -inline ERROR MemoryPtrInfo(APTR Address, struct MemInfo * MemInfo) { +inline ERR MemoryPtrInfo(APTR Address, struct MemInfo * MemInfo) { return MemoryPtrInfo(Address,MemInfo,sizeof(struct MemInfo)); } -inline ERROR QueueAction(LONG Action, OBJECTID ObjectID) { +inline ERR QueueAction(LONG Action, OBJECTID ObjectID) { return QueueAction(Action, ObjectID, NULL); } -template inline ERROR StrCompare(T &&A, U &&B, LONG Length = 0, STR Flags = STR::NIL) { +template inline ERR StrCompare(T &&A, U &&B, LONG Length = 0, STR Flags = STR::NIL) { return StrCompare(to_cstring(A), to_cstring(B), Length, Flags); } @@ -2421,18 +2443,23 @@ inline ULONG StrHash(const std::string Value) { return StrHash(Value.c_str(), FALSE); } -template inline ERROR SetArray(OBJECTPTR Object, FIELD FieldID, pf::vector Array) +template inline ERR SetArray(OBJECTPTR Object, FIELD FieldID, pf::vector &Array) { return SetArray(Object, FieldID, Array.data(), Array.size()); } -template inline ERROR SetArray(OBJECTPTR Object, FIELD FieldID, std::vector Array) +template inline ERR SetArray(OBJECTPTR Object, FIELD FieldID, std::vector &Array) { return SetArray(Object, FieldID, Array.data(), Array.size()); } + +template inline ERR SetArray(OBJECTPTR Object, FIELD FieldID, std::array Array) +{ + return SetArray(Object, FieldID, Array.data(), SIZE); +} #endif -typedef std::map ConfigKeys; +typedef KEYVALUE ConfigKeys; typedef std::pair ConfigGroup; typedef std::vector ConfigGroups; @@ -2473,7 +2500,7 @@ inline void CopyMemory(const void *Src, APTR Dest, LONG Length) auto len = LONG(strlen(String)); STRING newstr; - if (!AllocMemory(len+1, MEM::STRING, (APTR *)&newstr, NULL)) { + if (AllocMemory(len+1, MEM::STRING, (APTR *)&newstr, NULL) IS ERR::Okay) { CopyMemory(String, newstr, len+1); return newstr; } @@ -2520,10 +2547,10 @@ inline LONG IntToStr(LARGE Integer, STRING String, LONG StringSize) { return len; } -inline ERROR ClearMemory(APTR Memory, LONG Length) { - if (!Memory) return ERR_NullArgs; +inline ERR ClearMemory(APTR Memory, LONG Length) { + if (!Memory) return ERR::NullArgs; memset(Memory, 0, Length); // memset() is assumed to be optimised by the compiler. - return ERR_Okay; + return ERR::Okay; } namespace pf { @@ -2604,10 +2631,10 @@ class Log { // C++ wrapper for Parasol's log functionality if ((Flags & VLF::BRANCH) != VLF::NIL) branches++; } - void extmsg(CSTRING Message, ...) __attribute__((format(printf, 2, 3))) { // Extended API message + void detail(CSTRING Message, ...) __attribute__((format(printf, 2, 3))) { // Detailed API message va_list arg; va_start(arg, Message); - VLogF(VLF::EXTAPI, header, Message, arg); + VLogF(VLF::DETAIL, header, Message, arg); va_end(arg); } @@ -2632,13 +2659,6 @@ class Log { // C++ wrapper for Parasol's log functionality va_end(arg); } - void debug(CSTRING Message, ...) __attribute__((format(printf, 2, 3))) { - va_list arg; - va_start(arg, Message); - VLogF(VLF::DEBUG, header, Message, arg); - va_end(arg); - } - void function(CSTRING Message, ...) __attribute__((format(printf, 2, 3))) { // Equivalent to branch() but without a new branch being created va_list arg; va_start(arg, Message); @@ -2646,12 +2666,12 @@ class Log { // C++ wrapper for Parasol's log functionality va_end(arg); } - ERROR error(ERROR Code) { // Technically a warning + ERR error(ERR Code) { // Technically a warning FuncError(header, Code); return Code; } - ERROR warning(ERROR Code) { + ERR warning(ERR Code) { FuncError(header, Code); return Code; } @@ -2673,10 +2693,44 @@ class Log { // C++ wrapper for Parasol's log functionality va_end(arg); #endif } + + ERR traceWarning(ERR Code) { + #ifdef _DEBUG + FuncError(header, Code); + #endif + return Code; + } +}; + +class LogLevel { + private: + LONG level; + public: + LogLevel(LONG Level) : level(Level) { + AdjustLogLevel(Level); + } + + ~LogLevel() { + AdjustLogLevel(-level); + } }; } // namespace +//******************************************************************************************************************** +// Refer to BaseClass->get() to see what this is about... + +template inline LARGE FIELD_TAG() { return 0; } +template <> inline LARGE FIELD_TAG() { return TDOUBLE; } +template <> inline LARGE FIELD_TAG() { return TLONG; } +template <> inline LARGE FIELD_TAG() { return TFLOAT; } +template <> inline LARGE FIELD_TAG() { return TPTR; } +template <> inline LARGE FIELD_TAG() { return TPTR; } +template <> inline LARGE FIELD_TAG() { return TLARGE; } +template <> inline LARGE FIELD_TAG() { return TSTRING; } +template <> inline LARGE FIELD_TAG() { return TSTRING; } +template <> inline LARGE FIELD_TAG() { return TDOUBLE|TSCALE; } + //******************************************************************************************************************** // Header used for all objects. @@ -2686,10 +2740,11 @@ struct BaseClass { // Must be 64-bit aligned class extMetaClass *ExtClass; // [Private] Internal version of the class pointer }; APTR ChildPrivate; // Address for the ChildPrivate structure, if allocated - APTR CreatorMeta; // The creator (via NewObject) is permitted to store a custom data pointer here. + APTR CreatorMeta; // The creator of the object is permitted to store a custom data pointer here. + struct BaseClass *Owner; // The owner of this object std::atomic_uint64_t NotifyFlags; // Action subscription flags - space for 64 actions max + LONG Dummy; // For 64-bit alignment OBJECTID UID; // Unique object identifier - OBJECTID OwnerID; // The owner of this object NF Flags; // Object flags volatile LONG ThreadID; // Managed by locking functions char Name[MAX_NAME_LEN]; // The name of the object (optional) @@ -2702,13 +2757,13 @@ struct BaseClass { // Must be 64-bit aligned inline bool initialised() { return (Flags & NF::INITIALISED) != NF::NIL; } inline bool defined(NF pFlags) { return (Flags & pFlags) != NF::NIL; } inline bool isSubClass(); - inline OBJECTID ownerID() { return OwnerID; } + inline OBJECTID ownerID() { return Owner ? Owner->UID : 0; } inline NF flags() { return Flags; } CSTRING className(); inline bool collecting() { // Is object being freed or marked for collection? - return (Flags & (NF::FREE|NF::COLLECT)) != NF::NIL; + return (Flags & (NF::FREE|NF::COLLECT|NF::FREE_ON_UNLOCK)) != NF::NIL; } inline bool terminating() { // Is object currently being freed? @@ -2717,13 +2772,13 @@ struct BaseClass { // Must be 64-bit aligned // Use lock() to quickly obtain an object lock without a call to LockObject() - inline ERROR lock() { + inline ERR lock() { if (++Queue IS 1) { ThreadID = pf::_get_thread_id(); - return ERR_Okay; + return ERR::Okay; } else { - if (ThreadID IS pf::_get_thread_id()) return ERR_Okay; // If this is for the same thread then it's a nested lock, so there's no issue. + if (ThreadID IS pf::_get_thread_id()) return ERR::Okay; // If this is for the same thread then it's a nested lock, so there's no issue. --Queue; // Restore the lock count return LockObject(this, -1); // Can fail if object is marked for deletion. } @@ -2736,54 +2791,64 @@ struct BaseClass { // Must be 64-bit aligned } inline bool hasOwner(OBJECTID ID) { // Return true if ID has ownership. - auto oid = this->OwnerID; - while ((oid) and (oid != ID)) oid = GetOwnerID(oid); - return oid ? true : false; - } - - inline ERROR set(ULONG FieldID, int Value) { return SetField(this, (FIELD)FieldID|TLONG, Value); } - inline ERROR set(ULONG FieldID, unsigned int Value) { return SetField(this, (FIELD)FieldID|TLONG, Value); } - inline ERROR set(ULONG FieldID, LARGE Value) { return SetField(this, (FIELD)FieldID|TLARGE, Value); } - inline ERROR set(ULONG FieldID, DOUBLE Value) { return SetField(this, (FIELD)FieldID|TDOUBLE, Value); } - inline ERROR set(ULONG FieldID, const FUNCTION *Value) { return SetField(this, (FIELD)FieldID|TFUNCTION, Value); } - inline ERROR set(ULONG FieldID, const char *Value) { return SetField(this, (FIELD)FieldID|TSTRING, Value); } - inline ERROR set(ULONG FieldID, const unsigned char *Value) { return SetField(this, (FIELD)FieldID|TSTRING, Value); } - inline ERROR set(ULONG FieldID, const std::string &Value) { return SetField(this, (FIELD)FieldID|TSTRING, Value.c_str()); } - inline ERROR set(ULONG FieldID, const Variable *Value) { return SetField(this, (FIELD)FieldID|TVAR, Value); } + auto obj = this->Owner; + while ((obj) and (obj->UID != ID)) obj = obj->Owner; + return obj ? true : false; + } + + inline ERR set(ULONG FieldID, int Value) { return SetField(this, (FIELD)FieldID|TLONG, Value); } + inline ERR set(ULONG FieldID, unsigned int Value) { return SetField(this, (FIELD)FieldID|TLONG, Value); } + inline ERR set(ULONG FieldID, LARGE Value) { return SetField(this, (FIELD)FieldID|TLARGE, Value); } + inline ERR set(ULONG FieldID, DOUBLE Value) { return SetField(this, (FIELD)FieldID|TDOUBLE, Value); } + inline ERR set(ULONG FieldID, const FUNCTION *Value) { return SetField(this, (FIELD)FieldID|TFUNCTION, Value); } + inline ERR set(ULONG FieldID, const char *Value) { return SetField(this, (FIELD)FieldID|TSTRING, Value); } + inline ERR set(ULONG FieldID, const unsigned char *Value) { return SetField(this, (FIELD)FieldID|TSTRING, Value); } + inline ERR set(ULONG FieldID, const std::string &Value) { return SetField(this, (FIELD)FieldID|TSTRING, Value.c_str()); } + inline ERR set(ULONG FieldID, const Variable *Value) { return SetField(this, (FIELD)FieldID|TVAR, Value); } // Works both for regular data pointers and function pointers if field is defined correctly. - inline ERROR set(ULONG FieldID, const void *Value) { return SetField(this, (FIELD)FieldID|TPTR, Value); } - - inline ERROR setPercentage(ULONG FieldID, DOUBLE Value) { return SetField(this, (FIELD)FieldID|TDOUBLE|TPERCENT, Value); } - - inline ERROR get(ULONG FieldID, LONG *Value) { return GetField(this, (FIELD)FieldID|TLONG, Value); } - inline ERROR get(ULONG FieldID, LARGE *Value) { return GetField(this, (FIELD)FieldID|TLARGE, Value); } - inline ERROR get(ULONG FieldID, DOUBLE *Value) { return GetField(this, (FIELD)FieldID|TDOUBLE, Value); } - inline ERROR get(ULONG FieldID, STRING *Value) { return GetField(this, (FIELD)FieldID|TSTRING, Value); } - inline ERROR get(ULONG FieldID, CSTRING *Value) { return GetField(this, (FIELD)FieldID|TSTRING, Value); } - inline ERROR get(ULONG FieldID, Variable *Value) { return GetField(this, (FIELD)FieldID|TVAR, Value); } - inline ERROR getPtr(ULONG FieldID, APTR Value) { return GetField(this, (FIELD)FieldID|TPTR, Value); } - inline ERROR getPercentage(ULONG FieldID, DOUBLE *Value) { return GetField(this, (FIELD)FieldID|TDOUBLE|TPERCENT, Value); } + inline ERR set(ULONG FieldID, const void *Value) { return SetField(this, (FIELD)FieldID|TPTR, Value); } + + inline ERR setScale(ULONG FieldID, DOUBLE Value) { return SetField(this, (FIELD)FieldID|TDOUBLE|TSCALE, Value); } + + // There are two mechanisms for retrieving object values; the first allows the value to be retrieved with an error + // code and the value itself; the second ignores the error code and returns a value that could potentially be invalid. + + inline ERR get(ULONG FieldID, LONG *Value) { return GetField(this, (FIELD)FieldID|TLONG, Value); } + inline ERR get(ULONG FieldID, LARGE *Value) { return GetField(this, (FIELD)FieldID|TLARGE, Value); } + inline ERR get(ULONG FieldID, DOUBLE *Value) { return GetField(this, (FIELD)FieldID|TDOUBLE, Value); } + inline ERR get(ULONG FieldID, STRING *Value) { return GetField(this, (FIELD)FieldID|TSTRING, Value); } + inline ERR get(ULONG FieldID, CSTRING *Value) { return GetField(this, (FIELD)FieldID|TSTRING, Value); } + inline ERR get(ULONG FieldID, Variable *Value) { return GetField(this, (FIELD)FieldID|TVAR, Value); } + inline ERR getPtr(ULONG FieldID, APTR Value) { return GetField(this, (FIELD)FieldID|TPTR, Value); } + inline ERR getScale(ULONG FieldID, DOUBLE *Value) { return GetField(this, (FIELD)FieldID|TDOUBLE|TSCALE, Value); } + + template inline T get(ULONG FieldID) { // Validity of the result is not guaranteed + T val; + GetField(this, (FIELD)FieldID|FIELD_TAG(), &val); + return val; + }; - template ERROR setFields(Args&&... pFields) { + template ERR setFields(Args&&... pFields) { pf::Log log("setFields"); lock(); std::initializer_list Fields = { std::forward(pFields)... }; + auto ctx = CurrentContext(); for (auto &f : Fields) { OBJECTPTR target; if (auto field = FindField(this, f.FieldID, &target)) { - if ((!(field->Flags & (FD_INIT|FD_WRITE))) and (CurrentContext() != target)) { - log.warning("Field \"%s\" of class %s is not writeable.", field->Name, className()); + if ((!(field->Flags & (FD_INIT|FD_WRITE))) and (ctx != target)) { + log.warning("%s.%s is immutable.", className(), field->Name); } - else if ((field->Flags & FD_INIT) and (target->initialised()) and (CurrentContext() != target)) { - log.warning("Field \"%s\" of class %s is init-only.", field->Name, className()); + else if ((field->Flags & FD_INIT) and (target->initialised()) and (ctx != target)) { + log.warning("%s.%s is init-only.", className(), field->Name); } else { if (target != this) target->lock(); - ERROR error; + ERR error; if (f.Type & (FD_POINTER|FD_STRING|FD_ARRAY|FD_FUNCTION|FD_VARIABLE)) { error = field->WriteValue(target, field, f.Type, f.Pointer, 0); } @@ -2799,22 +2864,21 @@ struct BaseClass { // Must be 64-bit aligned // NB: NoSupport is considered a 'soft' error that does not warrant failure. - if ((error) and (error != ERR_NoSupport)) { - log.warning("(%s:%d) Failed to set field %s (error #%d).", target->className(), target->UID, field->Name, error); + if ((error != ERR::Okay) and (error != ERR::NoSupport)) { + log.warning("%s.%s: %s", target->className(), field->Name, GetErrorMsg(error)); unlock(); return error; } } } else { - log.warning("Field %s is not supported by class %s.", FieldName(f.FieldID), className()); unlock(); - return ERR_UnsupportedField; + return log.warning(ERR::UnsupportedField); } } unlock(); - return ERR_Okay; + return ERR::Okay; } } __attribute__ ((aligned (8))); @@ -2827,9 +2891,10 @@ class Create { T *obj; public: - ERROR error; + ERR error; - // Return an unscoped direct object pointer. NB: Globals are still tracked + // Return an unscoped direct object pointer. NB: Globals are still tracked to their owner; use untracked() if + // you don't want this. template static T * global(Args&&... Fields) { pf::Create object = { std::forward(Fields)... }; @@ -2841,7 +2906,18 @@ class Create { else return NULL; } - // Return an unscoped integral object (suitable for class allocations only). + inline static T * global(const std::initializer_list Fields) { + pf::Create object(Fields); + if (object.ok()) { + auto result = *object; + object.obj = NULL; + return result; + } + else return NULL; + } + + // Return an unscoped integral object (suitable for class allocations only). This marks the object as + // being 'hidden' from the client unless explicitly makes it available. template static T * integral(Args&&... Fields) { pf::Create object({ std::forward(Fields)... }, NF::INTEGRAL); @@ -2849,6 +2925,12 @@ class Create { else return NULL; } + inline static T * integral(const std::initializer_list Fields) { + pf::Create object(Fields, NF::INTEGRAL); + if (object.ok()) return *object; + else return NULL; + } + // Return an unscoped and untracked object pointer. template static T * untracked(Args&&... Fields) { @@ -2857,30 +2939,32 @@ class Create { else return NULL; } + inline static T * untracked(const std::initializer_list Fields) { + pf::Create object(Fields, NF::UNTRACKED); + if (object.ok()) return *object; + else return NULL; + } + // Create a scoped object that is not initialised. - Create(NF Flags = NF::NIL) : obj(NULL), error(ERR_NewObject) { - if (!NewObject(T::CLASS_ID, Flags, (BaseClass **)&obj)) { - error = ERR_Okay; + Create(NF Flags = NF::NIL) : obj(NULL), error(ERR::NewObject) { + if (NewObject(T::CLASS_ID, Flags, (BaseClass **)&obj) IS ERR::Okay) { + error = ERR::Okay; } } // Create a scoped object that is fully initialised. - Create(std::initializer_list Fields, NF Flags = NF::NIL) : obj(NULL), error(ERR_Failed) { + Create(const std::initializer_list Fields, NF Flags = NF::NIL) : obj(NULL), error(ERR::Failed) { pf::Log log("CreateObject"); log.branch(T::CLASS_NAME); - if (!NewObject(T::CLASS_ID, NF::SUPPRESS_LOG|Flags, (BaseClass **)&obj)) { + if (NewObject(T::CLASS_ID, NF::SUPPRESS_LOG|Flags, (BaseClass **)&obj) IS ERR::Okay) { for (auto &f : Fields) { OBJECTPTR target; if (auto field = FindField(obj, f.FieldID, &target)) { - if ((!(field->Flags & (FD_INIT|FD_WRITE))) and (CurrentContext() != target)) { - error = log.warning(ERR_NoFieldAccess); - return; - } - else if ((field->Flags & FD_INIT) and (target->initialised()) and (CurrentContext() != target)) { - error = log.warning(ERR_NoFieldAccess); + if (!(field->Flags & (FD_WRITE|FD_INIT))) { + error = log.warning(ERR::NoFieldAccess); return; } else { @@ -2895,30 +2979,28 @@ class Create { else if (f.Type & FD_LARGE) { error = field->WriteValue(target, field, f.Type, &f.Large, 1); } - else { - error = field->WriteValue(target, field, f.Type, &f.Long, 1); - } + else error = field->WriteValue(target, field, f.Type, &f.Long, 1); target->unlock(); // NB: NoSupport is considered a 'soft' error that does not warrant failure. - if ((error) and (error != ERR_NoSupport)) return; + if ((error != ERR::Okay) and (error != ERR::NoSupport)) return; } } else { - log.warning("Field %s is not supported by class %s.", FieldName(f.FieldID), T::CLASS_NAME); - error = log.warning(ERR_UnsupportedField); + log.warning("%s.%s field not supported.", T::CLASS_NAME, FieldName(f.FieldID)); + error = log.warning(ERR::UnsupportedField); return; } } - if ((error = InitObject(obj))) { + if ((error = InitObject(obj)) != ERR::Okay) { FreeResource(obj->UID); obj = NULL; } } - else error = ERR_NewObject; + else error = ERR::NewObject; } ~Create() { @@ -2936,7 +3018,7 @@ class Create { T * operator->() { return obj; }; // Promotes underlying methods and fields T * & operator*() { return obj; }; // To allow object pointer referencing when calling functions - inline bool ok() { return error == ERR_Okay; } + inline bool ok() { return error == ERR::Okay; } }; } @@ -2973,68 +3055,67 @@ struct acWrite { CPTR Buffer; LONG Length; LONG Result; }; // Action Macros -inline ERROR acActivate(OBJECTPTR Object) { return Action(AC_Activate,Object,NULL); } -inline ERROR acClear(OBJECTPTR Object) { return Action(AC_Clear,Object,NULL); } -inline ERROR acDeactivate(OBJECTPTR Object) { return Action(AC_Deactivate,Object,NULL); } -inline ERROR acDisable(OBJECTPTR Object) { return Action(AC_Disable,Object,NULL); } -inline ERROR acDraw(OBJECTPTR Object) { return Action(AC_Draw,Object,NULL); } -inline ERROR acEnable(OBJECTPTR Object) { return Action(AC_Enable,Object,NULL); } -inline ERROR acFlush(OBJECTPTR Object) { return Action(AC_Flush,Object,NULL); } -inline ERROR acFocus(OBJECTPTR Object) { return Action(AC_Focus,Object,NULL); } -inline ERROR acHide(OBJECTPTR Object) { return Action(AC_Hide,Object,NULL); } -inline ERROR acLock(OBJECTPTR Object) { return Action(AC_Lock,Object,NULL); } -inline ERROR acLostFocus(OBJECTPTR Object) { return Action(AC_LostFocus,Object,NULL); } -inline ERROR acMoveToBack(OBJECTPTR Object) { return Action(AC_MoveToBack,Object,NULL); } -inline ERROR acMoveToFront(OBJECTPTR Object) { return Action(AC_MoveToFront,Object,NULL); } -inline ERROR acNext(OBJECTPTR Object) { return Action(AC_Next,Object,NULL); } -inline ERROR acPrev(OBJECTPTR Object) { return Action(AC_Prev,Object,NULL); } -inline ERROR acQuery(OBJECTPTR Object) { return Action(AC_Query,Object,NULL); } -inline ERROR acRefresh(OBJECTPTR Object) { return Action(AC_Refresh, Object, NULL); } -inline ERROR acReset(OBJECTPTR Object) { return Action(AC_Reset,Object,NULL); } -inline ERROR acSaveSettings(OBJECTPTR Object) { return Action(AC_SaveSettings,Object,NULL); } -inline ERROR acShow(OBJECTPTR Object) { return Action(AC_Show,Object,NULL); } -inline ERROR acSignal(OBJECTPTR Object) { return Action(AC_Signal,Object,NULL); } -inline ERROR acSort(OBJECTPTR Object) { return Action(AC_Sort,Object,NULL); } -inline ERROR acUnlock(OBJECTPTR Object) { return Action(AC_Unlock,Object,NULL); } - -inline ERROR acClipboard(OBJECTPTR Object, CLIPMODE Mode) { +inline ERR acActivate(OBJECTPTR Object) { return Action(AC_Activate,Object,NULL); } +inline ERR acClear(OBJECTPTR Object) { return Action(AC_Clear,Object,NULL); } +inline ERR acDeactivate(OBJECTPTR Object) { return Action(AC_Deactivate,Object,NULL); } +inline ERR acDisable(OBJECTPTR Object) { return Action(AC_Disable,Object,NULL); } +inline ERR acDraw(OBJECTPTR Object) { return Action(AC_Draw,Object,NULL); } +inline ERR acEnable(OBJECTPTR Object) { return Action(AC_Enable,Object,NULL); } +inline ERR acFlush(OBJECTPTR Object) { return Action(AC_Flush,Object,NULL); } +inline ERR acFocus(OBJECTPTR Object) { return Action(AC_Focus,Object,NULL); } +inline ERR acHide(OBJECTPTR Object) { return Action(AC_Hide,Object,NULL); } +inline ERR acLock(OBJECTPTR Object) { return Action(AC_Lock,Object,NULL); } +inline ERR acLostFocus(OBJECTPTR Object) { return Action(AC_LostFocus,Object,NULL); } +inline ERR acMoveToBack(OBJECTPTR Object) { return Action(AC_MoveToBack,Object,NULL); } +inline ERR acMoveToFront(OBJECTPTR Object) { return Action(AC_MoveToFront,Object,NULL); } +inline ERR acNext(OBJECTPTR Object) { return Action(AC_Next,Object,NULL); } +inline ERR acPrev(OBJECTPTR Object) { return Action(AC_Prev,Object,NULL); } +inline ERR acQuery(OBJECTPTR Object) { return Action(AC_Query,Object,NULL); } +inline ERR acRefresh(OBJECTPTR Object) { return Action(AC_Refresh, Object, NULL); } +inline ERR acReset(OBJECTPTR Object) { return Action(AC_Reset,Object,NULL); } +inline ERR acSaveSettings(OBJECTPTR Object) { return Action(AC_SaveSettings,Object,NULL); } +inline ERR acShow(OBJECTPTR Object) { return Action(AC_Show,Object,NULL); } +inline ERR acSignal(OBJECTPTR Object) { return Action(AC_Signal,Object,NULL); } +inline ERR acSort(OBJECTPTR Object) { return Action(AC_Sort,Object,NULL); } +inline ERR acUnlock(OBJECTPTR Object) { return Action(AC_Unlock,Object,NULL); } + +inline ERR acClipboard(OBJECTPTR Object, CLIPMODE Mode) { struct acClipboard args = { Mode }; return Action(AC_Clipboard, Object, &args); } -inline ERROR acDragDrop(OBJECTPTR Object, OBJECTPTR Source, LONG Item, CSTRING Datatype) { +inline ERR acDragDrop(OBJECTPTR Object, OBJECTPTR Source, LONG Item, CSTRING Datatype) { struct acDragDrop args = { Source, Item, Datatype }; return Action(AC_DragDrop, Object, &args); } -inline ERROR acDrawArea(OBJECTPTR Object, LONG X, LONG Y, LONG Width, LONG Height) { +inline ERR acDrawArea(OBJECTPTR Object, LONG X, LONG Y, LONG Width, LONG Height) { struct acDraw args = { X, Y, Width, Height }; return Action(AC_Draw, Object, &args); } -inline ERROR acDataFeed(OBJECTPTR Object, OBJECTPTR Sender, DATA Datatype, const void *Buffer, LONG Size) { +inline ERR acDataFeed(OBJECTPTR Object, OBJECTPTR Sender, DATA Datatype, const void *Buffer, LONG Size) { struct acDataFeed args = { Sender, Datatype, Buffer, Size }; return Action(AC_DataFeed, Object, &args); } -inline ERROR acGetVar(OBJECTPTR Object, CSTRING FieldName, STRING Buffer, LONG Size) { +inline ERR acGetVar(OBJECTPTR Object, CSTRING FieldName, STRING Buffer, LONG Size) { struct acGetVar args = { FieldName, Buffer, Size }; - ERROR error = Action(AC_GetVar, Object, &args); - if ((error) and (Buffer)) Buffer[0] = 0; + ERR error = Action(AC_GetVar, Object, &args); + if ((error != ERR::Okay) and (Buffer)) Buffer[0] = 0; return error; } -inline ERROR acMove(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z) { +inline ERR acMove(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z) { struct acMove args = { X, Y, Z }; return Action(AC_Move, Object, &args); } -inline ERROR acRead(OBJECTPTR Object, APTR Buffer, LONG Bytes, LONG *Read) { - ERROR error; +inline ERR acRead(OBJECTPTR Object, APTR Buffer, LONG Bytes, LONG *Read) { struct acRead read = { (BYTE *)Buffer, Bytes }; - if (!(error = Action(AC_Read, Object, &read))) { + if (auto error = Action(AC_Read, Object, &read); error IS ERR::Okay) { if (Read) *Read = read.Result; - return ERR_Okay; + return ERR::Okay; } else { if (Read) *Read = 0; @@ -3042,90 +3123,92 @@ inline ERROR acRead(OBJECTPTR Object, APTR Buffer, LONG Bytes, LONG *Read) { } } -inline ERROR acRedo(OBJECTPTR Object, LONG Steps = 1) { +inline ERR acRedo(OBJECTPTR Object, LONG Steps = 1) { struct acRedo args = { Steps }; return Action(AC_Redo, Object, &args); } -inline ERROR acRedimension(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE Width, DOUBLE Height, DOUBLE Depth) { +inline ERR acRedimension(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE Width, DOUBLE Height, DOUBLE Depth) { struct acRedimension args = { X, Y, Z, Width, Height, Depth }; return Action(AC_Redimension, Object, &args); } -inline ERROR acRename(OBJECTPTR Object, CSTRING Name) { +inline ERR acRename(OBJECTPTR Object, CSTRING Name) { struct acRename args = { Name }; return Action(AC_Rename, Object, &args); } -inline ERROR acResize(OBJECTPTR Object, DOUBLE Width, DOUBLE Height, DOUBLE Depth) { +inline ERR acResize(OBJECTPTR Object, DOUBLE Width, DOUBLE Height, DOUBLE Depth) { struct acResize args = { Width, Height, Depth }; return Action(AC_Resize, Object, &args); } -inline ERROR acScroll(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z) { +inline ERR acScroll(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z) { struct acScroll args = { X, Y, Z }; return Action(AC_Scroll, Object, &args); } -inline ERROR acScrollToPoint(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z, STP Flags) { +inline ERR acScrollToPoint(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z, STP Flags) { struct acScrollToPoint args = { X, Y, Z, Flags }; return Action(AC_ScrollToPoint, Object, &args); } -inline ERROR acMoveToPoint(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z, MTF Flags) { +inline ERR acMoveToPoint(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z, MTF Flags) { struct acMoveToPoint moveto = { X, Y, Z, Flags }; return Action(AC_MoveToPoint, Object, &moveto); } -inline ERROR acSaveImage(OBJECTPTR Object, OBJECTPTR Dest, CLASSID ClassID = 0) { +inline ERR acSaveImage(OBJECTPTR Object, OBJECTPTR Dest, CLASSID ClassID = 0) { struct acSaveImage args = { Dest, { ClassID } }; return Action(AC_SaveImage, Object, &args); } -inline ERROR acSaveToObject(OBJECTPTR Object, OBJECTPTR Dest, CLASSID ClassID = 0) { +inline ERR acSaveToObject(OBJECTPTR Object, OBJECTPTR Dest, CLASSID ClassID = 0) { struct acSaveToObject args = { Dest, { ClassID } }; return Action(AC_SaveToObject, Object, &args); } -inline ERROR acSeek(OBJECTPTR Object, DOUBLE Offset, SEEK Position) { +inline ERR acSeek(OBJECTPTR Object, DOUBLE Offset, SEEK Position) { struct acSeek args = { Offset, Position }; return Action(AC_Seek, Object, &args); } -inline ERROR acSetVars(OBJECTPTR Object, CSTRING tags, ...) { +inline ERR acSetVars(OBJECTPTR Object, CSTRING tags, ...) { struct acSetVar args; va_list list; va_start(list, tags); while ((args.Field = va_arg(list, STRING)) != TAGEND) { args.Value = va_arg(list, STRING); - if (Action(AC_SetVar, Object, &args) != ERR_Okay) { + if (Action(AC_SetVar, Object, &args) != ERR::Okay) { va_end(list); - return ERR_Failed; + return ERR::Failed; } } va_end(list); - return ERR_Okay; + return ERR::Okay; } -inline ERROR acUndo(OBJECTPTR Object, LONG Steps) { +inline ERR acUndo(OBJECTPTR Object, LONG Steps) { struct acUndo args = { Steps }; return Action(AC_Undo, Object, &args); } -inline ERROR acWrite(OBJECTPTR Object, CPTR Buffer, LONG Bytes, LONG *Result) { - ERROR error; +inline ERR acWrite(OBJECTPTR Object, CPTR Buffer, LONG Bytes, LONG *Result) { struct acWrite write = { (BYTE *)Buffer, Bytes }; - if (!(error = Action(AC_Write, Object, &write))) { + if (auto error = Action(AC_Write, Object, &write); error IS ERR::Okay) { if (Result) *Result = write.Result; + return error; + } + else { + if (Result) *Result = 0; + return error; } - else if (Result) *Result = 0; - return error; } inline LONG acWriteResult(OBJECTPTR Object, CPTR Buffer, LONG Bytes) { struct acWrite write = { (BYTE *)Buffer, Bytes }; - if (!Action(AC_Write, Object, &write)) return write.Result; + if (Action(AC_Write, Object, &write) IS ERR::Okay) return write.Result; else return 0; } @@ -3133,12 +3216,12 @@ inline LONG acWriteResult(OBJECTPTR Object, CPTR Buffer, LONG Bytes) { #define acSeekEnd(a,b) acSeek((a),(b),SEEK::END) #define acSeekCurrent(a,b) acSeek((a),(b),SEEK::CURRENT) -inline ERROR acSelectArea(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) { +inline ERR acSelectArea(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) { struct acSelectArea area = { X, Y, Width, Height }; return Action(AC_SelectArea, Object, &area); } -inline ERROR acSetVar(OBJECTPTR Object, CSTRING FieldName, CSTRING Value) { +inline ERR acSetVar(OBJECTPTR Object, CSTRING FieldName, CSTRING Value) { struct acSetVar args = { FieldName, Value }; return Action(AC_SetVar, Object, &args); } @@ -3156,9 +3239,9 @@ inline ERROR acSetVar(OBJECTPTR Object, CSTRING FieldName, CSTRING Value) { struct mcFindField { LONG ID; struct Field * Field; objMetaClass * Source; }; -INLINE ERROR mcFindField(APTR Ob, LONG ID, struct Field ** Field, objMetaClass ** Source) { +INLINE ERR mcFindField(APTR Ob, LONG ID, struct Field ** Field, objMetaClass ** Source) noexcept { struct mcFindField args = { ID, (struct Field *)0, (objMetaClass *)0 }; - ERROR error = Action(MT_mcFindField, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_mcFindField, (OBJECTPTR)Ob, &args); if (Field) *Field = args.Field; if (Source) *Source = args.Source; return(error); @@ -3189,92 +3272,92 @@ class objMetaClass : public BaseClass { // Customised field setting - inline ERROR setClassVersion(const DOUBLE Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setClassVersion(const DOUBLE Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->ClassVersion = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFields(const struct FieldArray * Value, LONG Elements) { + inline ERR setFields(const struct FieldArray * Value, LONG Elements) noexcept { auto target = this; auto field = &this->Class->Dictionary[23]; return field->WriteValue(target, field, 0x00001510, Value, Elements); } - template inline ERROR setClassName(T && Value) { - if (this->initialised()) return ERR_NoFieldAccess; + template inline ERR setClassName(T && Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->ClassName = Value; - return ERR_Okay; + return ERR::Okay; } - template inline ERROR setFileExtension(T && Value) { - if (this->initialised()) return ERR_NoFieldAccess; + template inline ERR setFileExtension(T && Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->FileExtension = Value; - return ERR_Okay; + return ERR::Okay; } - template inline ERROR setFileDescription(T && Value) { - if (this->initialised()) return ERR_NoFieldAccess; + template inline ERR setFileDescription(T && Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->FileDescription = Value; - return ERR_Okay; + return ERR::Okay; } - template inline ERROR setFileHeader(T && Value) { - if (this->initialised()) return ERR_NoFieldAccess; + template inline ERR setFileHeader(T && Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->FileHeader = Value; - return ERR_Okay; + return ERR::Okay; } - template inline ERROR setPath(T && Value) { - if (this->initialised()) return ERR_NoFieldAccess; + template inline ERR setPath(T && Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Path = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setSize(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setSize(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Size = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFlags(const CLF Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setFlags(const CLF Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setClass(const CLASSID Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setClass(const CLASSID Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->ClassID = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setBaseClass(const CLASSID Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setBaseClass(const CLASSID Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->BaseClassID = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setCategory(const CCF Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setCategory(const CCF Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Category = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setMethods(const APTR Value, LONG Elements) { + inline ERR setMethods(const APTR Value, LONG Elements) noexcept { auto target = this; auto field = &this->Class->Dictionary[16]; return field->WriteValue(target, field, 0x00001510, Value, Elements); } - inline ERROR setActions(APTR Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setActions(APTR Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; auto target = this; auto field = &this->Class->Dictionary[5]; return field->WriteValue(target, field, 0x08000400, Value, 1); } - template inline ERROR setName(T && Value) { + template inline ERR setName(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[9]; return field->WriteValue(target, field, 0x08810500, to_cstring(Value), 1); @@ -3302,7 +3385,7 @@ class objStorageDevice : public BaseClass { // Customised field setting - template inline ERROR setVolume(T && Value) { + template inline ERR setVolume(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[4]; return field->WriteValue(target, field, 0x08800504, to_cstring(Value), 1); @@ -3336,43 +3419,43 @@ struct flReadLine { STRING Result; }; struct flNext { objFile * File; }; struct flWatch { FUNCTION * Callback; LARGE Custom; MFF Flags; }; -INLINE ERROR flStartStream(APTR Ob, OBJECTID SubscriberID, FL Flags, LONG Length) { +INLINE ERR flStartStream(APTR Ob, OBJECTID SubscriberID, FL Flags, LONG Length) noexcept { struct flStartStream args = { SubscriberID, Flags, Length }; return(Action(MT_FlStartStream, (OBJECTPTR)Ob, &args)); } #define flStopStream(obj) Action(MT_FlStopStream,(obj),0) -INLINE ERROR flDelete(APTR Ob, FUNCTION * Callback) { +INLINE ERR flDelete(APTR Ob, FUNCTION * Callback) noexcept { struct flDelete args = { Callback }; return(Action(MT_FlDelete, (OBJECTPTR)Ob, &args)); } -INLINE ERROR flMove(APTR Ob, CSTRING Dest, FUNCTION * Callback) { +INLINE ERR flMove(APTR Ob, CSTRING Dest, FUNCTION * Callback) noexcept { struct flMove args = { Dest, Callback }; return(Action(MT_FlMove, (OBJECTPTR)Ob, &args)); } -INLINE ERROR flCopy(APTR Ob, CSTRING Dest, FUNCTION * Callback) { +INLINE ERR flCopy(APTR Ob, CSTRING Dest, FUNCTION * Callback) noexcept { struct flCopy args = { Dest, Callback }; return(Action(MT_FlCopy, (OBJECTPTR)Ob, &args)); } -INLINE ERROR flSetDate(APTR Ob, LONG Year, LONG Month, LONG Day, LONG Hour, LONG Minute, LONG Second, FDT Type) { +INLINE ERR flSetDate(APTR Ob, LONG Year, LONG Month, LONG Day, LONG Hour, LONG Minute, LONG Second, FDT Type) noexcept { struct flSetDate args = { Year, Month, Day, Hour, Minute, Second, Type }; return(Action(MT_FlSetDate, (OBJECTPTR)Ob, &args)); } #define flBufferContent(obj) Action(MT_FlBufferContent,(obj),0) -INLINE ERROR flNext(APTR Ob, objFile ** File) { +INLINE ERR flNext(APTR Ob, objFile ** File) noexcept { struct flNext args = { (objFile *)0 }; - ERROR error = Action(MT_FlNext, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_FlNext, (OBJECTPTR)Ob, &args); if (File) *File = args.File; return(error); } -INLINE ERROR flWatch(APTR Ob, FUNCTION * Callback, LARGE Custom, MFF Flags) { +INLINE ERR flWatch(APTR Ob, FUNCTION * Callback, LARGE Custom, MFF Flags) noexcept { struct flWatch args = { Callback, Custom, Flags }; return(Action(MT_FlWatch, (OBJECTPTR)Ob, &args)); } @@ -3393,133 +3476,138 @@ class objFile : public BaseClass { // Action stubs - inline ERROR activate() { return Action(AC_Activate, this, NULL); } - inline ERROR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) { + inline ERR activate() noexcept { return Action(AC_Activate, this, NULL); } + inline ERR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) noexcept { struct acDataFeed args = { Object, Datatype, Buffer, Size }; return Action(AC_DataFeed, this, &args); } - inline ERROR init() { return InitObject(this); } - inline ERROR query() { return Action(AC_Query, this, NULL); } - template ERROR read(APTR Buffer, T Size, U *Result) { + inline ERR init() noexcept { return InitObject(this); } + inline ERR query() noexcept { return Action(AC_Query, this, NULL); } + template ERR read(APTR Buffer, T Size, U *Result) noexcept { static_assert(std::is_integral::value, "Result value must be an integer type"); static_assert(std::is_integral::value, "Size value must be an integer type"); - ERROR error; const LONG bytes = (Size > 0x7fffffff) ? 0x7fffffff : Size; struct acRead read = { (BYTE *)Buffer, bytes }; - if (!(error = Action(AC_Read, this, &read))) *Result = static_cast(read.Result); - else *Result = 0; - return error; + if (auto error = Action(AC_Read, this, &read); error IS ERR::Okay) { + *Result = static_cast(read.Result); + return ERR::Okay; + } + else { *Result = 0; return error; } } - template ERROR read(APTR Buffer, T Size) { + template ERR read(APTR Buffer, T Size) noexcept { static_assert(std::is_integral::value, "Size value must be an integer type"); const LONG bytes = (Size > 0x7fffffff) ? 0x7fffffff : Size; struct acRead read = { (BYTE *)Buffer, bytes }; return Action(AC_Read, this, &read); } - inline ERROR rename(CSTRING Name) { + inline ERR rename(CSTRING Name) noexcept { struct acRename args = { Name }; return Action(AC_Rename, this, &args); } - inline ERROR reset() { return Action(AC_Reset, this, NULL); } - inline ERROR seek(DOUBLE Offset, SEEK Position = SEEK::CURRENT) { + inline ERR reset() noexcept { return Action(AC_Reset, this, NULL); } + inline ERR seek(DOUBLE Offset, SEEK Position = SEEK::CURRENT) noexcept { struct acSeek args = { Offset, Position }; return Action(AC_Seek, this, &args); } - inline ERROR seekStart(DOUBLE Offset) { return seek(Offset, SEEK::START); } - inline ERROR seekEnd(DOUBLE Offset) { return seek(Offset, SEEK::END); } - inline ERROR seekCurrent(DOUBLE Offset) { return seek(Offset, SEEK::CURRENT); } - inline ERROR write(CPTR Buffer, LONG Size, LONG *Result = NULL) { - ERROR error; + inline ERR seekStart(DOUBLE Offset) noexcept { return seek(Offset, SEEK::START); } + inline ERR seekEnd(DOUBLE Offset) noexcept { return seek(Offset, SEEK::END); } + inline ERR seekCurrent(DOUBLE Offset) noexcept { return seek(Offset, SEEK::CURRENT); } + inline ERR write(CPTR Buffer, LONG Size, LONG *Result = NULL) noexcept { struct acWrite write = { (BYTE *)Buffer, Size }; - if (!(error = Action(AC_Write, this, &write))) { + if (auto error = Action(AC_Write, this, &write); error IS ERR::Okay) { if (Result) *Result = write.Result; + return ERR::Okay; + } + else { + if (Result) *Result = 0; + return error; } - else if (Result) *Result = 0; - return error; } - inline ERROR write(std::string Buffer, LONG *Result = NULL) { - ERROR error; + inline ERR write(std::string Buffer, LONG *Result = NULL) noexcept { struct acWrite write = { (BYTE *)Buffer.c_str(), LONG(Buffer.size()) }; - if (!(error = Action(AC_Write, this, &write))) { + if (auto error = Action(AC_Write, this, &write); error IS ERR::Okay) { if (Result) *Result = write.Result; + return ERR::Okay; + } + else { + if (Result) *Result = 0; + return error; } - else if (Result) *Result = 0; - return error; } - inline LONG writeResult(CPTR Buffer, LONG Size) { + inline LONG writeResult(CPTR Buffer, LONG Size) noexcept { struct acWrite write = { (BYTE *)Buffer, Size }; - if (!Action(AC_Write, this, &write)) return write.Result; + if (Action(AC_Write, this, &write) IS ERR::Okay) return write.Result; else return 0; } // Customised field setting - inline ERROR setPosition(const LARGE Value) { + inline ERR setPosition(const LARGE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[9]; return field->WriteValue(target, field, FD_LARGE, &Value, 1); } - inline ERROR setFlags(const FL Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setFlags(const FL Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setStatic(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setStatic(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Static = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setTarget(const OBJECTID Value) { + inline ERR setTarget(OBJECTID Value) noexcept { this->TargetID = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setDate(APTR Value) { + inline ERR setDate(APTR Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[12]; return field->WriteValue(target, field, 0x08000310, Value, 1); } - inline ERROR setCreated(APTR Value) { + inline ERR setCreated(APTR Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[20]; return field->WriteValue(target, field, 0x08000310, Value, 1); } - template inline ERROR setPath(T && Value) { + template inline ERR setPath(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[16]; return field->WriteValue(target, field, 0x08800500, to_cstring(Value), 1); } - inline ERROR setPermissions(const LONG Value) { + inline ERR setPermissions(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[22]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setSize(const LARGE Value) { + inline ERR setSize(const LARGE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[17]; return field->WriteValue(target, field, FD_LARGE, &Value, 1); } - template inline ERROR setLink(T && Value) { + template inline ERR setLink(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[14]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setUser(const LONG Value) { + inline ERR setUser(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[18]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setGroup(const LONG Value) { + inline ERR setGroup(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[4]; return field->WriteValue(target, field, FD_LONG, &Value, 1); @@ -3553,51 +3641,51 @@ struct cfgSortByKey { CSTRING Key; LONG Descending; }; struct cfgMergeFile { CSTRING Path; }; struct cfgMerge { OBJECTPTR Source; }; -INLINE ERROR cfgReadValue(APTR Ob, CSTRING Group, CSTRING Key, CSTRING * Data) { +INLINE ERR cfgReadValue(APTR Ob, CSTRING Group, CSTRING Key, CSTRING * Data) noexcept { struct cfgReadValue args = { Group, Key, (CSTRING)0 }; - ERROR error = Action(MT_CfgReadValue, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_CfgReadValue, (OBJECTPTR)Ob, &args); if (Data) *Data = args.Data; return(error); } -INLINE ERROR cfgSet(APTR Ob, CSTRING Group, CSTRING Key, CSTRING Data) { +INLINE ERR cfgSet(APTR Ob, CSTRING Group, CSTRING Key, CSTRING Data) noexcept { struct cfgSet args = { Group, Key, Data }; return(Action(MT_CfgSet, (OBJECTPTR)Ob, &args)); } -INLINE ERROR cfgWriteValue(APTR Ob, CSTRING Group, CSTRING Key, CSTRING Data) { +INLINE ERR cfgWriteValue(APTR Ob, CSTRING Group, CSTRING Key, CSTRING Data) noexcept { struct cfgWriteValue args = { Group, Key, Data }; return(Action(MT_CfgWriteValue, (OBJECTPTR)Ob, &args)); } -INLINE ERROR cfgDeleteKey(APTR Ob, CSTRING Group, CSTRING Key) { +INLINE ERR cfgDeleteKey(APTR Ob, CSTRING Group, CSTRING Key) noexcept { struct cfgDeleteKey args = { Group, Key }; return(Action(MT_CfgDeleteKey, (OBJECTPTR)Ob, &args)); } -INLINE ERROR cfgDeleteGroup(APTR Ob, CSTRING Group) { +INLINE ERR cfgDeleteGroup(APTR Ob, CSTRING Group) noexcept { struct cfgDeleteGroup args = { Group }; return(Action(MT_CfgDeleteGroup, (OBJECTPTR)Ob, &args)); } -INLINE ERROR cfgGetGroupFromIndex(APTR Ob, LONG Index, CSTRING * Group) { +INLINE ERR cfgGetGroupFromIndex(APTR Ob, LONG Index, CSTRING * Group) noexcept { struct cfgGetGroupFromIndex args = { Index, (CSTRING)0 }; - ERROR error = Action(MT_CfgGetGroupFromIndex, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_CfgGetGroupFromIndex, (OBJECTPTR)Ob, &args); if (Group) *Group = args.Group; return(error); } -INLINE ERROR cfgSortByKey(APTR Ob, CSTRING Key, LONG Descending) { +INLINE ERR cfgSortByKey(APTR Ob, CSTRING Key, LONG Descending) noexcept { struct cfgSortByKey args = { Key, Descending }; return(Action(MT_CfgSortByKey, (OBJECTPTR)Ob, &args)); } -INLINE ERROR cfgMergeFile(APTR Ob, CSTRING Path) { +INLINE ERR cfgMergeFile(APTR Ob, CSTRING Path) noexcept { struct cfgMergeFile args = { Path }; return(Action(MT_CfgMergeFile, (OBJECTPTR)Ob, &args)); } -INLINE ERROR cfgMerge(APTR Ob, OBJECTPTR Source) { +INLINE ERR cfgMerge(APTR Ob, OBJECTPTR Source) noexcept { struct cfgMerge args = { Source }; return(Action(MT_CfgMerge, (OBJECTPTR)Ob, &args)); } @@ -3619,64 +3707,64 @@ class objConfig : public BaseClass { // For C++ only, these read variants avoid method calls for speed, but apply identical logic. - inline ERROR read(CSTRING pGroup, CSTRING pKey, DOUBLE *pValue) { + inline ERR read(CSTRING pGroup, CSTRING pKey, DOUBLE *pValue) { for (auto& [group, keys] : Groups[0]) { if ((pGroup) and (group.compare(pGroup))) continue; if (!pKey) { *pValue = strtod(keys.cbegin()->second.c_str(), NULL); - return ERR_Okay; + return ERR::Okay; } else if (keys.contains(pKey)) { *pValue = strtod(keys[pKey].c_str(), NULL); - return ERR_Okay; + return ERR::Okay; } } - return ERR_Search; + return ERR::Search; } - inline ERROR read(CSTRING pGroup, CSTRING pKey, LONG *pValue) { + inline ERR read(CSTRING pGroup, CSTRING pKey, LONG *pValue) { for (auto& [group, keys] : Groups[0]) { if ((pGroup) and (group.compare(pGroup))) continue; if (!pKey) { *pValue = strtol(keys.cbegin()->second.c_str(), NULL, 0); - return ERR_Okay; + return ERR::Okay; } else if (keys.contains(pKey)) { *pValue = strtol(keys[pKey].c_str(), NULL, 0); - return ERR_Okay; + return ERR::Okay; } } - return ERR_Search; + return ERR::Search; } - inline ERROR read(CSTRING pGroup, CSTRING pKey, std::string &pValue) { + inline ERR read(CSTRING pGroup, CSTRING pKey, std::string &pValue) { for (auto& [group, keys] : Groups[0]) { if ((pGroup) and (group.compare(pGroup))) continue; if (!pKey) { pValue = keys.cbegin()->second; - return ERR_Okay; + return ERR::Okay; } else if (keys.contains(pKey)) { pValue = keys[pKey]; - return ERR_Okay; + return ERR::Okay; } } - return ERR_Search; + return ERR::Search; } - inline ERROR write(CSTRING Group, CSTRING Key, CSTRING Value) { + inline ERR write(CSTRING Group, CSTRING Key, CSTRING Value) { struct cfgWriteValue write = { Group, Key, Value }; return Action(MT_CfgWriteValue, this, &write); } - inline ERROR write(CSTRING Group, CSTRING Key, STRING Value) { + inline ERR write(CSTRING Group, CSTRING Key, STRING Value) { struct cfgWriteValue write = { Group, Key, Value }; return Action(MT_CfgWriteValue, this, &write); } - inline ERROR write(CSTRING Group, CSTRING Key, std::string Value) { + inline ERR write(CSTRING Group, CSTRING Key, std::string Value) { struct cfgWriteValue write = { Group, Key, Value.c_str() }; return Action(MT_CfgWriteValue, this, &write); } - template inline ERROR write(CSTRING Group, CSTRING Key, T Value) { + template inline ERR write(CSTRING Group, CSTRING Key, T Value) { auto str = std::to_string(Value); struct cfgWriteValue write = { Group, Key, str.c_str() }; return Action(MT_CfgWriteValue, this, &write); @@ -3684,65 +3772,63 @@ class objConfig : public BaseClass { // Action stubs - inline ERROR clear() { return Action(AC_Clear, this, NULL); } - inline ERROR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) { + inline ERR clear() noexcept { return Action(AC_Clear, this, NULL); } + inline ERR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) noexcept { struct acDataFeed args = { Object, Datatype, Buffer, Size }; return Action(AC_DataFeed, this, &args); } - inline ERROR flush() { return Action(AC_Flush, this, NULL); } - inline ERROR init() { return InitObject(this); } - inline ERROR saveSettings() { return Action(AC_SaveSettings, this, NULL); } - inline ERROR saveToObject(OBJECTPTR Dest, CLASSID ClassID = 0) { + inline ERR flush() noexcept { return Action(AC_Flush, this, NULL); } + inline ERR init() noexcept { return InitObject(this); } + inline ERR saveSettings() noexcept { return Action(AC_SaveSettings, this, NULL); } + inline ERR saveToObject(OBJECTPTR Dest, CLASSID ClassID = 0) noexcept { struct acSaveToObject args = { Dest, { ClassID } }; return Action(AC_SaveToObject, this, &args); } - inline ERROR sort() { return Action(AC_Sort, this, NULL); } + inline ERR sort() noexcept { return Action(AC_Sort, this, NULL); } // Customised field setting - template inline ERROR setPath(T && Value) { + template inline ERR setPath(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[6]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setKeyFilter(T && Value) { + template inline ERR setKeyFilter(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[3]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setGroupFilter(T && Value) { + template inline ERR setGroupFilter(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[7]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setFlags(const CNF Value) { + inline ERR setFlags(const CNF Value) noexcept { this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } }; -inline ERROR cfgRead(OBJECTPTR Self, CSTRING Group, CSTRING Key, DOUBLE *Value) +inline ERR cfgRead(OBJECTPTR Self, CSTRING Group, CSTRING Key, DOUBLE *Value) { - ERROR error; struct cfgReadValue read = { .Group = Group, .Key = Key }; - if (!(error = Action(MT_CfgReadValue, Self, &read))) { + if (auto error = Action(MT_CfgReadValue, Self, &read); error IS ERR::Okay) { *Value = strtod(read.Data, NULL); - return ERR_Okay; + return ERR::Okay; } else { *Value = 0; return error; } } -inline ERROR cfgRead(OBJECTPTR Self, CSTRING Group, CSTRING Key, LONG *Value) +inline ERR cfgRead(OBJECTPTR Self, CSTRING Group, CSTRING Key, LONG *Value) { - ERROR error; struct cfgReadValue read = { .Group = Group, .Key = Key }; - if (!(error = Action(MT_CfgReadValue, Self, &read))) { + if (auto error = Action(MT_CfgReadValue, Self, &read); error IS ERR::Okay) { *Value = strtol(read.Data, NULL, 0); - return ERR_Okay; + return ERR::Okay; } else { *Value = 0; return error; } } @@ -3759,29 +3845,29 @@ inline ERROR cfgRead(OBJECTPTR Self, CSTRING Group, CSTRING Key, LONG *Value) struct scExec { CSTRING Procedure; const struct ScriptArg * Args; LONG TotalArgs; }; struct scDerefProcedure { FUNCTION * Procedure; }; -struct scCallback { LARGE ProcedureID; const struct ScriptArg * Args; LONG TotalArgs; LONG Error; }; +struct scCallback { LARGE ProcedureID; const struct ScriptArg * Args; LONG TotalArgs; ERR Error; }; struct scGetProcedureID { CSTRING Procedure; LARGE ProcedureID; }; -INLINE ERROR scExec(APTR Ob, CSTRING Procedure, const struct ScriptArg * Args, LONG TotalArgs) { +INLINE ERR scExec(APTR Ob, CSTRING Procedure, const struct ScriptArg * Args, LONG TotalArgs) noexcept { struct scExec args = { Procedure, Args, TotalArgs }; return(Action(MT_ScExec, (OBJECTPTR)Ob, &args)); } -INLINE ERROR scDerefProcedure(APTR Ob, FUNCTION * Procedure) { +INLINE ERR scDerefProcedure(APTR Ob, FUNCTION * Procedure) noexcept { struct scDerefProcedure args = { Procedure }; return(Action(MT_ScDerefProcedure, (OBJECTPTR)Ob, &args)); } -INLINE ERROR scCallback(APTR Ob, LARGE ProcedureID, const struct ScriptArg * Args, LONG TotalArgs, LONG * Error) { - struct scCallback args = { ProcedureID, Args, TotalArgs, (LONG)0 }; - ERROR error = Action(MT_ScCallback, (OBJECTPTR)Ob, &args); +INLINE ERR scCallback(APTR Ob, LARGE ProcedureID, const struct ScriptArg * Args, LONG TotalArgs, ERR * Error) noexcept { + struct scCallback args = { ProcedureID, Args, TotalArgs, (ERR)0 }; + ERR error = Action(MT_ScCallback, (OBJECTPTR)Ob, &args); if (Error) *Error = args.Error; return(error); } -INLINE ERROR scGetProcedureID(APTR Ob, CSTRING Procedure, LARGE * ProcedureID) { +INLINE ERR scGetProcedureID(APTR Ob, CSTRING Procedure, LARGE * ProcedureID) noexcept { struct scGetProcedureID args = { Procedure, (LARGE)0 }; - ERROR error = Action(MT_ScGetProcedureID, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_ScGetProcedureID, (OBJECTPTR)Ob, &args); if (ProcedureID) *ProcedureID = args.ProcedureID; return(error); } @@ -3796,13 +3882,13 @@ class objScript : public BaseClass { OBJECTID TargetID; // Reference to the default container that new script objects will be initialised to. SCF Flags; // Optional flags. - ERROR Error; // If a script fails during execution, an error code may be readable here. + ERR Error; // If a script fails during execution, an error code may be readable here. LONG CurrentLine; // Indicates the current line being executed when in debug mode. LONG LineOffset; // For debugging purposes, this value is added to any message referencing a line number. #ifdef PRV_SCRIPT LARGE ProcedureID; // For callbacks - std::map Vars; // Global parameters + KEYVALUE Vars; // Global parameters STRING *Results; char Language[4]; // 3-character language code, null-terminated const ScriptArg *ProcArgs; // Procedure args - applies during Exec @@ -3821,91 +3907,91 @@ class objScript : public BaseClass { // Action stubs - inline ERROR activate() { return Action(AC_Activate, this, NULL); } - inline ERROR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) { + inline ERR activate() noexcept { return Action(AC_Activate, this, NULL); } + inline ERR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) noexcept { struct acDataFeed args = { Object, Datatype, Buffer, Size }; return Action(AC_DataFeed, this, &args); } - inline ERROR getVar(CSTRING FieldName, STRING Buffer, LONG Size) { + inline ERR getVar(CSTRING FieldName, STRING Buffer, LONG Size) noexcept { struct acGetVar args = { FieldName, Buffer, Size }; - ERROR error = Action(AC_GetVar, this, &args); - if ((error) and (Buffer)) Buffer[0] = 0; + auto error = Action(AC_GetVar, this, &args); + if ((error != ERR::Okay) and (Buffer)) Buffer[0] = 0; return error; } - inline ERROR init() { return InitObject(this); } - inline ERROR reset() { return Action(AC_Reset, this, NULL); } - inline ERROR acSetVar(CSTRING FieldName, CSTRING Value) { + inline ERR init() noexcept { return InitObject(this); } + inline ERR reset() noexcept { return Action(AC_Reset, this, NULL); } + inline ERR acSetVar(CSTRING FieldName, CSTRING Value) noexcept { struct acSetVar args = { FieldName, Value }; return Action(AC_SetVar, this, &args); } // Customised field setting - inline ERROR setTarget(const OBJECTID Value) { + inline ERR setTarget(OBJECTID Value) noexcept { this->TargetID = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFlags(const SCF Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setFlags(const SCF Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setLineOffset(const LONG Value) { + inline ERR setLineOffset(const LONG Value) noexcept { this->LineOffset = Value; - return ERR_Okay; + return ERR::Okay; } - template inline ERROR setCacheFile(T && Value) { + template inline ERR setCacheFile(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[9]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setErrorString(T && Value) { + template inline ERR setErrorString(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[0]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setWorkingPath(T && Value) { + template inline ERR setWorkingPath(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[20]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setProcedure(T && Value) { + template inline ERR setProcedure(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[12]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setName(T && Value) { + template inline ERR setName(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[14]; return field->WriteValue(target, field, 0x08810300, to_cstring(Value), 1); } - inline ERROR setOwner(const OBJECTID Value) { + inline ERR setOwner(OBJECTID Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[5]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - template inline ERROR setPath(T && Value) { + template inline ERR setPath(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[15]; return field->WriteValue(target, field, 0x08800500, to_cstring(Value), 1); } - inline ERROR setResults(STRING * Value, LONG Elements) { + inline ERR setResults(STRING * Value, LONG Elements) noexcept { auto target = this; auto field = &this->Class->Dictionary[8]; return field->WriteValue(target, field, 0x08801300, Value, Elements); } - template inline ERROR setStatement(T && Value) { + template inline ERR setStatement(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[16]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); @@ -3931,21 +4017,21 @@ struct taskSetEnv { CSTRING Name; CSTRING Value; }; #define taskExpunge(obj) Action(MT_TaskExpunge,(obj),0) -INLINE ERROR taskAddArgument(APTR Ob, CSTRING Argument) { +INLINE ERR taskAddArgument(APTR Ob, CSTRING Argument) noexcept { struct taskAddArgument args = { Argument }; return(Action(MT_TaskAddArgument, (OBJECTPTR)Ob, &args)); } #define taskQuit(obj) Action(MT_TaskQuit,(obj),0) -INLINE ERROR taskGetEnv(APTR Ob, CSTRING Name, CSTRING * Value) { +INLINE ERR taskGetEnv(APTR Ob, CSTRING Name, CSTRING * Value) noexcept { struct taskGetEnv args = { Name, (CSTRING)0 }; - ERROR error = Action(MT_TaskGetEnv, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_TaskGetEnv, (OBJECTPTR)Ob, &args); if (Value) *Value = args.Value; return(error); } -INLINE ERROR taskSetEnv(APTR Ob, CSTRING Name, CSTRING Value) { +INLINE ERR taskSetEnv(APTR Ob, CSTRING Name, CSTRING Value) noexcept { struct taskSetEnv args = { Name, Value }; return(Action(MT_TaskSetEnv, (OBJECTPTR)Ob, &args)); } @@ -3965,128 +4051,132 @@ class objTask : public BaseClass { // Action stubs - inline ERROR activate() { return Action(AC_Activate, this, NULL); } - inline ERROR getVar(CSTRING FieldName, STRING Buffer, LONG Size) { + inline ERR activate() noexcept { return Action(AC_Activate, this, NULL); } + inline ERR getVar(CSTRING FieldName, STRING Buffer, LONG Size) noexcept { struct acGetVar args = { FieldName, Buffer, Size }; - ERROR error = Action(AC_GetVar, this, &args); - if ((error) and (Buffer)) Buffer[0] = 0; + auto error = Action(AC_GetVar, this, &args); + if ((error != ERR::Okay) and (Buffer)) Buffer[0] = 0; return error; } - inline ERROR init() { return InitObject(this); } - inline ERROR acSetVar(CSTRING FieldName, CSTRING Value) { + inline ERR init() noexcept { return InitObject(this); } + inline ERR acSetVar(CSTRING FieldName, CSTRING Value) noexcept { struct acSetVar args = { FieldName, Value }; return Action(AC_SetVar, this, &args); } - inline ERROR write(CPTR Buffer, LONG Size, LONG *Result = NULL) { - ERROR error; + inline ERR write(CPTR Buffer, LONG Size, LONG *Result = NULL) noexcept { struct acWrite write = { (BYTE *)Buffer, Size }; - if (!(error = Action(AC_Write, this, &write))) { + if (auto error = Action(AC_Write, this, &write); error IS ERR::Okay) { if (Result) *Result = write.Result; + return ERR::Okay; + } + else { + if (Result) *Result = 0; + return error; } - else if (Result) *Result = 0; - return error; } - inline ERROR write(std::string Buffer, LONG *Result = NULL) { - ERROR error; + inline ERR write(std::string Buffer, LONG *Result = NULL) noexcept { struct acWrite write = { (BYTE *)Buffer.c_str(), LONG(Buffer.size()) }; - if (!(error = Action(AC_Write, this, &write))) { + if (auto error = Action(AC_Write, this, &write); error IS ERR::Okay) { if (Result) *Result = write.Result; + return ERR::Okay; + } + else { + if (Result) *Result = 0; + return error; } - else if (Result) *Result = 0; - return error; } - inline LONG writeResult(CPTR Buffer, LONG Size) { + inline LONG writeResult(CPTR Buffer, LONG Size) noexcept { struct acWrite write = { (BYTE *)Buffer, Size }; - if (!Action(AC_Write, this, &write)) return write.Result; + if (Action(AC_Write, this, &write) IS ERR::Okay) return write.Result; else return 0; } // Customised field setting - inline ERROR setTimeOut(const DOUBLE Value) { + inline ERR setTimeOut(const DOUBLE Value) noexcept { this->TimeOut = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFlags(const TSF Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setFlags(const TSF Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setReturnCode(const LONG Value) { + inline ERR setReturnCode(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[9]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setProcess(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setProcess(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->ProcessID = Value; - return ERR_Okay; + return ERR::Okay; } - template inline ERROR setArgs(T && Value) { + template inline ERR setArgs(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[13]; return field->WriteValue(target, field, 0x08800200, to_cstring(Value), 1); } - inline ERROR setParameters(pf::vector *Value) { + inline ERR setParameters(pf::vector *Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[16]; return field->WriteValue(target, field, 0x08805300, Value, LONG(Value->size())); } - inline ERROR setErrorCallback(FUNCTION Value) { + inline ERR setErrorCallback(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[5]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } - inline ERROR setExitCallback(FUNCTION Value) { + inline ERR setExitCallback(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[8]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } - inline ERROR setInputCallback(FUNCTION Value) { + inline ERR setInputCallback(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[17]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } - template inline ERROR setLaunchPath(T && Value) { + template inline ERR setLaunchPath(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[0]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setLocation(T && Value) { + template inline ERR setLocation(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[12]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setName(T && Value) { + template inline ERR setName(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[14]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setOutputCallback(FUNCTION Value) { + inline ERR setOutputCallback(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[18]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } - template inline ERROR setPath(T && Value) { + template inline ERR setPath(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[15]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setPriority(const LONG Value) { + inline ERR setPriority(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[6]; return field->WriteValue(target, field, FD_LONG, &Value, 1); @@ -4104,7 +4194,7 @@ class objTask : public BaseClass { struct thSetData { APTR Data; LONG Size; }; -INLINE ERROR thSetData(APTR Ob, APTR Data, LONG Size) { +INLINE ERR thSetData(APTR Ob, APTR Data, LONG Size) noexcept { struct thSetData args = { Data, Size }; return(Action(MT_ThSetData, (OBJECTPTR)Ob, &args)); } @@ -4117,38 +4207,38 @@ class objThread : public BaseClass { using create = pf::Create; - APTR Data; // Pointer to initialisation data for the thread. - LONG DataSize; // The size of the buffer referenced in the Data field. - LONG StackSize; // The stack size to allocate for the thread. - ERROR Error; // Reflects the error code returned by the thread routine. - THF Flags; // Optional flags can be defined here. + APTR Data; // Pointer to initialisation data for the thread. + LONG DataSize; // The size of the buffer referenced in the Data field. + LONG StackSize; // The stack size to allocate for the thread. + ERR Error; // Reflects the error code returned by the thread routine. + THF Flags; // Optional flags can be defined here. // Action stubs - inline ERROR activate() { return Action(AC_Activate, this, NULL); } - inline ERROR deactivate() { return Action(AC_Deactivate, this, NULL); } - inline ERROR init() { return InitObject(this); } + inline ERR activate() noexcept { return Action(AC_Activate, this, NULL); } + inline ERR deactivate() noexcept { return Action(AC_Deactivate, this, NULL); } + inline ERR init() noexcept { return InitObject(this); } // Customised field setting - inline ERROR setStackSize(const LONG Value) { + inline ERR setStackSize(const LONG Value) noexcept { this->StackSize = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFlags(const THF Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setFlags(const THF Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setCallback(FUNCTION Value) { + inline ERR setCallback(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[1]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } - inline ERROR setRoutine(FUNCTION Value) { + inline ERR setRoutine(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[6]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); @@ -4166,9 +4256,9 @@ class objThread : public BaseClass { struct modResolveSymbol { CSTRING Name; APTR Address; }; -INLINE ERROR modResolveSymbol(APTR Ob, CSTRING Name, APTR * Address) { +INLINE ERR modResolveSymbol(APTR Ob, CSTRING Name, APTR * Address) noexcept { struct modResolveSymbol args = { Name, (APTR)0 }; - ERROR error = Action(MT_ModResolveSymbol, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_ModResolveSymbol, (OBJECTPTR)Ob, &args); if (Address) *Address = args.Address; return(error); } @@ -4187,49 +4277,49 @@ class objModule : public BaseClass { struct ModHeader * Header; // For internal usage only. MOF Flags; // Optional flags. public: - static ERROR load(std::string Name, OBJECTPTR *Module = NULL, APTR Functions = NULL) { + static ERR load(std::string Name, OBJECTPTR *Module = NULL, APTR Functions = NULL) { if (auto module = objModule::create::global(pf::FieldValue(FID_Name, Name.c_str()))) { #ifdef PARASOL_STATIC if (Module) *Module = module; if (Functions) ((APTR *)Functions)[0] = NULL; - return ERR_Okay; + return ERR::Okay; #else APTR functionbase; - if (!module->getPtr(FID_ModBase, &functionbase)) { + if (module->getPtr(FID_ModBase, &functionbase) IS ERR::Okay) { if (Module) *Module = module; if (Functions) ((APTR *)Functions)[0] = functionbase; - return ERR_Okay; + return ERR::Okay; } - else return ERR_GetField; + else return ERR::GetField; #endif } - else return ERR_CreateObject; + else return ERR::CreateObject; } // Action stubs - inline ERROR init() { return InitObject(this); } + inline ERR init() noexcept { return InitObject(this); } // Customised field setting - inline ERROR setFunctionList(const struct Function * Value) { + inline ERR setFunctionList(const struct Function * Value) noexcept { this->FunctionList = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setHeader(struct ModHeader * Value) { + inline ERR setHeader(struct ModHeader * Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[0]; return field->WriteValue(target, field, 0x08000500, Value, 1); } - inline ERROR setFlags(const MOF Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setFlags(const MOF Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - template inline ERROR setName(T && Value) { + template inline ERR setName(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[5]; return field->WriteValue(target, field, 0x08800500, to_cstring(Value), 1); @@ -4264,69 +4354,69 @@ class objTime : public BaseClass { LONG Second; // Second (0 - 59) LONG TimeZone; // No information. LONG DayOfWeek; // Day of week (0 - 6) starting from Sunday. - LONG MilliSecond; // Millisecond (0 - 999) - LONG MicroSecond; // Microsecond (0 - 999999) + LONG MilliSecond; // A millisecond is one thousandth of a second (0 - 999) + LONG MicroSecond; // A microsecond is one millionth of a second (0 - 999999) // Action stubs - inline ERROR query() { return Action(AC_Query, this, NULL); } - inline ERROR init() { return InitObject(this); } + inline ERR query() noexcept { return Action(AC_Query, this, NULL); } + inline ERR init() noexcept { return InitObject(this); } // Customised field setting - inline ERROR setSystemTime(const LARGE Value) { + inline ERR setSystemTime(const LARGE Value) noexcept { this->SystemTime = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setYear(const LONG Value) { + inline ERR setYear(const LONG Value) noexcept { this->Year = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setMonth(const LONG Value) { + inline ERR setMonth(const LONG Value) noexcept { this->Month = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setDay(const LONG Value) { + inline ERR setDay(const LONG Value) noexcept { this->Day = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setHour(const LONG Value) { + inline ERR setHour(const LONG Value) noexcept { this->Hour = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setMinute(const LONG Value) { + inline ERR setMinute(const LONG Value) noexcept { this->Minute = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setSecond(const LONG Value) { + inline ERR setSecond(const LONG Value) noexcept { this->Second = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setTimeZone(const LONG Value) { + inline ERR setTimeZone(const LONG Value) noexcept { this->TimeZone = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setDayOfWeek(const LONG Value) { + inline ERR setDayOfWeek(const LONG Value) noexcept { this->DayOfWeek = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setMilliSecond(const LONG Value) { + inline ERR setMilliSecond(const LONG Value) noexcept { this->MilliSecond = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setMicroSecond(const LONG Value) { + inline ERR setMicroSecond(const LONG Value) noexcept { this->MicroSecond = Value; - return ERR_Okay; + return ERR::Okay; } }; @@ -4365,72 +4455,72 @@ struct cmpDecompressObject { CSTRING Path; OBJECTPTR Object; }; struct cmpScan { CSTRING Folder; CSTRING Filter; FUNCTION * Callback; }; struct cmpFind { CSTRING Path; STR Flags; struct CompressedItem * Item; }; -INLINE ERROR cmpCompressBuffer(APTR Ob, APTR Input, LONG InputSize, APTR Output, LONG OutputSize, LONG * Result) { +INLINE ERR cmpCompressBuffer(APTR Ob, APTR Input, LONG InputSize, APTR Output, LONG OutputSize, LONG * Result) noexcept { struct cmpCompressBuffer args = { Input, InputSize, Output, OutputSize, (LONG)0 }; - ERROR error = Action(MT_CmpCompressBuffer, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_CmpCompressBuffer, (OBJECTPTR)Ob, &args); if (Result) *Result = args.Result; return(error); } -INLINE ERROR cmpCompressFile(APTR Ob, CSTRING Location, CSTRING Path) { +INLINE ERR cmpCompressFile(APTR Ob, CSTRING Location, CSTRING Path) noexcept { struct cmpCompressFile args = { Location, Path }; return(Action(MT_CmpCompressFile, (OBJECTPTR)Ob, &args)); } -INLINE ERROR cmpDecompressBuffer(APTR Ob, APTR Input, APTR Output, LONG OutputSize, LONG * Result) { +INLINE ERR cmpDecompressBuffer(APTR Ob, APTR Input, APTR Output, LONG OutputSize, LONG * Result) noexcept { struct cmpDecompressBuffer args = { Input, Output, OutputSize, (LONG)0 }; - ERROR error = Action(MT_CmpDecompressBuffer, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_CmpDecompressBuffer, (OBJECTPTR)Ob, &args); if (Result) *Result = args.Result; return(error); } -INLINE ERROR cmpDecompressFile(APTR Ob, CSTRING Path, CSTRING Dest, LONG Flags) { +INLINE ERR cmpDecompressFile(APTR Ob, CSTRING Path, CSTRING Dest, LONG Flags) noexcept { struct cmpDecompressFile args = { Path, Dest, Flags }; return(Action(MT_CmpDecompressFile, (OBJECTPTR)Ob, &args)); } -INLINE ERROR cmpRemoveFile(APTR Ob, CSTRING Path) { +INLINE ERR cmpRemoveFile(APTR Ob, CSTRING Path) noexcept { struct cmpRemoveFile args = { Path }; return(Action(MT_CmpRemoveFile, (OBJECTPTR)Ob, &args)); } -INLINE ERROR cmpCompressStream(APTR Ob, APTR Input, LONG Length, FUNCTION * Callback, APTR Output, LONG OutputSize) { +INLINE ERR cmpCompressStream(APTR Ob, APTR Input, LONG Length, FUNCTION * Callback, APTR Output, LONG OutputSize) noexcept { struct cmpCompressStream args = { Input, Length, Callback, Output, OutputSize }; return(Action(MT_CmpCompressStream, (OBJECTPTR)Ob, &args)); } -INLINE ERROR cmpDecompressStream(APTR Ob, APTR Input, LONG Length, FUNCTION * Callback, APTR Output, LONG OutputSize) { +INLINE ERR cmpDecompressStream(APTR Ob, APTR Input, LONG Length, FUNCTION * Callback, APTR Output, LONG OutputSize) noexcept { struct cmpDecompressStream args = { Input, Length, Callback, Output, OutputSize }; return(Action(MT_CmpDecompressStream, (OBJECTPTR)Ob, &args)); } #define cmpCompressStreamStart(obj) Action(MT_CmpCompressStreamStart,(obj),0) -INLINE ERROR cmpCompressStreamEnd(APTR Ob, FUNCTION * Callback, APTR Output, LONG OutputSize) { +INLINE ERR cmpCompressStreamEnd(APTR Ob, FUNCTION * Callback, APTR Output, LONG OutputSize) noexcept { struct cmpCompressStreamEnd args = { Callback, Output, OutputSize }; return(Action(MT_CmpCompressStreamEnd, (OBJECTPTR)Ob, &args)); } -INLINE ERROR cmpDecompressStreamEnd(APTR Ob, FUNCTION * Callback) { +INLINE ERR cmpDecompressStreamEnd(APTR Ob, FUNCTION * Callback) noexcept { struct cmpDecompressStreamEnd args = { Callback }; return(Action(MT_CmpDecompressStreamEnd, (OBJECTPTR)Ob, &args)); } #define cmpDecompressStreamStart(obj) Action(MT_CmpDecompressStreamStart,(obj),0) -INLINE ERROR cmpDecompressObject(APTR Ob, CSTRING Path, OBJECTPTR Object) { +INLINE ERR cmpDecompressObject(APTR Ob, CSTRING Path, OBJECTPTR Object) noexcept { struct cmpDecompressObject args = { Path, Object }; return(Action(MT_CmpDecompressObject, (OBJECTPTR)Ob, &args)); } -INLINE ERROR cmpScan(APTR Ob, CSTRING Folder, CSTRING Filter, FUNCTION * Callback) { +INLINE ERR cmpScan(APTR Ob, CSTRING Folder, CSTRING Filter, FUNCTION * Callback) noexcept { struct cmpScan args = { Folder, Filter, Callback }; return(Action(MT_CmpScan, (OBJECTPTR)Ob, &args)); } -INLINE ERROR cmpFind(APTR Ob, CSTRING Path, STR Flags, struct CompressedItem ** Item) { +INLINE ERR cmpFind(APTR Ob, CSTRING Path, STR Flags, struct CompressedItem ** Item) noexcept { struct cmpFind args = { Path, Flags, (struct CompressedItem *)0 }; - ERROR error = Action(MT_CmpFind, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_CmpFind, (OBJECTPTR)Ob, &args); if (Item) *Item = args.Item; return(error); } @@ -4454,63 +4544,63 @@ class objCompression : public BaseClass { // Action stubs - inline ERROR flush() { return Action(AC_Flush, this, NULL); } - inline ERROR init() { return InitObject(this); } + inline ERR flush() noexcept { return Action(AC_Flush, this, NULL); } + inline ERR init() noexcept { return InitObject(this); } // Customised field setting - inline ERROR setOutput(const OBJECTID Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setOutput(OBJECTID Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->OutputID = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setCompressionLevel(const LONG Value) { + inline ERR setCompressionLevel(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[6]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setFlags(const CMF Value) { + inline ERR setFlags(const CMF Value) noexcept { this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setSegmentSize(const LONG Value) { + inline ERR setSegmentSize(const LONG Value) noexcept { this->SegmentSize = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setPermissions(const PERMIT Value) { + inline ERR setPermissions(const PERMIT Value) noexcept { this->Permissions = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setWindowBits(const LONG Value) { + inline ERR setWindowBits(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[14]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - template inline ERROR setArchiveName(T && Value) { + template inline ERR setArchiveName(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[18]; return field->WriteValue(target, field, 0x08800200, to_cstring(Value), 1); } - template inline ERROR setPath(T && Value) { + template inline ERR setPath(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[12]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setFeedback(FUNCTION Value) { + inline ERR setFeedback(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[17]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } - template inline ERROR setPassword(T && Value) { + template inline ERR setPassword(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[7]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); @@ -4536,22 +4626,22 @@ class objCompressedStream : public BaseClass { // Customised field setting - inline ERROR setInput(OBJECTPTR Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setInput(OBJECTPTR Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Input = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setOutput(OBJECTPTR Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setOutput(OBJECTPTR Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Output = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFormat(const CF Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setFormat(const CF Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Format = Value; - return ERR_Okay; + return ERR::Okay; } }; @@ -4565,78 +4655,78 @@ class objCompressedStream : public BaseClass { #define acDataXML(a,b) acDataFeed((a),0,DATA::XML,(b),0) #define acDataText(a,b) acDataFeed((a),0,DATA::TEXT,(b),0) -inline ERROR acCustom(OBJECTID ObjectID, LONG Number, CSTRING String) { +inline ERR acCustom(OBJECTID ObjectID, LONG Number, CSTRING String) { struct acCustom args = { Number, String }; return ActionMsg(AC_Custom, ObjectID, &args); } -inline ERROR acDataFeed(OBJECTID ObjectID, OBJECTPTR Sender, DATA Datatype, const APTR Data, LONG Size) { +inline ERR acDataFeed(OBJECTID ObjectID, OBJECTPTR Sender, DATA Datatype, const APTR Data, LONG Size) { struct acDataFeed channel = { Sender, Datatype, Data, Size }; return ActionMsg(AC_DataFeed, ObjectID, &channel); } -inline ERROR acDragDrop(OBJECTID ObjectID, OBJECTPTR Source, LONG Item, CSTRING Datatype) { +inline ERR acDragDrop(OBJECTID ObjectID, OBJECTPTR Source, LONG Item, CSTRING Datatype) { struct acDragDrop args = { Source, Item, Datatype }; return ActionMsg(AC_DragDrop, ObjectID, &args); } -inline ERROR acDrawArea(OBJECTID ObjectID, LONG X, LONG Y, LONG Width, LONG Height) { +inline ERR acDrawArea(OBJECTID ObjectID, LONG X, LONG Y, LONG Width, LONG Height) { struct acDraw draw = { X, Y, Width, Height }; return ActionMsg(AC_Draw, ObjectID, &draw); } -inline ERROR acMove(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z = 0) { +inline ERR acMove(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z = 0) { struct acMove move = { X, Y, Z }; return ActionMsg(AC_Move, ObjectID, &move); } -inline ERROR acMoveToPoint(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z = 0, MTF Flags = MTF::X|MTF::Y) { +inline ERR acMoveToPoint(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z = 0, MTF Flags = MTF::X|MTF::Y) { struct acMoveToPoint moveto = { X, Y, Z, Flags }; return ActionMsg(AC_MoveToPoint, ObjectID, &moveto); } -inline ERROR acRedimension(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE Width, DOUBLE Height, DOUBLE Depth) { +inline ERR acRedimension(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE Width, DOUBLE Height, DOUBLE Depth) { struct acRedimension resize = { X, Y, Z, Width, Height, Depth }; return ActionMsg(AC_Redimension, ObjectID, &resize); } -inline ERROR acResize(OBJECTID ObjectID, DOUBLE Width, DOUBLE Height, DOUBLE Depth) { +inline ERR acResize(OBJECTID ObjectID, DOUBLE Width, DOUBLE Height, DOUBLE Depth) { struct acResize resize = { Width, Height, Depth }; return ActionMsg(AC_Resize, ObjectID, &resize); } -inline ERROR acScrollToPoint(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z = 0, STP Flags = STP::X|STP::Y) { +inline ERR acScrollToPoint(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z = 0, STP Flags = STP::X|STP::Y) { struct acScrollToPoint scroll = { X, Y, Z, Flags }; return ActionMsg(AC_ScrollToPoint, ObjectID, &scroll); } -inline ERROR acScroll(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z = 0) { +inline ERR acScroll(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z = 0) { struct acScroll scroll = { X, Y, Z }; return ActionMsg(AC_Scroll, ObjectID, &scroll); } -inline ERROR acSelectArea(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) { +inline ERR acSelectArea(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) { struct acSelectArea area = { X, Y, Width, Height }; return ActionMsg(AC_SelectArea, ObjectID, &area); } -inline ERROR acActivate(OBJECTID ObjectID) { return ActionMsg(AC_Activate, ObjectID, NULL); } -inline ERROR acClear(OBJECTID ObjectID) { return ActionMsg(AC_Clear, ObjectID, NULL); } -inline ERROR acDisable(OBJECTID ObjectID) { return ActionMsg(AC_Disable, ObjectID, NULL); } -inline ERROR acDraw(OBJECTID ObjectID) { return ActionMsg(AC_Draw, ObjectID, NULL); } -inline ERROR acEnable(OBJECTID ObjectID) { return ActionMsg(AC_Enable, ObjectID, NULL); } -inline ERROR acFlush(OBJECTID ObjectID) { return ActionMsg(AC_Flush, ObjectID, NULL); } -inline ERROR acFocus(OBJECTID ObjectID) { return ActionMsg(AC_Focus, ObjectID, NULL); } -inline ERROR acHide(OBJECTID ObjectID) { return ActionMsg(AC_Hide, ObjectID, NULL); } -inline ERROR acLostFocus(OBJECTID ObjectID) { return ActionMsg(AC_LostFocus, ObjectID, NULL); } -inline ERROR acMoveToBack(OBJECTID ObjectID) { return ActionMsg(AC_MoveToBack, ObjectID, NULL); } -inline ERROR acMoveToFront(OBJECTID ObjectID) { return ActionMsg(AC_MoveToFront, ObjectID, NULL); } -inline ERROR acQuery(OBJECTID ObjectID) { return ActionMsg(AC_Query, ObjectID, NULL); } -inline ERROR acRefresh(OBJECTID ObjectID) { return ActionMsg(AC_Refresh, ObjectID, NULL); } -inline ERROR acSaveSettings(OBJECTID ObjectID) { return ActionMsg(AC_SaveSettings, ObjectID, NULL); } -inline ERROR acShow(OBJECTID ObjectID) { return ActionMsg(AC_Show, ObjectID, NULL); } - -inline ERROR acWrite(OBJECTID ObjectID, CPTR Buffer, LONG Bytes) { +inline ERR acActivate(OBJECTID ObjectID) { return ActionMsg(AC_Activate, ObjectID, NULL); } +inline ERR acClear(OBJECTID ObjectID) { return ActionMsg(AC_Clear, ObjectID, NULL); } +inline ERR acDisable(OBJECTID ObjectID) { return ActionMsg(AC_Disable, ObjectID, NULL); } +inline ERR acDraw(OBJECTID ObjectID) { return ActionMsg(AC_Draw, ObjectID, NULL); } +inline ERR acEnable(OBJECTID ObjectID) { return ActionMsg(AC_Enable, ObjectID, NULL); } +inline ERR acFlush(OBJECTID ObjectID) { return ActionMsg(AC_Flush, ObjectID, NULL); } +inline ERR acFocus(OBJECTID ObjectID) { return ActionMsg(AC_Focus, ObjectID, NULL); } +inline ERR acHide(OBJECTID ObjectID) { return ActionMsg(AC_Hide, ObjectID, NULL); } +inline ERR acLostFocus(OBJECTID ObjectID) { return ActionMsg(AC_LostFocus, ObjectID, NULL); } +inline ERR acMoveToBack(OBJECTID ObjectID) { return ActionMsg(AC_MoveToBack, ObjectID, NULL); } +inline ERR acMoveToFront(OBJECTID ObjectID) { return ActionMsg(AC_MoveToFront, ObjectID, NULL); } +inline ERR acQuery(OBJECTID ObjectID) { return ActionMsg(AC_Query, ObjectID, NULL); } +inline ERR acRefresh(OBJECTID ObjectID) { return ActionMsg(AC_Refresh, ObjectID, NULL); } +inline ERR acSaveSettings(OBJECTID ObjectID) { return ActionMsg(AC_SaveSettings, ObjectID, NULL); } +inline ERR acShow(OBJECTID ObjectID) { return ActionMsg(AC_Show, ObjectID, NULL); } + +inline ERR acWrite(OBJECTID ObjectID, CPTR Buffer, LONG Bytes) { struct acWrite write = { (BYTE *)Buffer, Bytes }; return ActionMsg(AC_Write, ObjectID, &write); } @@ -4741,17 +4831,17 @@ struct evHotplug { inline CSTRING flReadLine(OBJECTPTR Object) { struct flReadLine args; - if (!Action(MT_FlReadLine, Object, &args)) return args.Result; + if (Action(MT_FlReadLine, Object, &args) IS ERR::Okay) return args.Result; else return NULL; } // Read endian values from files and objects. -template ERROR flReadLE(OBJECTPTR Object, T *Result) +template ERR flReadLE(OBJECTPTR Object, T *Result) { UBYTE data[sizeof(T)]; struct acRead read = { .Buffer = data, .Length = sizeof(T) }; - if (!Action(AC_Read, Object, &read)) { + if (Action(AC_Read, Object, &read) IS ERR::Okay) { if (read.Result IS sizeof(T)) { if constexpr (std::endian::native == std::endian::little) { *Result = ((T *)data)[0]; @@ -4764,18 +4854,18 @@ template ERROR flReadLE(OBJECTPTR Object, T *Result) default: *Result = ((T *)data)[0]; } } - return ERR_Okay; + return ERR::Okay; } - else return ERR_Read; + else return ERR::Read; } - else return ERR_Read; + else return ERR::Read; } -template ERROR flReadBE(OBJECTPTR Object, T *Result) +template ERR flReadBE(OBJECTPTR Object, T *Result) { UBYTE data[sizeof(T)]; struct acRead read = { .Buffer = data, .Length = sizeof(T) }; - if (!Action(AC_Read, Object, &read)) { + if (Action(AC_Read, Object, &read) IS ERR::Okay) { if (read.Result IS sizeof(T)) { if constexpr (std::endian::native == std::endian::little) { switch(sizeof(T)) { @@ -4788,22 +4878,33 @@ template ERROR flReadBE(OBJECTPTR Object, T *Result) else { *Result = ((T *)data)[0]; } - return ERR_Okay; + return ERR::Okay; } - else return ERR_Read; + else return ERR::Read; } - else return ERR_Read; + else return ERR::Read; } -template -constexpr FUNCTION make_function_stdc(R Routine, OBJECTPTR Context = CurrentContext()) { - FUNCTION func = { .Type = CALL_STDC, .StdC = { .Context = Context, .Routine = (APTR)Routine } }; - return func; -} +// Function construction (refer types.h) -inline FUNCTION make_function_script(OBJECTPTR Script, LARGE Procedure) { - FUNCTION func = { .Type = CALL_SCRIPT, .Script = { .Script = (OBJECTPTR)Script, .ProcedureID = Procedure } }; - return func; -} +template FUNCTION::FUNCTION(T *pRoutine) { + Type = CALL_STDC; + StdC.Context = CurrentContext(); + StdC.Routine = (APTR)pRoutine; +}; + +template FUNCTION::FUNCTION(T *pRoutine, OBJECTPTR pContext, APTR pMeta) { + Type = CALL_STDC; + StdC.Context = pContext; + StdC.Routine = (APTR)pRoutine; + StdC.Meta = pMeta; +}; + +template FUNCTION::FUNCTION(T *pRoutine, APTR pMeta) { + Type = CALL_STDC; + StdC.Context = CurrentContext(); + StdC.Routine = (APTR)pRoutine; + StdC.Meta = pMeta; +}; inline CSTRING BaseClass::className() { return Class->ClassName; } diff --git a/include/parasol/modules/display.h b/include/parasol/modules/display.h index 615029c30..416440e49 100644 --- a/include/parasol/modules/display.h +++ b/include/parasol/modules/display.h @@ -1,7 +1,7 @@ #pragma once // Name: display.h -// Copyright: Paul Manias 2003-2023 +// Copyright: Paul Manias 2003-2024 // Generator: idl-c #include @@ -503,32 +503,32 @@ struct bmpDrawRectangle { LONG X; LONG Y; LONG Width; LONG Height; ULONG Colour; struct bmpSetClipRegion { LONG Number; LONG Left; LONG Top; LONG Right; LONG Bottom; LONG Terminate; }; struct bmpGetColour { LONG Red; LONG Green; LONG Blue; LONG Alpha; ULONG Colour; }; -INLINE ERROR bmpCopyArea(APTR Ob, objBitmap * DestBitmap, BAF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) { +INLINE ERR bmpCopyArea(APTR Ob, objBitmap * DestBitmap, BAF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) noexcept { struct bmpCopyArea args = { DestBitmap, Flags, X, Y, Width, Height, XDest, YDest }; return(Action(MT_BmpCopyArea, (OBJECTPTR)Ob, &args)); } -INLINE ERROR bmpCompress(APTR Ob, LONG Level) { +INLINE ERR bmpCompress(APTR Ob, LONG Level) noexcept { struct bmpCompress args = { Level }; return(Action(MT_BmpCompress, (OBJECTPTR)Ob, &args)); } -INLINE ERROR bmpDecompress(APTR Ob, LONG RetainData) { +INLINE ERR bmpDecompress(APTR Ob, LONG RetainData) noexcept { struct bmpDecompress args = { RetainData }; return(Action(MT_BmpDecompress, (OBJECTPTR)Ob, &args)); } -INLINE ERROR bmpFlip(APTR Ob, FLIP Orientation) { +INLINE ERR bmpFlip(APTR Ob, FLIP Orientation) noexcept { struct bmpFlip args = { Orientation }; return(Action(MT_BmpFlip, (OBJECTPTR)Ob, &args)); } -INLINE ERROR bmpDrawRectangle(APTR Ob, LONG X, LONG Y, LONG Width, LONG Height, ULONG Colour, BAF Flags) { +INLINE ERR bmpDrawRectangle(APTR Ob, LONG X, LONG Y, LONG Width, LONG Height, ULONG Colour, BAF Flags) noexcept { struct bmpDrawRectangle args = { X, Y, Width, Height, Colour, Flags }; return(Action(MT_BmpDrawRectangle, (OBJECTPTR)Ob, &args)); } -INLINE ERROR bmpSetClipRegion(APTR Ob, LONG Number, LONG Left, LONG Top, LONG Right, LONG Bottom, LONG Terminate) { +INLINE ERR bmpSetClipRegion(APTR Ob, LONG Number, LONG Left, LONG Top, LONG Right, LONG Bottom, LONG Terminate) noexcept { struct bmpSetClipRegion args = { Number, Left, Top, Right, Bottom, Terminate }; return(Action(MT_BmpSetClipRegion, (OBJECTPTR)Ob, &args)); } @@ -585,7 +585,7 @@ class objBitmap : public BaseClass { if (BitsPerPixel > 8) return packPixel(Red, Green, Blue, Alpha); else { struct bmpGetColour args = { Red, Green, Blue, Alpha }; - if (!Action(MT_BmpGetColour, this, &args)) return args.Colour; + if (Action(MT_BmpGetColour, this, &args) IS ERR::Okay) return args.Colour; return 0; } } @@ -594,7 +594,7 @@ class objBitmap : public BaseClass { if (BitsPerPixel > 8) return packPixel(RGB); else { struct bmpGetColour args = { RGB.Red, RGB.Green, RGB.Blue, RGB.Alpha }; - if (!Action(MT_BmpGetColour, this, &args)) return args.Colour; + if (Action(MT_BmpGetColour, this, &args) IS ERR::Okay) return args.Colour; return 0; } } @@ -640,7 +640,7 @@ class objBitmap : public BaseClass { inline ULONG packPixelWB(struct RGB8 &RGB) { return (RGB.Red << ColourFormat->RedPos) | (RGB.Green << ColourFormat->GreenPos) | (RGB.Blue << ColourFormat->BluePos) | (RGB.Alpha << ColourFormat->AlphaPos); } - + inline ULONG packPixelWB(struct RGB8 &RGB, UBYTE Alpha) { return (RGB.Red << ColourFormat->RedPos) | (RGB.Green << ColourFormat->GreenPos) | (RGB.Blue << ColourFormat->BluePos) | (Alpha << ColourFormat->AlphaPos); } @@ -654,213 +654,218 @@ class objBitmap : public BaseClass { // Action stubs - inline ERROR clear() { return Action(AC_Clear, this, NULL); } - inline ERROR copyData(OBJECTPTR Dest) { + inline ERR clear() noexcept { return Action(AC_Clear, this, NULL); } + inline ERR copyData(OBJECTPTR Dest) noexcept { struct acCopyData args = { .Dest = Dest }; return Action(AC_CopyData, this, &args); } - inline ERROR draw() { return Action(AC_Draw, this, NULL); } - inline ERROR drawArea(LONG X, LONG Y, LONG Width, LONG Height) { + inline ERR draw() noexcept { return Action(AC_Draw, this, NULL); } + inline ERR drawArea(LONG X, LONG Y, LONG Width, LONG Height) noexcept { struct acDraw args = { X, Y, Width, Height }; return Action(AC_Draw, this, &args); } - inline ERROR flush() { return Action(AC_Flush, this, NULL); } - inline ERROR init() { return InitObject(this); } - inline ERROR lock() { return Action(AC_Lock, this, NULL); } - inline ERROR query() { return Action(AC_Query, this, NULL); } - template ERROR read(APTR Buffer, T Size, U *Result) { + inline ERR flush() noexcept { return Action(AC_Flush, this, NULL); } + inline ERR init() noexcept { return InitObject(this); } + inline ERR lock() noexcept { return Action(AC_Lock, this, NULL); } + inline ERR query() noexcept { return Action(AC_Query, this, NULL); } + template ERR read(APTR Buffer, T Size, U *Result) noexcept { static_assert(std::is_integral::value, "Result value must be an integer type"); static_assert(std::is_integral::value, "Size value must be an integer type"); - ERROR error; const LONG bytes = (Size > 0x7fffffff) ? 0x7fffffff : Size; struct acRead read = { (BYTE *)Buffer, bytes }; - if (!(error = Action(AC_Read, this, &read))) *Result = static_cast(read.Result); - else *Result = 0; - return error; + if (auto error = Action(AC_Read, this, &read); error IS ERR::Okay) { + *Result = static_cast(read.Result); + return ERR::Okay; + } + else { *Result = 0; return error; } } - template ERROR read(APTR Buffer, T Size) { + template ERR read(APTR Buffer, T Size) noexcept { static_assert(std::is_integral::value, "Size value must be an integer type"); const LONG bytes = (Size > 0x7fffffff) ? 0x7fffffff : Size; struct acRead read = { (BYTE *)Buffer, bytes }; return Action(AC_Read, this, &read); } - inline ERROR resize(DOUBLE Width, DOUBLE Height, DOUBLE Depth = 0) { + inline ERR resize(DOUBLE Width, DOUBLE Height, DOUBLE Depth = 0) noexcept { struct acResize args = { Width, Height, Depth }; return Action(AC_Resize, this, &args); } - inline ERROR saveImage(OBJECTPTR Dest, CLASSID ClassID = 0) { + inline ERR saveImage(OBJECTPTR Dest, CLASSID ClassID = 0) noexcept { struct acSaveImage args = { Dest, { ClassID } }; return Action(AC_SaveImage, this, &args); } - inline ERROR seek(DOUBLE Offset, SEEK Position = SEEK::CURRENT) { + inline ERR seek(DOUBLE Offset, SEEK Position = SEEK::CURRENT) noexcept { struct acSeek args = { Offset, Position }; return Action(AC_Seek, this, &args); } - inline ERROR seekStart(DOUBLE Offset) { return seek(Offset, SEEK::START); } - inline ERROR seekEnd(DOUBLE Offset) { return seek(Offset, SEEK::END); } - inline ERROR seekCurrent(DOUBLE Offset) { return seek(Offset, SEEK::CURRENT); } - inline ERROR unlock() { return Action(AC_Unlock, this, NULL); } - inline ERROR write(CPTR Buffer, LONG Size, LONG *Result = NULL) { - ERROR error; + inline ERR seekStart(DOUBLE Offset) noexcept { return seek(Offset, SEEK::START); } + inline ERR seekEnd(DOUBLE Offset) noexcept { return seek(Offset, SEEK::END); } + inline ERR seekCurrent(DOUBLE Offset) noexcept { return seek(Offset, SEEK::CURRENT); } + inline ERR unlock() noexcept { return Action(AC_Unlock, this, NULL); } + inline ERR write(CPTR Buffer, LONG Size, LONG *Result = NULL) noexcept { struct acWrite write = { (BYTE *)Buffer, Size }; - if (!(error = Action(AC_Write, this, &write))) { + if (auto error = Action(AC_Write, this, &write); error IS ERR::Okay) { if (Result) *Result = write.Result; + return ERR::Okay; + } + else { + if (Result) *Result = 0; + return error; } - else if (Result) *Result = 0; - return error; } - inline ERROR write(std::string Buffer, LONG *Result = NULL) { - ERROR error; + inline ERR write(std::string Buffer, LONG *Result = NULL) noexcept { struct acWrite write = { (BYTE *)Buffer.c_str(), LONG(Buffer.size()) }; - if (!(error = Action(AC_Write, this, &write))) { + if (auto error = Action(AC_Write, this, &write); error IS ERR::Okay) { if (Result) *Result = write.Result; + return ERR::Okay; + } + else { + if (Result) *Result = 0; + return error; } - else if (Result) *Result = 0; - return error; } - inline LONG writeResult(CPTR Buffer, LONG Size) { + inline LONG writeResult(CPTR Buffer, LONG Size) noexcept { struct acWrite write = { (BYTE *)Buffer, Size }; - if (!Action(AC_Write, this, &write)) return write.Result; + if (Action(AC_Write, this, &write) IS ERR::Okay) return write.Result; else return 0; } // Customised field setting - inline ERROR setPalette(struct RGBPalette * Value) { + inline ERR setPalette(struct RGBPalette * Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[31]; return field->WriteValue(target, field, 0x08000300, Value, 1); } - inline ERROR setData(UBYTE * Value) { + inline ERR setData(UBYTE * Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[25]; return field->WriteValue(target, field, 0x08000500, Value, 1); } - inline ERROR setWidth(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setWidth(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Width = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setHeight(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setHeight(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Height = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setType(const BMP Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setType(const BMP Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Type = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setClip(struct ClipRectangle * Value) { + inline ERR setClip(struct ClipRectangle * Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[24]; return field->WriteValue(target, field, 0x08000310, Value, 1); } - inline ERROR setDataFlags(const MEM Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setDataFlags(const MEM Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->DataFlags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setAmtColours(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setAmtColours(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->AmtColours = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFlags(const BMF Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setFlags(const BMF Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setTransIndex(const LONG Value) { + inline ERR setTransIndex(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[30]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setBytesPerPixel(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setBytesPerPixel(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->BytesPerPixel = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setBitsPerPixel(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setBitsPerPixel(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->BitsPerPixel = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setXOffset(const LONG Value) { + inline ERR setXOffset(const LONG Value) noexcept { this->XOffset = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setYOffset(const LONG Value) { + inline ERR setYOffset(const LONG Value) noexcept { this->YOffset = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setOpacity(const LONG Value) { + inline ERR setOpacity(const LONG Value) noexcept { this->Opacity = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setTransRGB(const struct RGB8 * Value, LONG Elements) { + inline ERR setTransRGB(const struct RGB8 * Value, LONG Elements) noexcept { auto target = this; auto field = &this->Class->Dictionary[34]; return field->WriteValue(target, field, 0x01081300, Value, Elements); } - inline ERROR setBkgdIndex(const LONG Value) { + inline ERR setBkgdIndex(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[10]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setColourSpace(const CS Value) { + inline ERR setColourSpace(const CS Value) noexcept { this->ColourSpace = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setClipLeft(const LONG Value) { + inline ERR setClipLeft(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[15]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setClipRight(const LONG Value) { + inline ERR setClipRight(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[13]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setClipBottom(const LONG Value) { + inline ERR setClipBottom(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[18]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setClipTop(const LONG Value) { + inline ERR setClipTop(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[38]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setBkgd(const BYTE * Value, LONG Elements) { + inline ERR setBkgd(const BYTE * Value, LONG Elements) noexcept { auto target = this; auto field = &this->Class->Dictionary[23]; return field->WriteValue(target, field, 0x01081300, Value, Elements); } - inline ERROR setHandle(APTR Value) { + inline ERR setHandle(APTR Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[0]; return field->WriteValue(target, field, 0x08010300, Value, 1); @@ -893,32 +898,32 @@ struct gfxSetMonitor { CSTRING Name; LONG MinH; LONG MaxH; LONG MinV; LONG MaxV; #define gfxWaitVBL(obj) Action(MT_GfxWaitVBL,(obj),0) -INLINE ERROR gfxUpdatePalette(APTR Ob, struct RGBPalette * NewPalette) { +INLINE ERR gfxUpdatePalette(APTR Ob, struct RGBPalette * NewPalette) noexcept { struct gfxUpdatePalette args = { NewPalette }; return(Action(MT_GfxUpdatePalette, (OBJECTPTR)Ob, &args)); } -INLINE ERROR gfxSetDisplay(APTR Ob, LONG X, LONG Y, LONG Width, LONG Height, LONG InsideWidth, LONG InsideHeight, LONG BitsPerPixel, DOUBLE RefreshRate, LONG Flags) { +INLINE ERR gfxSetDisplay(APTR Ob, LONG X, LONG Y, LONG Width, LONG Height, LONG InsideWidth, LONG InsideHeight, LONG BitsPerPixel, DOUBLE RefreshRate, LONG Flags) noexcept { struct gfxSetDisplay args = { X, Y, Width, Height, InsideWidth, InsideHeight, BitsPerPixel, RefreshRate, Flags }; return(Action(MT_GfxSetDisplay, (OBJECTPTR)Ob, &args)); } -INLINE ERROR gfxSizeHints(APTR Ob, LONG MinWidth, LONG MinHeight, LONG MaxWidth, LONG MaxHeight, LONG EnforceAspect) { +INLINE ERR gfxSizeHints(APTR Ob, LONG MinWidth, LONG MinHeight, LONG MaxWidth, LONG MaxHeight, LONG EnforceAspect) noexcept { struct gfxSizeHints args = { MinWidth, MinHeight, MaxWidth, MaxHeight, EnforceAspect }; return(Action(MT_GfxSizeHints, (OBJECTPTR)Ob, &args)); } -INLINE ERROR gfxSetGamma(APTR Ob, DOUBLE Red, DOUBLE Green, DOUBLE Blue, GMF Flags) { +INLINE ERR gfxSetGamma(APTR Ob, DOUBLE Red, DOUBLE Green, DOUBLE Blue, GMF Flags) noexcept { struct gfxSetGamma args = { Red, Green, Blue, Flags }; return(Action(MT_GfxSetGamma, (OBJECTPTR)Ob, &args)); } -INLINE ERROR gfxSetGammaLinear(APTR Ob, DOUBLE Red, DOUBLE Green, DOUBLE Blue, GMF Flags) { +INLINE ERR gfxSetGammaLinear(APTR Ob, DOUBLE Red, DOUBLE Green, DOUBLE Blue, GMF Flags) noexcept { struct gfxSetGammaLinear args = { Red, Green, Blue, Flags }; return(Action(MT_GfxSetGammaLinear, (OBJECTPTR)Ob, &args)); } -INLINE ERROR gfxSetMonitor(APTR Ob, CSTRING Name, LONG MinH, LONG MaxH, LONG MinV, LONG MaxV, MON Flags) { +INLINE ERR gfxSetMonitor(APTR Ob, CSTRING Name, LONG MinH, LONG MaxH, LONG MinV, LONG MaxV, MON Flags) noexcept { struct gfxSetMonitor args = { Name, MinH, MaxH, MinV, MaxV, Flags }; return(Action(MT_GfxSetMonitor, (OBJECTPTR)Ob, &args)); } @@ -960,154 +965,154 @@ class objDisplay : public BaseClass { // Action stubs - inline ERROR activate() { return Action(AC_Activate, this, NULL); } - inline ERROR clear() { return Action(AC_Clear, this, NULL); } - inline ERROR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) { + inline ERR activate() noexcept { return Action(AC_Activate, this, NULL); } + inline ERR clear() noexcept { return Action(AC_Clear, this, NULL); } + inline ERR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) noexcept { struct acDataFeed args = { Object, Datatype, Buffer, Size }; return Action(AC_DataFeed, this, &args); } - inline ERROR disable() { return Action(AC_Disable, this, NULL); } - inline ERROR draw() { return Action(AC_Draw, this, NULL); } - inline ERROR drawArea(LONG X, LONG Y, LONG Width, LONG Height) { + inline ERR disable() noexcept { return Action(AC_Disable, this, NULL); } + inline ERR draw() noexcept { return Action(AC_Draw, this, NULL); } + inline ERR drawArea(LONG X, LONG Y, LONG Width, LONG Height) noexcept { struct acDraw args = { X, Y, Width, Height }; return Action(AC_Draw, this, &args); } - inline ERROR enable() { return Action(AC_Enable, this, NULL); } - inline ERROR flush() { return Action(AC_Flush, this, NULL); } - inline ERROR focus() { return Action(AC_Focus, this, NULL); } - inline ERROR getVar(CSTRING FieldName, STRING Buffer, LONG Size) { + inline ERR enable() noexcept { return Action(AC_Enable, this, NULL); } + inline ERR flush() noexcept { return Action(AC_Flush, this, NULL); } + inline ERR focus() noexcept { return Action(AC_Focus, this, NULL); } + inline ERR getVar(CSTRING FieldName, STRING Buffer, LONG Size) noexcept { struct acGetVar args = { FieldName, Buffer, Size }; - ERROR error = Action(AC_GetVar, this, &args); - if ((error) and (Buffer)) Buffer[0] = 0; + auto error = Action(AC_GetVar, this, &args); + if ((error != ERR::Okay) and (Buffer)) Buffer[0] = 0; return error; } - inline ERROR hide() { return Action(AC_Hide, this, NULL); } - inline ERROR init() { return InitObject(this); } - inline ERROR move(DOUBLE X, DOUBLE Y, DOUBLE Z) { + inline ERR hide() noexcept { return Action(AC_Hide, this, NULL); } + inline ERR init() noexcept { return InitObject(this); } + inline ERR move(DOUBLE X, DOUBLE Y, DOUBLE Z) noexcept { struct acMove args = { X, Y, Z }; return Action(AC_Move, this, &args); } - inline ERROR moveToBack() { return Action(AC_MoveToBack, this, NULL); } - inline ERROR moveToFront() { return Action(AC_MoveToFront, this, NULL); } - inline ERROR moveToPoint(DOUBLE X, DOUBLE Y, DOUBLE Z, MTF Flags) { + inline ERR moveToBack() noexcept { return Action(AC_MoveToBack, this, NULL); } + inline ERR moveToFront() noexcept { return Action(AC_MoveToFront, this, NULL); } + inline ERR moveToPoint(DOUBLE X, DOUBLE Y, DOUBLE Z, MTF Flags) noexcept { struct acMoveToPoint moveto = { X, Y, Z, Flags }; return Action(AC_MoveToPoint, this, &moveto); } - inline ERROR redimension(DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE Width, DOUBLE Height, DOUBLE Depth) { + inline ERR redimension(DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE Width, DOUBLE Height, DOUBLE Depth) noexcept { struct acRedimension args = { X, Y, Z, Width, Height, Depth }; return Action(AC_Redimension, this, &args); } - inline ERROR redimension(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) { + inline ERR redimension(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) noexcept { struct acRedimension args = { X, Y, 0, Width, Height, 0 }; return Action(AC_Redimension, this, &args); } - inline ERROR resize(DOUBLE Width, DOUBLE Height, DOUBLE Depth = 0) { + inline ERR resize(DOUBLE Width, DOUBLE Height, DOUBLE Depth = 0) noexcept { struct acResize args = { Width, Height, Depth }; return Action(AC_Resize, this, &args); } - inline ERROR saveImage(OBJECTPTR Dest, CLASSID ClassID = 0) { + inline ERR saveImage(OBJECTPTR Dest, CLASSID ClassID = 0) noexcept { struct acSaveImage args = { Dest, { ClassID } }; return Action(AC_SaveImage, this, &args); } - inline ERROR saveSettings() { return Action(AC_SaveSettings, this, NULL); } - inline ERROR show() { return Action(AC_Show, this, NULL); } + inline ERR saveSettings() noexcept { return Action(AC_SaveSettings, this, NULL); } + inline ERR show() noexcept { return Action(AC_Show, this, NULL); } // Customised field setting - inline ERROR setRefreshRate(const DOUBLE Value) { + inline ERR setRefreshRate(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[43]; return field->WriteValue(target, field, FD_DOUBLE, &Value, 1); } - inline ERROR setFlags(const SCR Value) { + inline ERR setFlags(const SCR Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[4]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setWidth(const LONG Value) { + inline ERR setWidth(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[8]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setHeight(const LONG Value) { + inline ERR setHeight(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[2]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setX(const LONG Value) { + inline ERR setX(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[0]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setY(const LONG Value) { + inline ERR setY(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[1]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setBmpX(const LONG Value) { + inline ERR setBmpX(const LONG Value) noexcept { this->BmpX = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setBmpY(const LONG Value) { + inline ERR setBmpY(const LONG Value) noexcept { this->BmpY = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setPowerMode(const DPMS Value) { + inline ERR setPowerMode(const DPMS Value) noexcept { this->PowerMode = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setPopOver(const OBJECTID Value) { + inline ERR setPopOver(OBJECTID Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[27]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setGamma(const DOUBLE * Value, LONG Elements) { + inline ERR setGamma(const DOUBLE * Value, LONG Elements) noexcept { auto target = this; auto field = &this->Class->Dictionary[5]; return field->WriteValue(target, field, 0x80001508, Value, Elements); } - inline ERROR setHDensity(const LONG Value) { + inline ERR setHDensity(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[17]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setVDensity(const LONG Value) { + inline ERR setVDensity(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[15]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setOpacity(const DOUBLE Value) { + inline ERR setOpacity(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[16]; return field->WriteValue(target, field, FD_DOUBLE, &Value, 1); } - inline ERROR setResizeFeedback(const FUNCTION Value) { + inline ERR setResizeFeedback(const FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[32]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } - inline ERROR setWindowHandle(APTR Value) { + inline ERR setWindowHandle(APTR Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[11]; return field->WriteValue(target, field, 0x08000308, Value, 1); } - template inline ERROR setTitle(T && Value) { + template inline ERR setTitle(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[7]; return field->WriteValue(target, field, 0x08800308, to_cstring(Value), 1); @@ -1133,31 +1138,31 @@ struct clipGetFiles { CLIPTYPE Datatype; LONG Index; CSTRING * Files; CEF Flags; struct clipAddText { CSTRING String; }; struct clipRemove { CLIPTYPE Datatype; }; -INLINE ERROR clipAddFile(APTR Ob, CLIPTYPE Datatype, CSTRING Path, CEF Flags) { +INLINE ERR clipAddFile(APTR Ob, CLIPTYPE Datatype, CSTRING Path, CEF Flags) noexcept { struct clipAddFile args = { Datatype, Path, Flags }; return(Action(MT_ClipAddFile, (OBJECTPTR)Ob, &args)); } -INLINE ERROR clipAddObjects(APTR Ob, CLIPTYPE Datatype, OBJECTID * Objects, CEF Flags) { +INLINE ERR clipAddObjects(APTR Ob, CLIPTYPE Datatype, OBJECTID * Objects, CEF Flags) noexcept { struct clipAddObjects args = { Datatype, Objects, Flags }; return(Action(MT_ClipAddObjects, (OBJECTPTR)Ob, &args)); } -INLINE ERROR clipGetFiles(APTR Ob, CLIPTYPE * Datatype, LONG Index, CSTRING ** Files, CEF * Flags) { +INLINE ERR clipGetFiles(APTR Ob, CLIPTYPE * Datatype, LONG Index, CSTRING ** Files, CEF * Flags) noexcept { struct clipGetFiles args = { (CLIPTYPE)0, Index, (CSTRING *)0, (CEF)0 }; - ERROR error = Action(MT_ClipGetFiles, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_ClipGetFiles, (OBJECTPTR)Ob, &args); if (Datatype) *Datatype = args.Datatype; if (Files) *Files = args.Files; if (Flags) *Flags = args.Flags; return(error); } -INLINE ERROR clipAddText(APTR Ob, CSTRING String) { +INLINE ERR clipAddText(APTR Ob, CSTRING String) noexcept { struct clipAddText args = { String }; return(Action(MT_ClipAddText, (OBJECTPTR)Ob, &args)); } -INLINE ERROR clipRemove(APTR Ob, CLIPTYPE Datatype) { +INLINE ERR clipRemove(APTR Ob, CLIPTYPE Datatype) noexcept { struct clipRemove args = { Datatype }; return(Action(MT_ClipRemove, (OBJECTPTR)Ob, &args)); } @@ -1178,22 +1183,22 @@ class objClipboard : public BaseClass { // Action stubs - inline ERROR clear() { return Action(AC_Clear, this, NULL); } - inline ERROR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) { + inline ERR clear() noexcept { return Action(AC_Clear, this, NULL); } + inline ERR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) noexcept { struct acDataFeed args = { Object, Datatype, Buffer, Size }; return Action(AC_DataFeed, this, &args); } - inline ERROR init() { return InitObject(this); } + inline ERR init() noexcept { return InitObject(this); } // Customised field setting - inline ERROR setFlags(const CPF Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setFlags(const CPF Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setRequestHandler(FUNCTION Value) { + inline ERR setRequestHandler(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[3]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); @@ -1239,77 +1244,77 @@ class objPointer : public BaseClass { // Customised field setting - inline ERROR setSpeed(const DOUBLE Value) { + inline ERR setSpeed(const DOUBLE Value) noexcept { this->Speed = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setAcceleration(const DOUBLE Value) { + inline ERR setAcceleration(const DOUBLE Value) noexcept { this->Acceleration = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setDoubleClick(const DOUBLE Value) { + inline ERR setDoubleClick(const DOUBLE Value) noexcept { this->DoubleClick = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setWheelSpeed(const DOUBLE Value) { + inline ERR setWheelSpeed(const DOUBLE Value) noexcept { this->WheelSpeed = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setX(const DOUBLE Value) { + inline ERR setX(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[0]; return field->WriteValue(target, field, FD_DOUBLE, &Value, 1); } - inline ERROR setY(const DOUBLE Value) { + inline ERR setY(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[1]; return field->WriteValue(target, field, FD_DOUBLE, &Value, 1); } - inline ERROR setMaxSpeed(const LONG Value) { + inline ERR setMaxSpeed(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[21]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setInput(const OBJECTID Value) { + inline ERR setInput(OBJECTID Value) noexcept { this->InputID = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setSurface(const OBJECTID Value) { + inline ERR setSurface(OBJECTID Value) noexcept { this->SurfaceID = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setCursor(const PTC Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setCursor(const PTC Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->CursorID = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setCursorOwner(const OBJECTID Value) { + inline ERR setCursorOwner(OBJECTID Value) noexcept { this->CursorOwnerID = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFlags(const PF Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setFlags(const PF Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setClickSlop(const LONG Value) { + inline ERR setClickSlop(const LONG Value) noexcept { this->ClickSlop = Value; - return ERR_Okay; + return ERR::Okay; } - template inline ERROR setButtonOrder(T && Value) { + template inline ERR setButtonOrder(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[13]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); @@ -1343,34 +1348,34 @@ struct drwAddCallback { FUNCTION * Callback; }; struct drwResetDimensions { DOUBLE X; DOUBLE Y; DOUBLE XOffset; DOUBLE YOffset; DOUBLE Width; DOUBLE Height; LONG Dimensions; }; struct drwRemoveCallback { FUNCTION * Callback; }; -INLINE ERROR drwInheritedFocus(APTR Ob, OBJECTID FocusID, RNF Flags) { +INLINE ERR drwInheritedFocus(APTR Ob, OBJECTID FocusID, RNF Flags) noexcept { struct drwInheritedFocus args = { FocusID, Flags }; return(Action(MT_DrwInheritedFocus, (OBJECTPTR)Ob, &args)); } -INLINE ERROR drwExpose(APTR Ob, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags) { +INLINE ERR drwExpose(APTR Ob, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags) noexcept { struct drwExpose args = { X, Y, Width, Height, Flags }; return(Action(MT_DrwExpose, (OBJECTPTR)Ob, &args)); } -INLINE ERROR drwInvalidateRegion(APTR Ob, LONG X, LONG Y, LONG Width, LONG Height) { +INLINE ERR drwInvalidateRegion(APTR Ob, LONG X, LONG Y, LONG Width, LONG Height) noexcept { struct drwInvalidateRegion args = { X, Y, Width, Height }; return(Action(MT_DrwInvalidateRegion, (OBJECTPTR)Ob, &args)); } -INLINE ERROR drwSetDisplay(APTR Ob, LONG X, LONG Y, LONG Width, LONG Height, LONG InsideWidth, LONG InsideHeight, LONG BitsPerPixel, DOUBLE RefreshRate, LONG Flags) { +INLINE ERR drwSetDisplay(APTR Ob, LONG X, LONG Y, LONG Width, LONG Height, LONG InsideWidth, LONG InsideHeight, LONG BitsPerPixel, DOUBLE RefreshRate, LONG Flags) noexcept { struct drwSetDisplay args = { X, Y, Width, Height, InsideWidth, InsideHeight, BitsPerPixel, RefreshRate, Flags }; return(Action(MT_DrwSetDisplay, (OBJECTPTR)Ob, &args)); } -INLINE ERROR drwSetOpacity(APTR Ob, DOUBLE Value, DOUBLE Adjustment) { +INLINE ERR drwSetOpacity(APTR Ob, DOUBLE Value, DOUBLE Adjustment) noexcept { struct drwSetOpacity args = { Value, Adjustment }; return(Action(MT_DrwSetOpacity, (OBJECTPTR)Ob, &args)); } #define drwMinimise(obj) Action(MT_DrwMinimise,(obj),0) -INLINE ERROR drwResetDimensions(APTR Ob, DOUBLE X, DOUBLE Y, DOUBLE XOffset, DOUBLE YOffset, DOUBLE Width, DOUBLE Height, LONG Dimensions) { +INLINE ERR drwResetDimensions(APTR Ob, DOUBLE X, DOUBLE Y, DOUBLE XOffset, DOUBLE YOffset, DOUBLE Width, DOUBLE Height, LONG Dimensions) noexcept { struct drwResetDimensions args = { X, Y, XOffset, YOffset, Width, Height, Dimensions }; return(Action(MT_DrwResetDimensions, (OBJECTPTR)Ob, &args)); } @@ -1419,10 +1424,10 @@ class objSurface : public BaseClass { #ifdef PRV_SURFACE // These coordinate fields are considered private but may be accessed by some internal classes, like Document LONG XOffset, YOffset; // Fixed horizontal and vertical offset - DOUBLE XOffsetPercent; // Relative horizontal offset - DOUBLE YOffsetPercent; // Relative vertical offset - DOUBLE WidthPercent, HeightPercent; // Relative width and height - DOUBLE XPercent, YPercent; // Relative coordinate + DOUBLE XOffsetPercent; // Scaled horizontal offset + DOUBLE YOffsetPercent; // Scaled vertical offset + DOUBLE WidthPercent, HeightPercent; // Scaled width and height + DOUBLE XPercent, YPercent; // Scaled coordinate #endif public: inline bool visible() const { return (Flags & RNF::VISIBLE) != RNF::NIL; } @@ -1434,292 +1439,292 @@ class objSurface : public BaseClass { // Action stubs - inline ERROR activate() { return Action(AC_Activate, this, NULL); } - inline ERROR disable() { return Action(AC_Disable, this, NULL); } - inline ERROR draw() { return Action(AC_Draw, this, NULL); } - inline ERROR drawArea(LONG X, LONG Y, LONG Width, LONG Height) { + inline ERR activate() noexcept { return Action(AC_Activate, this, NULL); } + inline ERR disable() noexcept { return Action(AC_Disable, this, NULL); } + inline ERR draw() noexcept { return Action(AC_Draw, this, NULL); } + inline ERR drawArea(LONG X, LONG Y, LONG Width, LONG Height) noexcept { struct acDraw args = { X, Y, Width, Height }; return Action(AC_Draw, this, &args); } - inline ERROR enable() { return Action(AC_Enable, this, NULL); } - inline ERROR focus() { return Action(AC_Focus, this, NULL); } - inline ERROR hide() { return Action(AC_Hide, this, NULL); } - inline ERROR init() { return InitObject(this); } - inline ERROR lostFocus() { return Action(AC_LostFocus, this, NULL); } - inline ERROR move(DOUBLE X, DOUBLE Y, DOUBLE Z) { + inline ERR enable() noexcept { return Action(AC_Enable, this, NULL); } + inline ERR focus() noexcept { return Action(AC_Focus, this, NULL); } + inline ERR hide() noexcept { return Action(AC_Hide, this, NULL); } + inline ERR init() noexcept { return InitObject(this); } + inline ERR lostFocus() noexcept { return Action(AC_LostFocus, this, NULL); } + inline ERR move(DOUBLE X, DOUBLE Y, DOUBLE Z) noexcept { struct acMove args = { X, Y, Z }; return Action(AC_Move, this, &args); } - inline ERROR moveToBack() { return Action(AC_MoveToBack, this, NULL); } - inline ERROR moveToFront() { return Action(AC_MoveToFront, this, NULL); } - inline ERROR moveToPoint(DOUBLE X, DOUBLE Y, DOUBLE Z, MTF Flags) { + inline ERR moveToBack() noexcept { return Action(AC_MoveToBack, this, NULL); } + inline ERR moveToFront() noexcept { return Action(AC_MoveToFront, this, NULL); } + inline ERR moveToPoint(DOUBLE X, DOUBLE Y, DOUBLE Z, MTF Flags) noexcept { struct acMoveToPoint moveto = { X, Y, Z, Flags }; return Action(AC_MoveToPoint, this, &moveto); } - inline ERROR redimension(DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE Width, DOUBLE Height, DOUBLE Depth) { + inline ERR redimension(DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE Width, DOUBLE Height, DOUBLE Depth) noexcept { struct acRedimension args = { X, Y, Z, Width, Height, Depth }; return Action(AC_Redimension, this, &args); } - inline ERROR redimension(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) { + inline ERR redimension(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) noexcept { struct acRedimension args = { X, Y, 0, Width, Height, 0 }; return Action(AC_Redimension, this, &args); } - inline ERROR resize(DOUBLE Width, DOUBLE Height, DOUBLE Depth = 0) { + inline ERR resize(DOUBLE Width, DOUBLE Height, DOUBLE Depth = 0) noexcept { struct acResize args = { Width, Height, Depth }; return Action(AC_Resize, this, &args); } - inline ERROR saveImage(OBJECTPTR Dest, CLASSID ClassID = 0) { + inline ERR saveImage(OBJECTPTR Dest, CLASSID ClassID = 0) noexcept { struct acSaveImage args = { Dest, { ClassID } }; return Action(AC_SaveImage, this, &args); } - inline ERROR scroll(DOUBLE X, DOUBLE Y, DOUBLE Z = 0) { + inline ERR scroll(DOUBLE X, DOUBLE Y, DOUBLE Z = 0) noexcept { struct acScroll args = { X, Y, Z }; return Action(AC_Scroll, this, &args); } - inline ERROR scrollToPoint(DOUBLE X, DOUBLE Y, DOUBLE Z, STP Flags) { + inline ERR scrollToPoint(DOUBLE X, DOUBLE Y, DOUBLE Z, STP Flags) noexcept { struct acScrollToPoint args = { X, Y, Z, Flags }; return Action(AC_ScrollToPoint, this, &args); } - inline ERROR show() { return Action(AC_Show, this, NULL); } + inline ERR show() noexcept { return Action(AC_Show, this, NULL); } // Customised field setting - inline ERROR setDrag(const OBJECTID Value) { + inline ERR setDrag(OBJECTID Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[29]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setParent(const OBJECTID Value) { + inline ERR setParent(OBJECTID Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[15]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setPopOver(const OBJECTID Value) { + inline ERR setPopOver(OBJECTID Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[40]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setTopMargin(const LONG Value) { + inline ERR setTopMargin(const LONG Value) noexcept { this->TopMargin = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setBottomMargin(const LONG Value) { + inline ERR setBottomMargin(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[43]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setLeftMargin(const LONG Value) { + inline ERR setLeftMargin(const LONG Value) noexcept { this->LeftMargin = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setRightMargin(const LONG Value) { + inline ERR setRightMargin(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[38]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setMinWidth(const LONG Value) { + inline ERR setMinWidth(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[37]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setMinHeight(const LONG Value) { + inline ERR setMinHeight(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[33]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setMaxWidth(const LONG Value) { + inline ERR setMaxWidth(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[23]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setMaxHeight(const LONG Value) { + inline ERR setMaxHeight(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[16]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setLeftLimit(const LONG Value) { + inline ERR setLeftLimit(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[5]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setRightLimit(const LONG Value) { + inline ERR setRightLimit(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[19]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setTopLimit(const LONG Value) { + inline ERR setTopLimit(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[52]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setBottomLimit(const LONG Value) { + inline ERR setBottomLimit(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[50]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setFlags(const RNF Value) { + inline ERR setFlags(const RNF Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[8]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setX(const LONG Value) { + inline ERR setX(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[0]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setY(const LONG Value) { + inline ERR setY(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[1]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setWidth(const LONG Value) { + inline ERR setWidth(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[12]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setHeight(const LONG Value) { + inline ERR setHeight(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[2]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setAlign(const ALIGN Value) { + inline ERR setAlign(const ALIGN Value) noexcept { this->Align = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setDimensions(const LONG Value) { + inline ERR setDimensions(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[35]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setCursor(const PTC Value) { + inline ERR setCursor(const PTC Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[53]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setColour(const struct RGB8 Value) { + inline ERR setColour(const struct RGB8 Value) noexcept { this->Colour = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setType(const RT Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setType(const RT Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Type = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setModal(const LONG Value) { + inline ERR setModal(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[9]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setRootLayer(const OBJECTID Value) { + inline ERR setRootLayer(OBJECTID Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[39]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setAbsX(const LONG Value) { + inline ERR setAbsX(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[27]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setAbsY(const LONG Value) { + inline ERR setAbsY(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[28]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setBitsPerPixel(const LONG Value) { + inline ERR setBitsPerPixel(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[41]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setInsideHeight(const LONG Value) { + inline ERR setInsideHeight(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[47]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setInsideWidth(const LONG Value) { + inline ERR setInsideWidth(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[36]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setMovement(const LONG Value) { + inline ERR setMovement(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[34]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setOpacity(const DOUBLE Value) { + inline ERR setOpacity(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[25]; return field->WriteValue(target, field, FD_DOUBLE, &Value, 1); } - inline ERROR setRevertFocus(const OBJECTID Value) { + inline ERR setRevertFocus(OBJECTID Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[18]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setVisible(const LONG Value) { + inline ERR setVisible(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[26]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setWindowType(const LONG Value) { + inline ERR setWindowType(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[32]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setWindowHandle(APTR Value) { + inline ERR setWindowHandle(APTR Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[21]; return field->WriteValue(target, field, 0x08000308, Value, 1); } - inline ERROR setXOffset(const LONG Value) { + inline ERR setXOffset(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[17]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setYOffset(const LONG Value) { + inline ERR setYOffset(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[24]; Variable var(Value); @@ -1737,49 +1742,49 @@ class objSurface : public BaseClass { struct DisplayBase { #ifndef PARASOL_STATIC objPointer * (*_AccessPointer)(void); - ERROR (*_CheckIfChild)(OBJECTID Parent, OBJECTID Child); - ERROR (*_CopyArea)(objBitmap * Bitmap, objBitmap * Dest, BAF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); - ERROR (*_CopyRawBitmap)(struct BitmapSurfaceV2 * Surface, objBitmap * Bitmap, CSRF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); - ERROR (*_CopySurface)(OBJECTID Surface, objBitmap * Bitmap, BDF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); + ERR (*_CheckIfChild)(OBJECTID Parent, OBJECTID Child); + ERR (*_CopyArea)(objBitmap * Bitmap, objBitmap * Dest, BAF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); + ERR (*_CopyRawBitmap)(struct BitmapSurfaceV2 * Surface, objBitmap * Bitmap, CSRF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); + ERR (*_CopySurface)(OBJECTID Surface, objBitmap * Bitmap, BDF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); void (*_DrawPixel)(objBitmap * Bitmap, LONG X, LONG Y, ULONG Colour); void (*_DrawRGBPixel)(objBitmap * Bitmap, LONG X, LONG Y, struct RGB8 * RGB); void (*_DrawRectangle)(objBitmap * Bitmap, LONG X, LONG Y, LONG Width, LONG Height, ULONG Colour, BAF Flags); - ERROR (*_ExposeSurface)(OBJECTID Surface, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags); + ERR (*_ExposeSurface)(OBJECTID Surface, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags); void (*_FlipBitmap)(objBitmap * Bitmap, FLIP Orientation); void (*_GetColourFormat)(struct ColourFormat * Format, LONG BitsPerPixel, LONG RedMask, LONG GreenMask, LONG BlueMask, LONG AlphaMask); - ERROR (*_GetCursorInfo)(struct CursorInfo * Info, LONG Size); - ERROR (*_GetCursorPos)(DOUBLE * X, DOUBLE * Y); - ERROR (*_GetDisplayInfo)(OBJECTID Display, struct DisplayInfoV3 ** Info); + ERR (*_GetCursorInfo)(struct CursorInfo * Info, LONG Size); + ERR (*_GetCursorPos)(DOUBLE * X, DOUBLE * Y); + ERR (*_GetDisplayInfo)(OBJECTID Display, struct DisplayInfoV3 ** Info); DT (*_GetDisplayType)(void); CSTRING (*_GetInputTypeName)(JET Type); OBJECTID (*_GetModalSurface)(void); - ERROR (*_GetRelativeCursorPos)(OBJECTID Surface, DOUBLE * X, DOUBLE * Y); - ERROR (*_GetSurfaceCoords)(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height); - ERROR (*_GetSurfaceFlags)(OBJECTID Surface, RNF * Flags); - ERROR (*_GetSurfaceInfo)(OBJECTID Surface, struct SurfaceInfoV2 ** Info); + ERR (*_GetRelativeCursorPos)(OBJECTID Surface, DOUBLE * X, DOUBLE * Y); + ERR (*_GetSurfaceCoords)(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height); + ERR (*_GetSurfaceFlags)(OBJECTID Surface, RNF * Flags); + ERR (*_GetSurfaceInfo)(OBJECTID Surface, struct SurfaceInfoV2 ** Info); OBJECTID (*_GetUserFocus)(void); - ERROR (*_GetVisibleArea)(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height); - ERROR (*_LockBitmap)(OBJECTID Surface, objBitmap ** Bitmap, LVF * Info); - ERROR (*_LockCursor)(OBJECTID Surface); + ERR (*_GetVisibleArea)(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height); + ERR (*_LockBitmap)(OBJECTID Surface, objBitmap ** Bitmap, LVF * Info); + ERR (*_LockCursor)(OBJECTID Surface); ULONG (*_ReadPixel)(objBitmap * Bitmap, LONG X, LONG Y); void (*_ReadRGBPixel)(objBitmap * Bitmap, LONG X, LONG Y, struct RGB8 ** RGB); - ERROR (*_Resample)(objBitmap * Bitmap, struct ColourFormat * ColourFormat); - ERROR (*_RestoreCursor)(PTC Cursor, OBJECTID Owner); + ERR (*_Resample)(objBitmap * Bitmap, struct ColourFormat * ColourFormat); + ERR (*_RestoreCursor)(PTC Cursor, OBJECTID Owner); DOUBLE (*_ScaleToDPI)(DOUBLE Value); - ERROR (*_ScanDisplayModes)(CSTRING Filter, struct DisplayInfoV3 * Info, LONG Size); + ERR (*_ScanDisplayModes)(CSTRING Filter, struct DisplayInfoV3 * Info, LONG Size); void (*_SetClipRegion)(objBitmap * Bitmap, LONG Number, LONG Left, LONG Top, LONG Right, LONG Bottom, LONG Terminate); - ERROR (*_SetCursor)(OBJECTID Surface, CRF Flags, PTC Cursor, CSTRING Name, OBJECTID Owner); - ERROR (*_SetCursorPos)(DOUBLE X, DOUBLE Y); - ERROR (*_SetCustomCursor)(OBJECTID Surface, CRF Flags, objBitmap * Bitmap, LONG HotX, LONG HotY, OBJECTID Owner); - ERROR (*_SetHostOption)(HOST Option, LARGE Value); + ERR (*_SetCursor)(OBJECTID Surface, CRF Flags, PTC Cursor, CSTRING Name, OBJECTID Owner); + ERR (*_SetCursorPos)(DOUBLE X, DOUBLE Y); + ERR (*_SetCustomCursor)(OBJECTID Surface, CRF Flags, objBitmap * Bitmap, LONG HotX, LONG HotY, OBJECTID Owner); + ERR (*_SetHostOption)(HOST Option, LARGE Value); OBJECTID (*_SetModalSurface)(OBJECTID Surface); - ERROR (*_StartCursorDrag)(OBJECTID Source, LONG Item, CSTRING Datatypes, OBJECTID Surface); - ERROR (*_SubscribeInput)(FUNCTION * Callback, OBJECTID SurfaceFilter, JTYPE Mask, OBJECTID DeviceFilter, LONG * Handle); + ERR (*_StartCursorDrag)(OBJECTID Source, LONG Item, CSTRING Datatypes, OBJECTID Surface); + ERR (*_SubscribeInput)(FUNCTION * Callback, OBJECTID SurfaceFilter, JTYPE Mask, OBJECTID DeviceFilter, LONG * Handle); void (*_Sync)(objBitmap * Bitmap); - ERROR (*_UnlockBitmap)(OBJECTID Surface, objBitmap * Bitmap); - ERROR (*_UnlockCursor)(OBJECTID Surface); - ERROR (*_UnsubscribeInput)(LONG Handle); - ERROR (*_WindowHook)(OBJECTID SurfaceID, WH Event, FUNCTION * Callback); + ERR (*_UnlockBitmap)(OBJECTID Surface, objBitmap * Bitmap); + ERR (*_UnlockCursor)(OBJECTID Surface); + ERR (*_UnsubscribeInput)(LONG Handle); + ERR (*_WindowHook)(OBJECTID SurfaceID, WH Event, FUNCTION * Callback); #endif // PARASOL_STATIC }; @@ -1787,95 +1792,95 @@ struct DisplayBase { #ifndef PARASOL_STATIC extern struct DisplayBase *DisplayBase; inline objPointer * gfxAccessPointer(void) { return DisplayBase->_AccessPointer(); } -inline ERROR gfxCheckIfChild(OBJECTID Parent, OBJECTID Child) { return DisplayBase->_CheckIfChild(Parent,Child); } -inline ERROR gfxCopyArea(objBitmap * Bitmap, objBitmap * Dest, BAF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) { return DisplayBase->_CopyArea(Bitmap,Dest,Flags,X,Y,Width,Height,XDest,YDest); } -inline ERROR gfxCopyRawBitmap(struct BitmapSurfaceV2 * Surface, objBitmap * Bitmap, CSRF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) { return DisplayBase->_CopyRawBitmap(Surface,Bitmap,Flags,X,Y,Width,Height,XDest,YDest); } -inline ERROR gfxCopySurface(OBJECTID Surface, objBitmap * Bitmap, BDF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) { return DisplayBase->_CopySurface(Surface,Bitmap,Flags,X,Y,Width,Height,XDest,YDest); } +inline ERR gfxCheckIfChild(OBJECTID Parent, OBJECTID Child) { return DisplayBase->_CheckIfChild(Parent,Child); } +inline ERR gfxCopyArea(objBitmap * Bitmap, objBitmap * Dest, BAF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) { return DisplayBase->_CopyArea(Bitmap,Dest,Flags,X,Y,Width,Height,XDest,YDest); } +inline ERR gfxCopyRawBitmap(struct BitmapSurfaceV2 * Surface, objBitmap * Bitmap, CSRF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) { return DisplayBase->_CopyRawBitmap(Surface,Bitmap,Flags,X,Y,Width,Height,XDest,YDest); } +inline ERR gfxCopySurface(OBJECTID Surface, objBitmap * Bitmap, BDF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) { return DisplayBase->_CopySurface(Surface,Bitmap,Flags,X,Y,Width,Height,XDest,YDest); } inline void gfxDrawPixel(objBitmap * Bitmap, LONG X, LONG Y, ULONG Colour) { return DisplayBase->_DrawPixel(Bitmap,X,Y,Colour); } inline void gfxDrawRGBPixel(objBitmap * Bitmap, LONG X, LONG Y, struct RGB8 * RGB) { return DisplayBase->_DrawRGBPixel(Bitmap,X,Y,RGB); } inline void gfxDrawRectangle(objBitmap * Bitmap, LONG X, LONG Y, LONG Width, LONG Height, ULONG Colour, BAF Flags) { return DisplayBase->_DrawRectangle(Bitmap,X,Y,Width,Height,Colour,Flags); } -inline ERROR gfxExposeSurface(OBJECTID Surface, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags) { return DisplayBase->_ExposeSurface(Surface,X,Y,Width,Height,Flags); } +inline ERR gfxExposeSurface(OBJECTID Surface, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags) { return DisplayBase->_ExposeSurface(Surface,X,Y,Width,Height,Flags); } inline void gfxFlipBitmap(objBitmap * Bitmap, FLIP Orientation) { return DisplayBase->_FlipBitmap(Bitmap,Orientation); } inline void gfxGetColourFormat(struct ColourFormat * Format, LONG BitsPerPixel, LONG RedMask, LONG GreenMask, LONG BlueMask, LONG AlphaMask) { return DisplayBase->_GetColourFormat(Format,BitsPerPixel,RedMask,GreenMask,BlueMask,AlphaMask); } -inline ERROR gfxGetCursorInfo(struct CursorInfo * Info, LONG Size) { return DisplayBase->_GetCursorInfo(Info,Size); } -inline ERROR gfxGetCursorPos(DOUBLE * X, DOUBLE * Y) { return DisplayBase->_GetCursorPos(X,Y); } -inline ERROR gfxGetDisplayInfo(OBJECTID Display, struct DisplayInfoV3 ** Info) { return DisplayBase->_GetDisplayInfo(Display,Info); } +inline ERR gfxGetCursorInfo(struct CursorInfo * Info, LONG Size) { return DisplayBase->_GetCursorInfo(Info,Size); } +inline ERR gfxGetCursorPos(DOUBLE * X, DOUBLE * Y) { return DisplayBase->_GetCursorPos(X,Y); } +inline ERR gfxGetDisplayInfo(OBJECTID Display, struct DisplayInfoV3 ** Info) { return DisplayBase->_GetDisplayInfo(Display,Info); } inline DT gfxGetDisplayType(void) { return DisplayBase->_GetDisplayType(); } inline CSTRING gfxGetInputTypeName(JET Type) { return DisplayBase->_GetInputTypeName(Type); } inline OBJECTID gfxGetModalSurface(void) { return DisplayBase->_GetModalSurface(); } -inline ERROR gfxGetRelativeCursorPos(OBJECTID Surface, DOUBLE * X, DOUBLE * Y) { return DisplayBase->_GetRelativeCursorPos(Surface,X,Y); } -inline ERROR gfxGetSurfaceCoords(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height) { return DisplayBase->_GetSurfaceCoords(Surface,X,Y,AbsX,AbsY,Width,Height); } -inline ERROR gfxGetSurfaceFlags(OBJECTID Surface, RNF * Flags) { return DisplayBase->_GetSurfaceFlags(Surface,Flags); } -inline ERROR gfxGetSurfaceInfo(OBJECTID Surface, struct SurfaceInfoV2 ** Info) { return DisplayBase->_GetSurfaceInfo(Surface,Info); } +inline ERR gfxGetRelativeCursorPos(OBJECTID Surface, DOUBLE * X, DOUBLE * Y) { return DisplayBase->_GetRelativeCursorPos(Surface,X,Y); } +inline ERR gfxGetSurfaceCoords(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height) { return DisplayBase->_GetSurfaceCoords(Surface,X,Y,AbsX,AbsY,Width,Height); } +inline ERR gfxGetSurfaceFlags(OBJECTID Surface, RNF * Flags) { return DisplayBase->_GetSurfaceFlags(Surface,Flags); } +inline ERR gfxGetSurfaceInfo(OBJECTID Surface, struct SurfaceInfoV2 ** Info) { return DisplayBase->_GetSurfaceInfo(Surface,Info); } inline OBJECTID gfxGetUserFocus(void) { return DisplayBase->_GetUserFocus(); } -inline ERROR gfxGetVisibleArea(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height) { return DisplayBase->_GetVisibleArea(Surface,X,Y,AbsX,AbsY,Width,Height); } -inline ERROR gfxLockBitmap(OBJECTID Surface, objBitmap ** Bitmap, LVF * Info) { return DisplayBase->_LockBitmap(Surface,Bitmap,Info); } -inline ERROR gfxLockCursor(OBJECTID Surface) { return DisplayBase->_LockCursor(Surface); } +inline ERR gfxGetVisibleArea(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height) { return DisplayBase->_GetVisibleArea(Surface,X,Y,AbsX,AbsY,Width,Height); } +inline ERR gfxLockBitmap(OBJECTID Surface, objBitmap ** Bitmap, LVF * Info) { return DisplayBase->_LockBitmap(Surface,Bitmap,Info); } +inline ERR gfxLockCursor(OBJECTID Surface) { return DisplayBase->_LockCursor(Surface); } inline ULONG gfxReadPixel(objBitmap * Bitmap, LONG X, LONG Y) { return DisplayBase->_ReadPixel(Bitmap,X,Y); } inline void gfxReadRGBPixel(objBitmap * Bitmap, LONG X, LONG Y, struct RGB8 ** RGB) { return DisplayBase->_ReadRGBPixel(Bitmap,X,Y,RGB); } -inline ERROR gfxResample(objBitmap * Bitmap, struct ColourFormat * ColourFormat) { return DisplayBase->_Resample(Bitmap,ColourFormat); } -inline ERROR gfxRestoreCursor(PTC Cursor, OBJECTID Owner) { return DisplayBase->_RestoreCursor(Cursor,Owner); } +inline ERR gfxResample(objBitmap * Bitmap, struct ColourFormat * ColourFormat) { return DisplayBase->_Resample(Bitmap,ColourFormat); } +inline ERR gfxRestoreCursor(PTC Cursor, OBJECTID Owner) { return DisplayBase->_RestoreCursor(Cursor,Owner); } inline DOUBLE gfxScaleToDPI(DOUBLE Value) { return DisplayBase->_ScaleToDPI(Value); } -inline ERROR gfxScanDisplayModes(CSTRING Filter, struct DisplayInfoV3 * Info, LONG Size) { return DisplayBase->_ScanDisplayModes(Filter,Info,Size); } +inline ERR gfxScanDisplayModes(CSTRING Filter, struct DisplayInfoV3 * Info, LONG Size) { return DisplayBase->_ScanDisplayModes(Filter,Info,Size); } inline void gfxSetClipRegion(objBitmap * Bitmap, LONG Number, LONG Left, LONG Top, LONG Right, LONG Bottom, LONG Terminate) { return DisplayBase->_SetClipRegion(Bitmap,Number,Left,Top,Right,Bottom,Terminate); } -inline ERROR gfxSetCursor(OBJECTID Surface, CRF Flags, PTC Cursor, CSTRING Name, OBJECTID Owner) { return DisplayBase->_SetCursor(Surface,Flags,Cursor,Name,Owner); } -inline ERROR gfxSetCursorPos(DOUBLE X, DOUBLE Y) { return DisplayBase->_SetCursorPos(X,Y); } -inline ERROR gfxSetCustomCursor(OBJECTID Surface, CRF Flags, objBitmap * Bitmap, LONG HotX, LONG HotY, OBJECTID Owner) { return DisplayBase->_SetCustomCursor(Surface,Flags,Bitmap,HotX,HotY,Owner); } -inline ERROR gfxSetHostOption(HOST Option, LARGE Value) { return DisplayBase->_SetHostOption(Option,Value); } +inline ERR gfxSetCursor(OBJECTID Surface, CRF Flags, PTC Cursor, CSTRING Name, OBJECTID Owner) { return DisplayBase->_SetCursor(Surface,Flags,Cursor,Name,Owner); } +inline ERR gfxSetCursorPos(DOUBLE X, DOUBLE Y) { return DisplayBase->_SetCursorPos(X,Y); } +inline ERR gfxSetCustomCursor(OBJECTID Surface, CRF Flags, objBitmap * Bitmap, LONG HotX, LONG HotY, OBJECTID Owner) { return DisplayBase->_SetCustomCursor(Surface,Flags,Bitmap,HotX,HotY,Owner); } +inline ERR gfxSetHostOption(HOST Option, LARGE Value) { return DisplayBase->_SetHostOption(Option,Value); } inline OBJECTID gfxSetModalSurface(OBJECTID Surface) { return DisplayBase->_SetModalSurface(Surface); } -inline ERROR gfxStartCursorDrag(OBJECTID Source, LONG Item, CSTRING Datatypes, OBJECTID Surface) { return DisplayBase->_StartCursorDrag(Source,Item,Datatypes,Surface); } -inline ERROR gfxSubscribeInput(FUNCTION * Callback, OBJECTID SurfaceFilter, JTYPE Mask, OBJECTID DeviceFilter, LONG * Handle) { return DisplayBase->_SubscribeInput(Callback,SurfaceFilter,Mask,DeviceFilter,Handle); } +inline ERR gfxStartCursorDrag(OBJECTID Source, LONG Item, CSTRING Datatypes, OBJECTID Surface) { return DisplayBase->_StartCursorDrag(Source,Item,Datatypes,Surface); } +inline ERR gfxSubscribeInput(FUNCTION * Callback, OBJECTID SurfaceFilter, JTYPE Mask, OBJECTID DeviceFilter, LONG * Handle) { return DisplayBase->_SubscribeInput(Callback,SurfaceFilter,Mask,DeviceFilter,Handle); } inline void gfxSync(objBitmap * Bitmap) { return DisplayBase->_Sync(Bitmap); } -inline ERROR gfxUnlockBitmap(OBJECTID Surface, objBitmap * Bitmap) { return DisplayBase->_UnlockBitmap(Surface,Bitmap); } -inline ERROR gfxUnlockCursor(OBJECTID Surface) { return DisplayBase->_UnlockCursor(Surface); } -inline ERROR gfxUnsubscribeInput(LONG Handle) { return DisplayBase->_UnsubscribeInput(Handle); } -inline ERROR gfxWindowHook(OBJECTID SurfaceID, WH Event, FUNCTION * Callback) { return DisplayBase->_WindowHook(SurfaceID,Event,Callback); } +inline ERR gfxUnlockBitmap(OBJECTID Surface, objBitmap * Bitmap) { return DisplayBase->_UnlockBitmap(Surface,Bitmap); } +inline ERR gfxUnlockCursor(OBJECTID Surface) { return DisplayBase->_UnlockCursor(Surface); } +inline ERR gfxUnsubscribeInput(LONG Handle) { return DisplayBase->_UnsubscribeInput(Handle); } +inline ERR gfxWindowHook(OBJECTID SurfaceID, WH Event, FUNCTION * Callback) { return DisplayBase->_WindowHook(SurfaceID,Event,Callback); } #else extern "C" { extern objPointer * gfxAccessPointer(void); -extern ERROR gfxCheckIfChild(OBJECTID Parent, OBJECTID Child); -extern ERROR gfxCopyArea(objBitmap * Bitmap, objBitmap * Dest, BAF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); -extern ERROR gfxCopyRawBitmap(struct BitmapSurfaceV2 * Surface, objBitmap * Bitmap, CSRF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); -extern ERROR gfxCopySurface(OBJECTID Surface, objBitmap * Bitmap, BDF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); +extern ERR gfxCheckIfChild(OBJECTID Parent, OBJECTID Child); +extern ERR gfxCopyArea(objBitmap * Bitmap, objBitmap * Dest, BAF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); +extern ERR gfxCopyRawBitmap(struct BitmapSurfaceV2 * Surface, objBitmap * Bitmap, CSRF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); +extern ERR gfxCopySurface(OBJECTID Surface, objBitmap * Bitmap, BDF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); extern void gfxDrawPixel(objBitmap * Bitmap, LONG X, LONG Y, ULONG Colour); extern void gfxDrawRGBPixel(objBitmap * Bitmap, LONG X, LONG Y, struct RGB8 * RGB); extern void gfxDrawRectangle(objBitmap * Bitmap, LONG X, LONG Y, LONG Width, LONG Height, ULONG Colour, BAF Flags); -extern ERROR gfxExposeSurface(OBJECTID Surface, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags); +extern ERR gfxExposeSurface(OBJECTID Surface, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags); extern void gfxFlipBitmap(objBitmap * Bitmap, FLIP Orientation); extern void gfxGetColourFormat(struct ColourFormat * Format, LONG BitsPerPixel, LONG RedMask, LONG GreenMask, LONG BlueMask, LONG AlphaMask); -extern ERROR gfxGetCursorInfo(struct CursorInfo * Info, LONG Size); -extern ERROR gfxGetCursorPos(DOUBLE * X, DOUBLE * Y); -extern ERROR gfxGetDisplayInfo(OBJECTID Display, struct DisplayInfoV3 ** Info); +extern ERR gfxGetCursorInfo(struct CursorInfo * Info, LONG Size); +extern ERR gfxGetCursorPos(DOUBLE * X, DOUBLE * Y); +extern ERR gfxGetDisplayInfo(OBJECTID Display, struct DisplayInfoV3 ** Info); extern DT gfxGetDisplayType(void); extern CSTRING gfxGetInputTypeName(JET Type); extern OBJECTID gfxGetModalSurface(void); -extern ERROR gfxGetRelativeCursorPos(OBJECTID Surface, DOUBLE * X, DOUBLE * Y); -extern ERROR gfxGetSurfaceCoords(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height); -extern ERROR gfxGetSurfaceFlags(OBJECTID Surface, RNF * Flags); -extern ERROR gfxGetSurfaceInfo(OBJECTID Surface, struct SurfaceInfoV2 ** Info); +extern ERR gfxGetRelativeCursorPos(OBJECTID Surface, DOUBLE * X, DOUBLE * Y); +extern ERR gfxGetSurfaceCoords(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height); +extern ERR gfxGetSurfaceFlags(OBJECTID Surface, RNF * Flags); +extern ERR gfxGetSurfaceInfo(OBJECTID Surface, struct SurfaceInfoV2 ** Info); extern OBJECTID gfxGetUserFocus(void); -extern ERROR gfxGetVisibleArea(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height); -extern ERROR gfxLockBitmap(OBJECTID Surface, objBitmap ** Bitmap, LVF * Info); -extern ERROR gfxLockCursor(OBJECTID Surface); +extern ERR gfxGetVisibleArea(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height); +extern ERR gfxLockBitmap(OBJECTID Surface, objBitmap ** Bitmap, LVF * Info); +extern ERR gfxLockCursor(OBJECTID Surface); extern ULONG gfxReadPixel(objBitmap * Bitmap, LONG X, LONG Y); extern void gfxReadRGBPixel(objBitmap * Bitmap, LONG X, LONG Y, struct RGB8 ** RGB); -extern ERROR gfxResample(objBitmap * Bitmap, struct ColourFormat * ColourFormat); -extern ERROR gfxRestoreCursor(PTC Cursor, OBJECTID Owner); +extern ERR gfxResample(objBitmap * Bitmap, struct ColourFormat * ColourFormat); +extern ERR gfxRestoreCursor(PTC Cursor, OBJECTID Owner); extern DOUBLE gfxScaleToDPI(DOUBLE Value); -extern ERROR gfxScanDisplayModes(CSTRING Filter, struct DisplayInfoV3 * Info, LONG Size); +extern ERR gfxScanDisplayModes(CSTRING Filter, struct DisplayInfoV3 * Info, LONG Size); extern void gfxSetClipRegion(objBitmap * Bitmap, LONG Number, LONG Left, LONG Top, LONG Right, LONG Bottom, LONG Terminate); -extern ERROR gfxSetCursor(OBJECTID Surface, CRF Flags, PTC Cursor, CSTRING Name, OBJECTID Owner); -extern ERROR gfxSetCursorPos(DOUBLE X, DOUBLE Y); -extern ERROR gfxSetCustomCursor(OBJECTID Surface, CRF Flags, objBitmap * Bitmap, LONG HotX, LONG HotY, OBJECTID Owner); -extern ERROR gfxSetHostOption(HOST Option, LARGE Value); +extern ERR gfxSetCursor(OBJECTID Surface, CRF Flags, PTC Cursor, CSTRING Name, OBJECTID Owner); +extern ERR gfxSetCursorPos(DOUBLE X, DOUBLE Y); +extern ERR gfxSetCustomCursor(OBJECTID Surface, CRF Flags, objBitmap * Bitmap, LONG HotX, LONG HotY, OBJECTID Owner); +extern ERR gfxSetHostOption(HOST Option, LARGE Value); extern OBJECTID gfxSetModalSurface(OBJECTID Surface); -extern ERROR gfxStartCursorDrag(OBJECTID Source, LONG Item, CSTRING Datatypes, OBJECTID Surface); -extern ERROR gfxSubscribeInput(FUNCTION * Callback, OBJECTID SurfaceFilter, JTYPE Mask, OBJECTID DeviceFilter, LONG * Handle); +extern ERR gfxStartCursorDrag(OBJECTID Source, LONG Item, CSTRING Datatypes, OBJECTID Surface); +extern ERR gfxSubscribeInput(FUNCTION * Callback, OBJECTID SurfaceFilter, JTYPE Mask, OBJECTID DeviceFilter, LONG * Handle); extern void gfxSync(objBitmap * Bitmap); -extern ERROR gfxUnlockBitmap(OBJECTID Surface, objBitmap * Bitmap); -extern ERROR gfxUnlockCursor(OBJECTID Surface); -extern ERROR gfxUnsubscribeInput(LONG Handle); -extern ERROR gfxWindowHook(OBJECTID SurfaceID, WH Event, FUNCTION * Callback); +extern ERR gfxUnlockBitmap(OBJECTID Surface, objBitmap * Bitmap); +extern ERR gfxUnlockCursor(OBJECTID Surface); +extern ERR gfxUnsubscribeInput(LONG Handle); +extern ERR gfxWindowHook(OBJECTID SurfaceID, WH Event, FUNCTION * Callback); } #endif // PARASOL_STATIC #endif @@ -1896,24 +1901,24 @@ extern ERROR gfxWindowHook(OBJECTID SurfaceID, WH Event, FUNCTION * Callback); // Stubs -INLINE ERROR drwInvalidateRegionID(OBJECTID ObjectID, LONG X, LONG Y, LONG Width, LONG Height) { +inline ERR drwInvalidateRegionID(OBJECTID ObjectID, LONG X, LONG Y, LONG Width, LONG Height) { struct drwInvalidateRegion args = { X, Y, Width, Height }; return ActionMsg(MT_DrwInvalidateRegion, ObjectID, &args); } -INLINE ERROR drwExposeID(OBJECTID ObjectID, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags) { +inline ERR drwExposeID(OBJECTID ObjectID, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags) { struct drwExpose args = { X, Y, Width, Height, Flags }; return ActionMsg(MT_DrwExpose, ObjectID, &args); } -INLINE ERROR drwSetOpacityID(OBJECTID ObjectID, DOUBLE Value, DOUBLE Adjustment) { +inline ERR drwSetOpacityID(OBJECTID ObjectID, DOUBLE Value, DOUBLE Adjustment) { struct drwSetOpacity args = { Value, Adjustment}; return ActionMsg(MT_DrwSetOpacity, ObjectID, &args); } -INLINE ERROR drwAddCallback(OBJECTPTR Surface, APTR Callback) { +inline ERR drwAddCallback(OBJECTPTR Surface, APTR Callback) { if (Callback) { - auto call = make_function_stdc(Callback); + auto call = FUNCTION(Callback); struct drwAddCallback args = { &call }; return Action(MT_DrwAddCallback, Surface, &args); } @@ -1923,9 +1928,9 @@ INLINE ERROR drwAddCallback(OBJECTPTR Surface, APTR Callback) { } } -INLINE ERROR drwRemoveCallback(OBJECTPTR Surface, APTR Callback) { +inline ERR drwRemoveCallback(OBJECTPTR Surface, APTR Callback) { if (Callback) { - auto call = make_function_stdc(Callback); + auto call = FUNCTION(Callback); struct drwRemoveCallback args = { &call }; return Action(MT_DrwRemoveCallback, Surface, &args); } @@ -1934,3 +1939,11 @@ INLINE ERROR drwRemoveCallback(OBJECTPTR Surface, APTR Callback) { return Action(MT_DrwRemoveCallback, Surface, &args); } } + + +namespace fl { + using namespace pf; + +constexpr FieldValue WindowType(SWIN Value) { return FieldValue(FID_WindowType, LONG(Value)); } + +} // namespace diff --git a/include/parasol/modules/document.h b/include/parasol/modules/document.h index 9ab0ed81d..4c121cc4c 100644 --- a/include/parasol/modules/document.h +++ b/include/parasol/modules/document.h @@ -1,7 +1,7 @@ #pragma once // Name: document.h -// Copyright: Paul Manias © 2005-2023 +// Copyright: Paul Manias © 2005-2024 // Generator: idl-c #include @@ -11,116 +11,82 @@ #include #include #include +#include class objDocument; // Official version number (date format). Any changes to the handling of document content require that this number be updated. -#define RIPPLE_VERSION "20160601" +#define RIPL_VERSION "20240126" -#define TT_OBJECT 1 -#define TT_LINK 2 -#define TT_EDIT 3 +enum class TT : BYTE { + NIL = 0, + VECTOR = 1, + LINK = 2, + EDIT = 3, +}; // Event flags for selectively receiving events from the Document object. -#define DEF_PATH 0x00000001 -#define DEF_LINK_ACTIVATED 0x00000002 +enum class DEF : ULONG { + NIL = 0, + PATH = 0x00000001, + ON_CLICK = 0x00000002, + ON_MOTION = 0x00000004, + ON_CROSSING_IN = 0x00000008, + ON_CROSSING_OUT = 0x00000010, + ON_CROSSING = 0x00000018, + LINK_ACTIVATED = 0x00000020, +}; + +DEFINE_ENUM_FLAG_OPERATORS(DEF) // Internal trigger codes -#define DRT_BEFORE_LAYOUT 0 -#define DRT_AFTER_LAYOUT 1 -#define DRT_USER_CLICK 2 -#define DRT_USER_CLICK_RELEASE 3 -#define DRT_USER_MOVEMENT 4 -#define DRT_REFRESH 5 -#define DRT_GOT_FOCUS 6 -#define DRT_LOST_FOCUS 7 -#define DRT_LEAVING_PAGE 8 -#define DRT_PAGE_PROCESSED 9 -#define DRT_MAX 10 +enum class DRT : LONG { + NIL = 0, + BEFORE_LAYOUT = 0, + AFTER_LAYOUT = 1, + USER_CLICK = 2, + USER_CLICK_RELEASE = 3, + USER_MOVEMENT = 4, + REFRESH = 5, + GOT_FOCUS = 6, + LOST_FOCUS = 7, + LEAVING_PAGE = 8, + PAGE_PROCESSED = 9, + MAX = 10, +}; // Document flags -#define DCF_EDIT 0x00000001 -#define DCF_OVERWRITE 0x00000002 -#define DCF_NO_SYS_KEYS 0x00000004 -#define DCF_DISABLED 0x00000008 -#define DCF_NO_SCROLLBARS 0x00000010 -#define DCF_NO_LAYOUT_MSG 0x00000020 -#define DCF_UNRESTRICTED 0x00000040 - -// Border edge flags. - -#define DBE_TOP 0x00000001 -#define DBE_LEFT 0x00000002 -#define DBE_RIGHT 0x00000004 -#define DBE_BOTTOM 0x00000008 - -// These are document style flags, as used in the DocStyle structure - -#define FSO_BOLD 0x00000001 -#define FSO_ITALIC 0x00000002 -#define FSO_UNDERLINE 0x00000004 -#define FSO_PREFORMAT 0x00000008 -#define FSO_CAPS 0x00000010 -#define FSO_STYLES 0x00000017 -#define FSO_ALIGN_RIGHT 0x00000020 -#define FSO_ALIGN_CENTER 0x00000040 -#define FSO_ANCHOR 0x00000080 -#define FSO_NO_WRAP 0x00000100 - -#define VER_DOCSTYLE 1 - -typedef struct DocStyleV1 { - LONG Version; // Version of this DocStyle structure - objDocument * Document; // The document object that this style originates from - objFont * Font; // Pointer to the current font object. Indicates face, style etc, but not simple attributes like colour - struct RGB8 FontColour; // Foreground colour (colour of the font) - struct RGB8 FontUnderline; // Underline colour for the font, if active - LONG StyleFlags; // Font style flags (FSO) -} DOCSTYLE; - -struct deLinkActivated { - struct KeyStore * Parameters; // All key-values associated with the link. -}; - -struct escFont { - WORD Index; // Font lookup - WORD Options; // FSO flags - struct RGB8 Colour; // Font colour +enum class DCF : ULONG { + NIL = 0, + EDIT = 0x00000001, + OVERWRITE = 0x00000002, + NO_SYS_KEYS = 0x00000004, + DISABLED = 0x00000008, + NO_LAYOUT_MSG = 0x00000010, + UNRESTRICTED = 0x00000020, }; -typedef struct escFont escFont; -struct SurfaceClip { - struct SurfaceClip * Next; - LONG Left; - LONG Top; - LONG Right; - LONG Bottom; -}; +DEFINE_ENUM_FLAG_OPERATORS(DCF) -struct style_status { - struct escFont FontStyle; - struct process_table * Table; - struct escList * List; - char Face[36]; - WORD Point; - UBYTE FontChange:1; // A major font change has occurred (e.g. face, point size) - UBYTE StyleChange:1; // A minor style change has occurred (e.g. font colour) -}; +// These are document style flags, as used in the DocStyle structure -struct docdraw { - APTR Object; - OBJECTID ID; +enum class FSO : ULONG { + NIL = 0, + BOLD = 0x00000001, + ITALIC = 0x00000002, + UNDERLINE = 0x00000004, + STYLES = 0x00000007, + PREFORMAT = 0x00000008, + ALIGN_RIGHT = 0x00000010, + ALIGN_CENTER = 0x00000020, + NO_WRAP = 0x00000040, }; -struct DocTrigger { - struct DocTrigger * Next; - struct DocTrigger * Prev; - FUNCTION Function; -}; +DEFINE_ENUM_FLAG_OPERATORS(FSO) // Document class definition @@ -130,7 +96,6 @@ struct DocTrigger { #define MT_docFeedParser -1 #define MT_docSelectLink -2 -#define MT_docApplyFontStyle -3 #define MT_docFindIndex -4 #define MT_docInsertXML -5 #define MT_docRemoveContent -6 @@ -145,90 +110,84 @@ struct DocTrigger { struct docFeedParser { CSTRING String; }; struct docSelectLink { LONG Index; CSTRING Name; }; -struct docApplyFontStyle { struct DocStyleV1 * Style; objFont * Font; }; struct docFindIndex { CSTRING Name; LONG Start; LONG End; }; struct docInsertXML { CSTRING XML; LONG Index; }; struct docRemoveContent { LONG Start; LONG End; }; -struct docInsertText { CSTRING Text; LONG Index; LONG Preformat; }; +struct docInsertText { CSTRING Text; LONG Index; LONG Char; LONG Preformat; }; struct docCallFunction { CSTRING Function; struct ScriptArg * Args; LONG TotalArgs; }; -struct docAddListener { LONG Trigger; FUNCTION * Function; }; +struct docAddListener { DRT Trigger; FUNCTION * Function; }; struct docRemoveListener { LONG Trigger; FUNCTION * Function; }; struct docShowIndex { CSTRING Name; }; struct docHideIndex { CSTRING Name; }; struct docEdit { CSTRING Name; LONG Flags; }; -struct docReadContent { LONG Format; LONG Start; LONG End; STRING Result; }; +struct docReadContent { DATA Format; LONG Start; LONG End; STRING Result; }; -INLINE ERROR docFeedParser(APTR Ob, CSTRING String) { +INLINE ERR docFeedParser(APTR Ob, CSTRING String) noexcept { struct docFeedParser args = { String }; return(Action(MT_docFeedParser, (OBJECTPTR)Ob, &args)); } -INLINE ERROR docSelectLink(APTR Ob, LONG Index, CSTRING Name) { +INLINE ERR docSelectLink(APTR Ob, LONG Index, CSTRING Name) noexcept { struct docSelectLink args = { Index, Name }; return(Action(MT_docSelectLink, (OBJECTPTR)Ob, &args)); } -INLINE ERROR docApplyFontStyle(APTR Ob, struct DocStyleV1 * Style, objFont * Font) { - struct docApplyFontStyle args = { Style, Font }; - return(Action(MT_docApplyFontStyle, (OBJECTPTR)Ob, &args)); -} - -INLINE ERROR docFindIndex(APTR Ob, CSTRING Name, LONG * Start, LONG * End) { - struct docFindIndex args = { Name, 0, 0 }; - ERROR error = Action(MT_docFindIndex, (OBJECTPTR)Ob, &args); +INLINE ERR docFindIndex(APTR Ob, CSTRING Name, LONG * Start, LONG * End) noexcept { + struct docFindIndex args = { Name, (LONG)0, (LONG)0 }; + ERR error = Action(MT_docFindIndex, (OBJECTPTR)Ob, &args); if (Start) *Start = args.Start; if (End) *End = args.End; return(error); } -INLINE ERROR docInsertXML(APTR Ob, CSTRING XML, LONG Index) { +INLINE ERR docInsertXML(APTR Ob, CSTRING XML, LONG Index) noexcept { struct docInsertXML args = { XML, Index }; return(Action(MT_docInsertXML, (OBJECTPTR)Ob, &args)); } -INLINE ERROR docRemoveContent(APTR Ob, LONG Start, LONG End) { +INLINE ERR docRemoveContent(APTR Ob, LONG Start, LONG End) noexcept { struct docRemoveContent args = { Start, End }; return(Action(MT_docRemoveContent, (OBJECTPTR)Ob, &args)); } -INLINE ERROR docInsertText(APTR Ob, CSTRING Text, LONG Index, LONG Preformat) { - struct docInsertText args = { Text, Index, Preformat }; +INLINE ERR docInsertText(APTR Ob, CSTRING Text, LONG Index, LONG Char, LONG Preformat) noexcept { + struct docInsertText args = { Text, Index, Char, Preformat }; return(Action(MT_docInsertText, (OBJECTPTR)Ob, &args)); } -INLINE ERROR docCallFunction(APTR Ob, CSTRING Function, struct ScriptArg * Args, LONG TotalArgs) { +INLINE ERR docCallFunction(APTR Ob, CSTRING Function, struct ScriptArg * Args, LONG TotalArgs) noexcept { struct docCallFunction args = { Function, Args, TotalArgs }; return(Action(MT_docCallFunction, (OBJECTPTR)Ob, &args)); } -INLINE ERROR docAddListener(APTR Ob, LONG Trigger, FUNCTION * Function) { +INLINE ERR docAddListener(APTR Ob, DRT Trigger, FUNCTION * Function) noexcept { struct docAddListener args = { Trigger, Function }; return(Action(MT_docAddListener, (OBJECTPTR)Ob, &args)); } -INLINE ERROR docRemoveListener(APTR Ob, LONG Trigger, FUNCTION * Function) { +INLINE ERR docRemoveListener(APTR Ob, LONG Trigger, FUNCTION * Function) noexcept { struct docRemoveListener args = { Trigger, Function }; return(Action(MT_docRemoveListener, (OBJECTPTR)Ob, &args)); } -INLINE ERROR docShowIndex(APTR Ob, CSTRING Name) { +INLINE ERR docShowIndex(APTR Ob, CSTRING Name) noexcept { struct docShowIndex args = { Name }; return(Action(MT_docShowIndex, (OBJECTPTR)Ob, &args)); } -INLINE ERROR docHideIndex(APTR Ob, CSTRING Name) { +INLINE ERR docHideIndex(APTR Ob, CSTRING Name) noexcept { struct docHideIndex args = { Name }; return(Action(MT_docHideIndex, (OBJECTPTR)Ob, &args)); } -INLINE ERROR docEdit(APTR Ob, CSTRING Name, LONG Flags) { +INLINE ERR docEdit(APTR Ob, CSTRING Name, LONG Flags) noexcept { struct docEdit args = { Name, Flags }; return(Action(MT_docEdit, (OBJECTPTR)Ob, &args)); } -INLINE ERROR docReadContent(APTR Ob, LONG Format, LONG Start, LONG End, STRING * Result) { - struct docReadContent args = { Format, Start, End, 0 }; - ERROR error = Action(MT_docReadContent, (OBJECTPTR)Ob, &args); +INLINE ERR docReadContent(APTR Ob, DATA Format, LONG Start, LONG End, STRING * Result) noexcept { + struct docReadContent args = { Format, Start, End, (STRING)0 }; + ERR error = Action(MT_docReadContent, (OBJECTPTR)Ob, &args); if (Result) *Result = args.Result; return(error); } @@ -241,83 +200,138 @@ class objDocument : public BaseClass { using create = pf::Create; - LARGE EventMask; // Specifies events that need to be reported from the Document object. - STRING Description; // A description of the document, provided by its author. - STRING FontFace; // Defines the default font face. - STRING Title; // The title of the document. - STRING Author; // The author(s) of the document. - STRING Copyright; // Copyright information for the document. - STRING Keywords; // Includes keywords declared by the source document. - OBJECTID TabFocusID; // Allows the user to hit the tab key to focus on other GUI objects. - OBJECTID SurfaceID; // Defines the surface area for document graphics. - OBJECTID FocusID; // Refers to the object that will be monitored for user focusing. - LONG Flags; // Optional flags that affect object behaviour. - LONG LeftMargin; // Defines the amount of whitespace to leave at the left of the page. - LONG TopMargin; // Defines the amount of white-space to leave at the top of the document page. - LONG RightMargin; // Defines the amount of white-space to leave at the right side of the document page. - LONG BottomMargin; // Defines the amount of whitespace to leave at the bottom of the document page. - LONG FontSize; // The point-size of the default font. - LONG PageHeight; // Measures the page height of the document, in pixels. - LONG BorderEdge; // Border edge flags. - LONG LineHeight; // Default line height (taken as an average) for all text on the page. - ERROR Error; // The most recently generated error code. - struct RGB8 FontColour; // Default font colour. - struct RGB8 Highlight; // Defines the colour used to highlight document. - struct RGB8 Background; // Optional background colour for the document. - struct RGB8 CursorColour; // The colour used for the document cursor. - struct RGB8 LinkColour; // Default font colour for hyperlinks. - struct RGB8 VLinkColour; // Default font colour for visited hyperlinks. - struct RGB8 SelectColour; // Default font colour to use when hyperlinks are selected. - struct RGB8 Border; // Border colour around the document's surface. + STRING Description; // A description of the document, provided by its author. + STRING Title; // The title of the document. + STRING Author; // The author(s) of the document. + STRING Copyright; // Copyright information for the document. + STRING Keywords; // Includes keywords declared by the source document. + objVectorViewport * Viewport; // A client-specific viewport that will host the document graphics. + objVectorViewport * Focus; // Refers to the object that will be monitored for user focusing. + objVectorViewport * View; // An internally created viewport that hosts the Page + objVectorViewport * Page; // The Page contains the document content and is hosted by the View + OBJECTID TabFocusID; // Allows the user to hit the tab key to focus on other GUI objects. + DEF EventMask; // Specifies events that need to be reported from the Document object. + DCF Flags; // Optional flags that affect object behaviour. + LONG PageHeight; // Measures the page height of the document, in pixels. + ERR Error; // The most recently generated error code. // Action stubs - inline ERROR activate() { return Action(AC_Activate, this, NULL); } - inline ERROR clear() { return Action(AC_Clear, this, NULL); } - inline ERROR clipboard(LONG Mode) { + inline ERR activate() noexcept { return Action(AC_Activate, this, NULL); } + inline ERR clear() noexcept { return Action(AC_Clear, this, NULL); } + inline ERR clipboard(CLIPMODE Mode) noexcept { struct acClipboard args = { Mode }; return Action(AC_Clipboard, this, &args); } - inline ERROR dataFeed(OBJECTID ObjectID, LONG Datatype, const void *Buffer, LONG Size) { - struct acDataFeed args = { { ObjectID }, { Datatype }, Buffer, Size }; + inline ERR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) noexcept { + struct acDataFeed args = { Object, Datatype, Buffer, Size }; return Action(AC_DataFeed, this, &args); } - inline ERROR disable() { return Action(AC_Disable, this, NULL); } - inline ERROR draw() { return Action(AC_Draw, this, NULL); } - inline ERROR drawArea(LONG X, LONG Y, LONG Width, LONG Height) { + inline ERR disable() noexcept { return Action(AC_Disable, this, NULL); } + inline ERR draw() noexcept { return Action(AC_Draw, this, NULL); } + inline ERR drawArea(LONG X, LONG Y, LONG Width, LONG Height) noexcept { struct acDraw args = { X, Y, Width, Height }; return Action(AC_Draw, this, &args); } - inline ERROR enable() { return Action(AC_Enable, this, NULL); } - inline ERROR focus() { return Action(AC_Focus, this, NULL); } - inline ERROR getVar(CSTRING FieldName, STRING Buffer, LONG Size) { + inline ERR enable() noexcept { return Action(AC_Enable, this, NULL); } + inline ERR focus() noexcept { return Action(AC_Focus, this, NULL); } + inline ERR getVar(CSTRING FieldName, STRING Buffer, LONG Size) noexcept { struct acGetVar args = { FieldName, Buffer, Size }; - ERROR error = Action(AC_GetVar, this, &args); - if ((error) and (Buffer)) Buffer[0] = 0; + auto error = Action(AC_GetVar, this, &args); + if ((error != ERR::Okay) and (Buffer)) Buffer[0] = 0; return error; } - inline ERROR init() { return InitObject(this); } - inline ERROR refresh() { return Action(AC_Refresh, this, NULL); } - inline ERROR saveToObject(OBJECTID DestID, CLASSID ClassID) { - struct acSaveToObject args = { { DestID }, { ClassID } }; + inline ERR init() noexcept { return InitObject(this); } + inline ERR refresh() noexcept { return Action(AC_Refresh, this, NULL); } + inline ERR saveToObject(OBJECTPTR Dest, CLASSID ClassID = 0) noexcept { + struct acSaveToObject args = { Dest, { ClassID } }; return Action(AC_SaveToObject, this, &args); } - inline ERROR scrollToPoint(DOUBLE X, DOUBLE Y, DOUBLE Z, LONG Flags) { + inline ERR scrollToPoint(DOUBLE X, DOUBLE Y, DOUBLE Z, STP Flags) noexcept { struct acScrollToPoint args = { X, Y, Z, Flags }; return Action(AC_ScrollToPoint, this, &args); } - inline ERROR acSetVar(CSTRING FieldName, CSTRING Value) { + inline ERR acSetVar(CSTRING FieldName, CSTRING Value) noexcept { struct acSetVar args = { FieldName, Value }; return Action(AC_SetVar, this, &args); } -}; -extern struct DocumentBase *DocumentBase; -struct DocumentBase { - LONG (*_CharLength)(objDocument * Document, LONG Index); + // Customised field setting + + inline ERR setViewport(objVectorViewport * Value) noexcept { + auto target = this; + auto field = &this->Class->Dictionary[23]; + return field->WriteValue(target, field, 0x08000301, Value, 1); + } + + inline ERR setFocus(objVectorViewport * Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; + this->Focus = Value; + return ERR::Okay; + } + + inline ERR setTabFocus(OBJECTID Value) noexcept { + this->TabFocusID = Value; + return ERR::Okay; + } + + inline ERR setEventMask(const DEF Value) noexcept { + this->EventMask = Value; + return ERR::Okay; + } + + inline ERR setFlags(const DCF Value) noexcept { + auto target = this; + auto field = &this->Class->Dictionary[3]; + return field->WriteValue(target, field, FD_LONG, &Value, 1); + } + + inline ERR setClientScript(OBJECTPTR Value) noexcept { + auto target = this; + auto field = &this->Class->Dictionary[18]; + return field->WriteValue(target, field, 0x08000401, Value, 1); + } + + inline ERR setEventCallback(FUNCTION Value) noexcept { + auto target = this; + auto field = &this->Class->Dictionary[25]; + return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); + } + + template inline ERR setPath(T && Value) noexcept { + auto target = this; + auto field = &this->Class->Dictionary[13]; + return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); + } + + template inline ERR setOrigin(T && Value) noexcept { + auto target = this; + auto field = &this->Class->Dictionary[7]; + return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); + } + + inline ERR setPageWidth(const LONG Value) noexcept { + auto target = this; + auto field = &this->Class->Dictionary[10]; + Variable var(Value); + return field->WriteValue(target, field, FD_VARIABLE, &var, 1); + } + + template inline ERR setPretext(T && Value) noexcept { + auto target = this; + auto field = &this->Class->Dictionary[20]; + return field->WriteValue(target, field, 0x08800200, to_cstring(Value), 1); + } + }; -#ifndef PRV_DOCUMENT_MODULE -inline LONG docCharLength(objDocument * Document, LONG Index) { return DocumentBase->_CharLength(Document,Index); } -#endif +namespace fl { + using namespace pf; + +constexpr FieldValue EventCallback(const FUNCTION &Value) { return FieldValue(FID_EventCallback, &Value); } +constexpr FieldValue EventCallback(APTR Value) { return FieldValue(FID_EventCallback, Value); } +constexpr FieldValue EventMask(DEF Value) { return FieldValue(FID_EventMask, LONG(Value)); } +constexpr FieldValue Flags(DCF Value) { return FieldValue(FID_Flags, LONG(Value)); } + +} diff --git a/include/parasol/modules/fluid.h b/include/parasol/modules/fluid.h index b326fd101..9f39ae4e1 100644 --- a/include/parasol/modules/fluid.h +++ b/include/parasol/modules/fluid.h @@ -1,7 +1,7 @@ #pragma once // Name: fluid.h -// Copyright: Paul Manias © 2006-2023 +// Copyright: Paul Manias © 2006-2024 // Generator: idl-c #include diff --git a/include/parasol/modules/font.h b/include/parasol/modules/font.h index 98ef10320..027b79b55 100644 --- a/include/parasol/modules/font.h +++ b/include/parasol/modules/font.h @@ -1,7 +1,7 @@ #pragma once // Name: font.h -// Copyright: Paul Manias © 1998-2023 +// Copyright: Paul Manias © 1998-2024 // Generator: idl-c #include @@ -16,26 +16,37 @@ class objFont; enum class FTF : ULONG { NIL = 0, - PREFER_SCALED = 0x00000001, - PREFER_FIXED = 0x00000002, - REQUIRE_SCALED = 0x00000004, - REQUIRE_FIXED = 0x00000008, - ANTIALIAS = 0x00000010, - SMOOTH = 0x00000010, - HEAVY_LINE = 0x00000020, - QUICK_ALIAS = 0x00000040, - CHAR_CLIP = 0x00000080, - BASE_LINE = 0x00000100, - ALLOW_SCALE = 0x00000200, - NO_BLEND = 0x00000400, - SCALABLE = 0x10000000, + HEAVY_LINE = 0x00000001, + BASE_LINE = 0x00000002, BOLD = 0x20000000, ITALIC = 0x40000000, - KERNING = 0x80000000, }; DEFINE_ENUM_FLAG_OPERATORS(FTF) +// Result flags for the SelectFont() function. + +enum class FMETA : ULONG { + NIL = 0, + SCALED = 0x00000001, + VARIABLE = 0x00000002, + HINT_NORMAL = 0x00000004, + HINT_LIGHT = 0x00000008, + HINT_INTERNAL = 0x00000010, + HIDDEN = 0x00000020, +}; + +DEFINE_ENUM_FLAG_OPERATORS(FMETA) + +// Force hinting options for a font. + +enum class HINT : BYTE { + NIL = 0, + NORMAL = 1, + INTERNAL = 2, + LIGHT = 3, +}; + // Options for the StringSize() function. #define FSS_ALL -1 @@ -44,11 +55,14 @@ DEFINE_ENUM_FLAG_OPERATORS(FTF) struct FontList { struct FontList * Next; // Pointer to the next entry in the list. STRING Name; // The name of the font face. + STRING Alias; // Reference to another font Name if this is an alias. LONG * Points; // Pointer to an array of fixed point sizes supported by the font. STRING Styles; // Supported styles are listed here in CSV format. + STRING Axes; // For variable fonts, lists all supported axis codes in CSV format BYTE Scalable; // TRUE if the font is scalable. - BYTE Reserved1; // Do not use. - WORD Reserved2; // Do not use. + BYTE Variable; // TRUE if the font has variable metrics. + HINT Hinting; // Hinting options + BYTE Hidden; // TRUE if the font should be hidden from user font lists. }; // Font class definition @@ -62,250 +76,197 @@ class objFont : public BaseClass { using create = pf::Create; - DOUBLE Angle; // A rotation angle to use when drawing scalable fonts. - DOUBLE Point; // The point size of a font. - DOUBLE StrokeSize; // The strength of stroked outlines is defined here. - objBitmap * Bitmap; // The destination Bitmap to use when drawing a font. - STRING String; // The string to use when drawing a Font. - STRING Path; // The path to a font file. - STRING Style; // Determines font styling. - STRING Face; // The name of a font face that is to be loaded on initialisation. - ERROR (*WrapCallback)(objFont *, LONG *, LONG *); // The routine defined here will be called when the wordwrap boundary is encountered. - APTR EscapeCallback; // The routine defined here will be called when escape characters are encountered. - APTR UserData; // Optional storage variable for user data; ignored by the Font class. - struct RGB8 Outline; // Defines the outline colour around a font. - struct RGB8 Underline; // Enables font underlining when set. - struct RGB8 Colour; // The font colour in RGB format. - FTF Flags; // Optional flags. - LONG Gutter; // The 'external leading' value, measured in pixels. Applies to fixed fonts only. - LONG GlyphSpacing; // The amount of spacing between each character. - LONG LineSpacing; // The amount of spacing between each line. - LONG X; // The starting horizontal position when drawing the font string. - LONG Y; // The starting vertical position when drawing the font string. - LONG TabSize; // Defines the tab size to use when drawing and manipulating a font string. - LONG TotalChars; // Reflects the total number of character glyphs that are available by the font object. - LONG WrapEdge; // Enables word wrapping at a given boundary. - LONG FixedWidth; // Forces a fixed pixel width to use for all glyphs. - LONG Height; // The point size of the font, expressed in pixels. - LONG Leading; // 'Internal leading' measured in pixels. Applies to fixed fonts only. - LONG MaxHeight; // The maximum possible pixel height per character. - ALIGN Align; // Sets the position of a font string to an abstract alignment. - LONG AlignWidth; // The width to use when aligning the font string. - LONG AlignHeight; // The height to use when aligning the font string. - LONG Ascent; // The total number of pixels above the baseline. - LONG EndX; // Indicates the final horizontal coordinate after completing a draw operation. - LONG EndY; // Indicates the final vertical coordinate after completing a draw operation. - LONG VDPI; // Defines the vertical dots-per-inch of the target device. - LONG HDPI; // Defines the horizontal dots-per-inch of the target device. + DOUBLE Point; // The point size of a font. + DOUBLE GlyphSpacing; // Adjusts the amount of spacing between each character. + objBitmap * Bitmap; // The destination Bitmap to use when drawing a font. + STRING String; // The string to use when drawing a Font. + STRING Path; // The path to a font file. + STRING Style; // Determines font styling. + STRING Face; // The name of a font face that is to be loaded on initialisation. + struct RGB8 Outline; // Defines the outline colour around a font. + struct RGB8 Underline; // Enables font underlining when set. + struct RGB8 Colour; // The font colour in RGB format. + FTF Flags; // Optional flags. + LONG Gutter; // The 'external leading' value, measured in pixels. Applies to fixed fonts only. + LONG LineSpacing; // The amount of spacing between each line. + LONG X; // The starting horizontal position when drawing the font string. + LONG Y; // The starting vertical position when drawing the font string. + LONG TabSize; // Defines the tab size to use when drawing and manipulating a font string. + LONG WrapEdge; // Enables word wrapping at a given boundary. + LONG FixedWidth; // Forces a fixed pixel width to use for all glyphs. + LONG Height; // The point size of the font, expressed in pixels. + LONG Leading; // 'Internal leading' measured in pixels. Applies to fixed fonts only. + LONG MaxHeight; // The maximum possible pixel height per character. + ALIGN Align; // Sets the position of a font string to an abstract alignment. + LONG AlignWidth; // The width to use when aligning the font string. + LONG AlignHeight; // The height to use when aligning the font string. + LONG Ascent; // The total number of pixels above the baseline. + LONG EndX; // Indicates the final horizontal coordinate after completing a draw operation. + LONG EndY; // Indicates the final vertical coordinate after completing a draw operation. // Action stubs - inline ERROR draw() { return Action(AC_Draw, this, NULL); } - inline ERROR drawArea(LONG X, LONG Y, LONG Width, LONG Height) { + inline ERR draw() noexcept { return Action(AC_Draw, this, NULL); } + inline ERR drawArea(LONG X, LONG Y, LONG Width, LONG Height) noexcept { struct acDraw args = { X, Y, Width, Height }; return Action(AC_Draw, this, &args); } - inline ERROR init() { return InitObject(this); } + inline ERR init() noexcept { return InitObject(this); } // Customised field setting - inline ERROR setAngle(const DOUBLE Value) { - this->Angle = Value; - return ERR_Okay; - } - - inline ERROR setPoint(const DOUBLE Value) { + inline ERR setPoint(const DOUBLE Value) noexcept { auto target = this; - auto field = &this->Class->Dictionary[12]; - Variable var(Value); - return field->WriteValue(target, field, FD_VARIABLE, &var, 1); + auto field = &this->Class->Dictionary[11]; + return field->WriteValue(target, field, FD_DOUBLE, &Value, 1); } - inline ERROR setStrokeSize(const DOUBLE Value) { - this->StrokeSize = Value; - return ERR_Okay; + inline ERR setGlyphSpacing(const DOUBLE Value) noexcept { + this->GlyphSpacing = Value; + return ERR::Okay; } - inline ERROR setBitmap(objBitmap * Value) { + inline ERR setBitmap(objBitmap * Value) noexcept { this->Bitmap = Value; - return ERR_Okay; + return ERR::Okay; } - template inline ERROR setString(T && Value) { + template inline ERR setString(T && Value) noexcept { auto target = this; - auto field = &this->Class->Dictionary[15]; + auto field = &this->Class->Dictionary[14]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setPath(T && Value) { + template inline ERR setPath(T && Value) noexcept { auto target = this; - auto field = &this->Class->Dictionary[30]; + auto field = &this->Class->Dictionary[25]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setStyle(T && Value) { + template inline ERR setStyle(T && Value) noexcept { auto target = this; - auto field = &this->Class->Dictionary[13]; + auto field = &this->Class->Dictionary[12]; return field->WriteValue(target, field, 0x08800500, to_cstring(Value), 1); } - template inline ERROR setFace(T && Value) { + template inline ERR setFace(T && Value) noexcept { auto target = this; - auto field = &this->Class->Dictionary[27]; + auto field = &this->Class->Dictionary[23]; return field->WriteValue(target, field, 0x08800500, to_cstring(Value), 1); } - inline ERROR setEscapeCallback(APTR Value) { - this->EscapeCallback = Value; - return ERR_Okay; - } - - inline ERROR setUserData(APTR Value) { - this->UserData = Value; - return ERR_Okay; - } - - inline ERROR setOutline(const struct RGB8 Value) { + inline ERR setOutline(const struct RGB8 Value) noexcept { this->Outline = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setUnderline(const struct RGB8 Value) { + inline ERR setUnderline(const struct RGB8 Value) noexcept { this->Underline = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setColour(const struct RGB8 Value) { + inline ERR setColour(const struct RGB8 Value) noexcept { this->Colour = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFlags(const FTF Value) { + inline ERR setFlags(const FTF Value) noexcept { auto target = this; - auto field = &this->Class->Dictionary[10]; + auto field = &this->Class->Dictionary[9]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setGutter(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setGutter(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Gutter = Value; - return ERR_Okay; - } - - inline ERROR setGlyphSpacing(const LONG Value) { - this->GlyphSpacing = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setLineSpacing(const LONG Value) { + inline ERR setLineSpacing(const LONG Value) noexcept { this->LineSpacing = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setX(const LONG Value) { + inline ERR setX(const LONG Value) noexcept { this->X = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setY(const LONG Value) { + inline ERR setY(const LONG Value) noexcept { this->Y = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setTabSize(const LONG Value) { + inline ERR setTabSize(const LONG Value) noexcept { this->TabSize = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setWrapEdge(const LONG Value) { + inline ERR setWrapEdge(const LONG Value) noexcept { this->WrapEdge = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFixedWidth(const LONG Value) { + inline ERR setFixedWidth(const LONG Value) noexcept { this->FixedWidth = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setHeight(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setHeight(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Height = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setMaxHeight(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setMaxHeight(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->MaxHeight = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setAlign(const ALIGN Value) { + inline ERR setAlign(const ALIGN Value) noexcept { this->Align = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setAlignWidth(const LONG Value) { + inline ERR setAlignWidth(const LONG Value) noexcept { this->AlignWidth = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setAlignHeight(const LONG Value) { + inline ERR setAlignHeight(const LONG Value) noexcept { this->AlignHeight = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setEndX(const LONG Value) { + inline ERR setEndX(const LONG Value) noexcept { this->EndX = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setEndY(const LONG Value) { + inline ERR setEndY(const LONG Value) noexcept { this->EndY = Value; - return ERR_Okay; - } - - inline ERROR setVDPI(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; - this->VDPI = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setHDPI(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; - this->HDPI = Value; - return ERR_Okay; - } - - inline ERROR setBold(const LONG Value) { + inline ERR setBold(const LONG Value) noexcept { auto target = this; - auto field = &this->Class->Dictionary[24]; + auto field = &this->Class->Dictionary[20]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - template inline ERROR setEscapeChar(T && Value) { - auto target = this; - auto field = &this->Class->Dictionary[38]; - return field->WriteValue(target, field, 0x08800308, to_cstring(Value), 1); - } - - inline ERROR setItalic(const LONG Value) { + inline ERR setItalic(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[5]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setOpacity(const DOUBLE Value) { + inline ERR setOpacity(const DOUBLE Value) noexcept { auto target = this; - auto field = &this->Class->Dictionary[22]; + auto field = &this->Class->Dictionary[18]; return field->WriteValue(target, field, FD_DOUBLE, &Value, 1); } - inline ERROR setTabs(const WORD * Value, LONG Elements) { - auto target = this; - auto field = &this->Class->Dictionary[31]; - return field->WriteValue(target, field, 0x00401308, Value, Elements); - } - }; #ifdef PARASOL_STATIC @@ -316,44 +277,32 @@ class objFont : public BaseClass { struct FontBase { #ifndef PARASOL_STATIC - ERROR (*_GetList)(struct FontList ** Result); + ERR (*_GetList)(struct FontList ** Result); LONG (*_StringWidth)(objFont * Font, CSTRING String, LONG Chars); - void (*_StringSize)(objFont * Font, CSTRING String, LONG Chars, LONG Wrap, LONG * Width, LONG * Rows); - ERROR (*_ConvertCoords)(objFont * Font, CSTRING String, LONG X, LONG Y, LONG * Column, LONG * Row, LONG * ByteColumn, LONG * BytePos, LONG * CharX); - LONG (*_CharWidth)(objFont * Font, ULONG Char, ULONG KChar, LONG * Kerning); - DOUBLE (*_SetDefaultSize)(DOUBLE Size); - APTR (*_FreetypeHandle)(void); - ERROR (*_InstallFont)(CSTRING Files); - ERROR (*_RemoveFont)(CSTRING Name); - ERROR (*_SelectFont)(CSTRING Name, CSTRING Style, LONG Point, FTF Flags, CSTRING * Path); + LONG (*_CharWidth)(objFont * Font, ULONG Char); + ERR (*_RefreshFonts)(void); + ERR (*_SelectFont)(CSTRING Name, CSTRING Style, CSTRING * Path, FMETA * Meta); + ERR (*_ResolveFamilyName)(CSTRING String, CSTRING * Result); #endif // PARASOL_STATIC }; #ifndef PRV_FONT_MODULE #ifndef PARASOL_STATIC extern struct FontBase *FontBase; -inline ERROR fntGetList(struct FontList ** Result) { return FontBase->_GetList(Result); } +inline ERR fntGetList(struct FontList ** Result) { return FontBase->_GetList(Result); } inline LONG fntStringWidth(objFont * Font, CSTRING String, LONG Chars) { return FontBase->_StringWidth(Font,String,Chars); } -inline void fntStringSize(objFont * Font, CSTRING String, LONG Chars, LONG Wrap, LONG * Width, LONG * Rows) { return FontBase->_StringSize(Font,String,Chars,Wrap,Width,Rows); } -inline ERROR fntConvertCoords(objFont * Font, CSTRING String, LONG X, LONG Y, LONG * Column, LONG * Row, LONG * ByteColumn, LONG * BytePos, LONG * CharX) { return FontBase->_ConvertCoords(Font,String,X,Y,Column,Row,ByteColumn,BytePos,CharX); } -inline LONG fntCharWidth(objFont * Font, ULONG Char, ULONG KChar, LONG * Kerning) { return FontBase->_CharWidth(Font,Char,KChar,Kerning); } -inline DOUBLE fntSetDefaultSize(DOUBLE Size) { return FontBase->_SetDefaultSize(Size); } -inline APTR fntFreetypeHandle(void) { return FontBase->_FreetypeHandle(); } -inline ERROR fntInstallFont(CSTRING Files) { return FontBase->_InstallFont(Files); } -inline ERROR fntRemoveFont(CSTRING Name) { return FontBase->_RemoveFont(Name); } -inline ERROR fntSelectFont(CSTRING Name, CSTRING Style, LONG Point, FTF Flags, CSTRING * Path) { return FontBase->_SelectFont(Name,Style,Point,Flags,Path); } +inline LONG fntCharWidth(objFont * Font, ULONG Char) { return FontBase->_CharWidth(Font,Char); } +inline ERR fntRefreshFonts(void) { return FontBase->_RefreshFonts(); } +inline ERR fntSelectFont(CSTRING Name, CSTRING Style, CSTRING * Path, FMETA * Meta) { return FontBase->_SelectFont(Name,Style,Path,Meta); } +inline ERR fntResolveFamilyName(CSTRING String, CSTRING * Result) { return FontBase->_ResolveFamilyName(String,Result); } #else extern "C" { -extern ERROR fntGetList(struct FontList ** Result); +extern ERR fntGetList(struct FontList ** Result); extern LONG fntStringWidth(objFont * Font, CSTRING String, LONG Chars); -extern void fntStringSize(objFont * Font, CSTRING String, LONG Chars, LONG Wrap, LONG * Width, LONG * Rows); -extern ERROR fntConvertCoords(objFont * Font, CSTRING String, LONG X, LONG Y, LONG * Column, LONG * Row, LONG * ByteColumn, LONG * BytePos, LONG * CharX); -extern LONG fntCharWidth(objFont * Font, ULONG Char, ULONG KChar, LONG * Kerning); -extern DOUBLE fntSetDefaultSize(DOUBLE Size); -extern APTR fntFreetypeHandle(void); -extern ERROR fntInstallFont(CSTRING Files); -extern ERROR fntRemoveFont(CSTRING Name); -extern ERROR fntSelectFont(CSTRING Name, CSTRING Style, LONG Point, FTF Flags, CSTRING * Path); +extern LONG fntCharWidth(objFont * Font, ULONG Char); +extern ERR fntRefreshFonts(void); +extern ERR fntSelectFont(CSTRING Name, CSTRING Style, CSTRING * Path, FMETA * Meta); +extern ERR fntResolveFamilyName(CSTRING String, CSTRING * Result); } #endif // PARASOL_STATIC #endif diff --git a/include/parasol/modules/http.h b/include/parasol/modules/http.h index 65439dac3..bd4ee60d8 100644 --- a/include/parasol/modules/http.h +++ b/include/parasol/modules/http.h @@ -1,7 +1,7 @@ #pragma once // Name: http.h -// Copyright: Paul Manias © 2005-2023 +// Copyright: Paul Manias © 2005-2024 // Generator: idl-c #include @@ -162,7 +162,7 @@ class objHTTP : public BaseClass { HOM ObjectMode; // The access mode used when passing data to a targeted object. HTF Flags; // Optional flags. HTS Status; // Indicates the HTTP status code returned on completion of an HTTP request. - ERROR Error; // The error code received for the most recently executed HTTP command. + ERR Error; // The error code received for the most recently executed HTTP command. DATA Datatype; // The default datatype format to use when passing data to a target object. HGS CurrentState; // Indicates the current state of an HTTP object during its interaction with an HTTP server. STRING ProxyServer; // The targeted HTTP server is specified here, either by name or IP address. @@ -171,223 +171,227 @@ class objHTTP : public BaseClass { // Action stubs - inline ERROR activate() { return Action(AC_Activate, this, NULL); } - inline ERROR deactivate() { return Action(AC_Deactivate, this, NULL); } - inline ERROR getVar(CSTRING FieldName, STRING Buffer, LONG Size) { + inline ERR activate() noexcept { return Action(AC_Activate, this, NULL); } + inline ERR deactivate() noexcept { return Action(AC_Deactivate, this, NULL); } + inline ERR getVar(CSTRING FieldName, STRING Buffer, LONG Size) noexcept { struct acGetVar args = { FieldName, Buffer, Size }; - ERROR error = Action(AC_GetVar, this, &args); - if ((error) and (Buffer)) Buffer[0] = 0; + auto error = Action(AC_GetVar, this, &args); + if ((error != ERR::Okay) and (Buffer)) Buffer[0] = 0; return error; } - inline ERROR init() { return InitObject(this); } - inline ERROR acSetVar(CSTRING FieldName, CSTRING Value) { + inline ERR init() noexcept { return InitObject(this); } + inline ERR acSetVar(CSTRING FieldName, CSTRING Value) noexcept { struct acSetVar args = { FieldName, Value }; return Action(AC_SetVar, this, &args); } - inline ERROR write(CPTR Buffer, LONG Size, LONG *Result = NULL) { - ERROR error; + inline ERR write(CPTR Buffer, LONG Size, LONG *Result = NULL) noexcept { struct acWrite write = { (BYTE *)Buffer, Size }; - if (!(error = Action(AC_Write, this, &write))) { + if (auto error = Action(AC_Write, this, &write); error IS ERR::Okay) { if (Result) *Result = write.Result; + return ERR::Okay; + } + else { + if (Result) *Result = 0; + return error; } - else if (Result) *Result = 0; - return error; } - inline ERROR write(std::string Buffer, LONG *Result = NULL) { - ERROR error; + inline ERR write(std::string Buffer, LONG *Result = NULL) noexcept { struct acWrite write = { (BYTE *)Buffer.c_str(), LONG(Buffer.size()) }; - if (!(error = Action(AC_Write, this, &write))) { + if (auto error = Action(AC_Write, this, &write); error IS ERR::Okay) { if (Result) *Result = write.Result; + return ERR::Okay; + } + else { + if (Result) *Result = 0; + return error; } - else if (Result) *Result = 0; - return error; } - inline LONG writeResult(CPTR Buffer, LONG Size) { + inline LONG writeResult(CPTR Buffer, LONG Size) noexcept { struct acWrite write = { (BYTE *)Buffer, Size }; - if (!Action(AC_Write, this, &write)) return write.Result; + if (Action(AC_Write, this, &write) IS ERR::Okay) return write.Result; else return 0; } // Customised field setting - inline ERROR setDataTimeout(const DOUBLE Value) { + inline ERR setDataTimeout(const DOUBLE Value) noexcept { this->DataTimeout = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setConnectTimeout(const DOUBLE Value) { + inline ERR setConnectTimeout(const DOUBLE Value) noexcept { this->ConnectTimeout = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setIndex(const LARGE Value) { + inline ERR setIndex(const LARGE Value) noexcept { this->Index = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setContentLength(const LARGE Value) { + inline ERR setContentLength(const LARGE Value) noexcept { this->ContentLength = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setSize(const LARGE Value) { + inline ERR setSize(const LARGE Value) noexcept { this->Size = Value; - return ERR_Okay; + return ERR::Okay; } - template inline ERROR setHost(T && Value) { + template inline ERR setHost(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[21]; return field->WriteValue(target, field, 0x08800500, to_cstring(Value), 1); } - template inline ERROR setRealm(T && Value) { + template inline ERR setRealm(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[11]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setPath(T && Value) { + template inline ERR setPath(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[23]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setOutputFile(T && Value) { + template inline ERR setOutputFile(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[2]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setInputFile(T && Value) { + template inline ERR setInputFile(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[0]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setUserAgent(T && Value) { + template inline ERR setUserAgent(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[31]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setUserData(APTR Value) { + inline ERR setUserData(APTR Value) noexcept { this->UserData = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setInputObject(const OBJECTID Value) { + inline ERR setInputObject(OBJECTID Value) noexcept { this->InputObjectID = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setOutputObject(const OBJECTID Value) { + inline ERR setOutputObject(OBJECTID Value) noexcept { this->OutputObjectID = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setMethod(const HTM Value) { + inline ERR setMethod(const HTM Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[5]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setPort(const LONG Value) { + inline ERR setPort(const LONG Value) noexcept { this->Port = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setObjectMode(const HOM Value) { + inline ERR setObjectMode(const HOM Value) noexcept { this->ObjectMode = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFlags(const HTF Value) { + inline ERR setFlags(const HTF Value) noexcept { this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setStatus(const HTS Value) { + inline ERR setStatus(const HTS Value) noexcept { this->Status = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setError(const ERROR Value) { + inline ERR setError(const ERR Value) noexcept { this->Error = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setDatatype(const DATA Value) { + inline ERR setDatatype(const DATA Value) noexcept { this->Datatype = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setCurrentState(const HGS Value) { + inline ERR setCurrentState(const HGS Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[17]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - template inline ERROR setProxyServer(T && Value) { + template inline ERR setProxyServer(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[34]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setProxyPort(const LONG Value) { + inline ERR setProxyPort(const LONG Value) noexcept { this->ProxyPort = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setBufferSize(const LONG Value) { + inline ERR setBufferSize(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[32]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setAuthCallback(FUNCTION Value) { + inline ERR setAuthCallback(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[26]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } - template inline ERROR setContentType(T && Value) { + template inline ERR setContentType(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[33]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setIncoming(FUNCTION Value) { + inline ERR setIncoming(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[19]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } - template inline ERROR setLocation(T && Value) { + template inline ERR setLocation(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[20]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setOutgoing(FUNCTION Value) { + inline ERR setOutgoing(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[14]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } - inline ERROR setStateChanged(FUNCTION Value) { + inline ERR setStateChanged(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[3]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } - template inline ERROR setUsername(T && Value) { + template inline ERR setUsername(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[38]; return field->WriteValue(target, field, 0x08800200, to_cstring(Value), 1); } - template inline ERROR setPassword(T && Value) { + template inline ERR setPassword(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[12]; return field->WriteValue(target, field, 0x08800200, to_cstring(Value), 1); diff --git a/include/parasol/modules/network.h b/include/parasol/modules/network.h index a394fb1eb..1a43b24de 100644 --- a/include/parasol/modules/network.h +++ b/include/parasol/modules/network.h @@ -1,7 +1,7 @@ #pragma once // Name: network.h -// Copyright: Paul Manias © 2005-2023 +// Copyright: Paul Manias © 2005-2024 // Generator: idl-c #include @@ -164,9 +164,9 @@ struct NetClient { struct csReadClientMsg { APTR Message; LONG Length; LONG Progress; LONG CRC; }; struct csWriteClientMsg { APTR Message; LONG Length; }; -INLINE ERROR csReadClientMsg(APTR Ob, APTR * Message, LONG * Length, LONG * Progress, LONG * CRC) { +INLINE ERR csReadClientMsg(APTR Ob, APTR * Message, LONG * Length, LONG * Progress, LONG * CRC) noexcept { struct csReadClientMsg args = { (APTR)0, (LONG)0, (LONG)0, (LONG)0 }; - ERROR error = Action(MT_csReadClientMsg, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_csReadClientMsg, (OBJECTPTR)Ob, &args); if (Message) *Message = args.Message; if (Length) *Length = args.Length; if (Progress) *Progress = args.Progress; @@ -174,7 +174,7 @@ INLINE ERROR csReadClientMsg(APTR Ob, APTR * Message, LONG * Length, LONG * Prog return(error); } -INLINE ERROR csWriteClientMsg(APTR Ob, APTR Message, LONG Length) { +INLINE ERR csWriteClientMsg(APTR Ob, APTR Message, LONG Length) noexcept { struct csWriteClientMsg args = { Message, Length }; return(Action(MT_csWriteClientMsg, (OBJECTPTR)Ob, &args)); } @@ -199,44 +199,49 @@ class objClientSocket : public BaseClass { // Action stubs - inline ERROR init() { return InitObject(this); } - template ERROR read(APTR Buffer, T Size, U *Result) { + inline ERR init() noexcept { return InitObject(this); } + template ERR read(APTR Buffer, T Size, U *Result) noexcept { static_assert(std::is_integral::value, "Result value must be an integer type"); static_assert(std::is_integral::value, "Size value must be an integer type"); - ERROR error; const LONG bytes = (Size > 0x7fffffff) ? 0x7fffffff : Size; struct acRead read = { (BYTE *)Buffer, bytes }; - if (!(error = Action(AC_Read, this, &read))) *Result = static_cast(read.Result); - else *Result = 0; - return error; + if (auto error = Action(AC_Read, this, &read); error IS ERR::Okay) { + *Result = static_cast(read.Result); + return ERR::Okay; + } + else { *Result = 0; return error; } } - template ERROR read(APTR Buffer, T Size) { + template ERR read(APTR Buffer, T Size) noexcept { static_assert(std::is_integral::value, "Size value must be an integer type"); const LONG bytes = (Size > 0x7fffffff) ? 0x7fffffff : Size; struct acRead read = { (BYTE *)Buffer, bytes }; return Action(AC_Read, this, &read); } - inline ERROR write(CPTR Buffer, LONG Size, LONG *Result = NULL) { - ERROR error; + inline ERR write(CPTR Buffer, LONG Size, LONG *Result = NULL) noexcept { struct acWrite write = { (BYTE *)Buffer, Size }; - if (!(error = Action(AC_Write, this, &write))) { + if (auto error = Action(AC_Write, this, &write); error IS ERR::Okay) { if (Result) *Result = write.Result; + return ERR::Okay; + } + else { + if (Result) *Result = 0; + return error; } - else if (Result) *Result = 0; - return error; } - inline ERROR write(std::string Buffer, LONG *Result = NULL) { - ERROR error; + inline ERR write(std::string Buffer, LONG *Result = NULL) noexcept { struct acWrite write = { (BYTE *)Buffer.c_str(), LONG(Buffer.size()) }; - if (!(error = Action(AC_Write, this, &write))) { + if (auto error = Action(AC_Write, this, &write); error IS ERR::Okay) { if (Result) *Result = write.Result; + return ERR::Okay; + } + else { + if (Result) *Result = 0; + return error; } - else if (Result) *Result = 0; - return error; } - inline LONG writeResult(CPTR Buffer, LONG Size) { + inline LONG writeResult(CPTR Buffer, LONG Size) noexcept { struct acWrite write = { (BYTE *)Buffer, Size }; - if (!Action(AC_Write, this, &write)) return write.Result; + if (Action(AC_Write, this, &write) IS ERR::Okay) return write.Result; else return 0; } @@ -258,7 +263,7 @@ struct prxFind { LONG Port; LONG Enabled; }; #define prxDelete(obj) Action(MT_prxDelete,(obj),0) -INLINE ERROR prxFind(APTR Ob, LONG Port, LONG Enabled) { +INLINE ERR prxFind(APTR Ob, LONG Port, LONG Enabled) noexcept { struct prxFind args = { Port, Enabled }; return(Action(MT_prxFind, (OBJECTPTR)Ob, &args)); } @@ -287,68 +292,68 @@ class objProxy : public BaseClass { // Action stubs - inline ERROR disable() { return Action(AC_Disable, this, NULL); } - inline ERROR enable() { return Action(AC_Enable, this, NULL); } - inline ERROR init() { return InitObject(this); } - inline ERROR saveSettings() { return Action(AC_SaveSettings, this, NULL); } + inline ERR disable() noexcept { return Action(AC_Disable, this, NULL); } + inline ERR enable() noexcept { return Action(AC_Enable, this, NULL); } + inline ERR init() noexcept { return InitObject(this); } + inline ERR saveSettings() noexcept { return Action(AC_SaveSettings, this, NULL); } // Customised field setting - template inline ERROR setNetworkFilter(T && Value) { + template inline ERR setNetworkFilter(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[0]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setGatewayFilter(T && Value) { + template inline ERR setGatewayFilter(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[12]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setUsername(T && Value) { + template inline ERR setUsername(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[13]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setPassword(T && Value) { + template inline ERR setPassword(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[3]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setProxyName(T && Value) { + template inline ERR setProxyName(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[9]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setServer(T && Value) { + template inline ERR setServer(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[5]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setPort(const LONG Value) { + inline ERR setPort(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[8]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setServerPort(const LONG Value) { + inline ERR setServerPort(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[10]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setEnabled(const LONG Value) { + inline ERR setEnabled(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[6]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setRecord(const LONG Value) { + inline ERR setRecord(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[4]; return field->WriteValue(target, field, FD_LONG, &Value, 1); @@ -372,22 +377,22 @@ struct nlResolveAddress { CSTRING Address; }; struct nlBlockingResolveName { CSTRING HostName; }; struct nlBlockingResolveAddress { CSTRING Address; }; -INLINE ERROR nlResolveName(APTR Ob, CSTRING HostName) { +INLINE ERR nlResolveName(APTR Ob, CSTRING HostName) noexcept { struct nlResolveName args = { HostName }; return(Action(MT_nlResolveName, (OBJECTPTR)Ob, &args)); } -INLINE ERROR nlResolveAddress(APTR Ob, CSTRING Address) { +INLINE ERR nlResolveAddress(APTR Ob, CSTRING Address) noexcept { struct nlResolveAddress args = { Address }; return(Action(MT_nlResolveAddress, (OBJECTPTR)Ob, &args)); } -INLINE ERROR nlBlockingResolveName(APTR Ob, CSTRING HostName) { +INLINE ERR nlBlockingResolveName(APTR Ob, CSTRING HostName) noexcept { struct nlBlockingResolveName args = { HostName }; return(Action(MT_nlBlockingResolveName, (OBJECTPTR)Ob, &args)); } -INLINE ERROR nlBlockingResolveAddress(APTR Ob, CSTRING Address) { +INLINE ERR nlBlockingResolveAddress(APTR Ob, CSTRING Address) noexcept { struct nlBlockingResolveAddress args = { Address }; return(Action(MT_nlBlockingResolveAddress, (OBJECTPTR)Ob, &args)); } @@ -405,21 +410,21 @@ class objNetLookup : public BaseClass { // Action stubs - inline ERROR init() { return InitObject(this); } + inline ERR init() noexcept { return InitObject(this); } // Customised field setting - inline ERROR setUserData(const LARGE Value) { + inline ERR setUserData(const LARGE Value) noexcept { this->UserData = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFlags(const NLF Value) { + inline ERR setFlags(const NLF Value) noexcept { this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setCallback(FUNCTION Value) { + inline ERR setCallback(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[0]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); @@ -447,29 +452,29 @@ struct nsDisconnectSocket { objClientSocket * Socket; }; struct nsReadMsg { APTR Message; LONG Length; LONG Progress; LONG CRC; }; struct nsWriteMsg { APTR Message; LONG Length; }; -INLINE ERROR nsConnect(APTR Ob, CSTRING Address, LONG Port) { +INLINE ERR nsConnect(APTR Ob, CSTRING Address, LONG Port) noexcept { struct nsConnect args = { Address, Port }; return(Action(MT_nsConnect, (OBJECTPTR)Ob, &args)); } -INLINE ERROR nsGetLocalIPAddress(APTR Ob, struct IPAddress * Address) { +INLINE ERR nsGetLocalIPAddress(APTR Ob, struct IPAddress * Address) noexcept { struct nsGetLocalIPAddress args = { Address }; return(Action(MT_nsGetLocalIPAddress, (OBJECTPTR)Ob, &args)); } -INLINE ERROR nsDisconnectClient(APTR Ob, struct NetClient * Client) { +INLINE ERR nsDisconnectClient(APTR Ob, struct NetClient * Client) noexcept { struct nsDisconnectClient args = { Client }; return(Action(MT_nsDisconnectClient, (OBJECTPTR)Ob, &args)); } -INLINE ERROR nsDisconnectSocket(APTR Ob, objClientSocket * Socket) { +INLINE ERR nsDisconnectSocket(APTR Ob, objClientSocket * Socket) noexcept { struct nsDisconnectSocket args = { Socket }; return(Action(MT_nsDisconnectSocket, (OBJECTPTR)Ob, &args)); } -INLINE ERROR nsReadMsg(APTR Ob, APTR * Message, LONG * Length, LONG * Progress, LONG * CRC) { +INLINE ERR nsReadMsg(APTR Ob, APTR * Message, LONG * Length, LONG * Progress, LONG * CRC) noexcept { struct nsReadMsg args = { (APTR)0, (LONG)0, (LONG)0, (LONG)0 }; - ERROR error = Action(MT_nsReadMsg, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_nsReadMsg, (OBJECTPTR)Ob, &args); if (Message) *Message = args.Message; if (Length) *Length = args.Length; if (Progress) *Progress = args.Progress; @@ -477,7 +482,7 @@ INLINE ERROR nsReadMsg(APTR Ob, APTR * Message, LONG * Length, LONG * Progress, return(error); } -INLINE ERROR nsWriteMsg(APTR Ob, APTR Message, LONG Length) { +INLINE ERR nsWriteMsg(APTR Ob, APTR Message, LONG Length) noexcept { struct nsWriteMsg args = { Message, Length }; return(Action(MT_nsWriteMsg, (OBJECTPTR)Ob, &args)); } @@ -494,7 +499,7 @@ class objNetSocket : public BaseClass { APTR UserData; // A user-defined pointer that can be useful in action notify events. STRING Address; // An IP address or domain name to connect to. NTC State; // The current connection state of the netsocket object. - ERROR Error; // Information about the last error that occurred during a NetSocket operation + ERR Error; // Information about the last error that occurred during a NetSocket operation LONG Port; // The port number to use for initiating a connection. NSF Flags; // Optional flags. LONG TotalClients; // Indicates the total number of clients currently connected to the socket (if in server mode). @@ -504,118 +509,123 @@ class objNetSocket : public BaseClass { // Action stubs - inline ERROR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) { + inline ERR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) noexcept { struct acDataFeed args = { Object, Datatype, Buffer, Size }; return Action(AC_DataFeed, this, &args); } - inline ERROR disable() { return Action(AC_Disable, this, NULL); } - inline ERROR init() { return InitObject(this); } - template ERROR read(APTR Buffer, T Size, U *Result) { + inline ERR disable() noexcept { return Action(AC_Disable, this, NULL); } + inline ERR init() noexcept { return InitObject(this); } + template ERR read(APTR Buffer, T Size, U *Result) noexcept { static_assert(std::is_integral::value, "Result value must be an integer type"); static_assert(std::is_integral::value, "Size value must be an integer type"); - ERROR error; const LONG bytes = (Size > 0x7fffffff) ? 0x7fffffff : Size; struct acRead read = { (BYTE *)Buffer, bytes }; - if (!(error = Action(AC_Read, this, &read))) *Result = static_cast(read.Result); - else *Result = 0; - return error; + if (auto error = Action(AC_Read, this, &read); error IS ERR::Okay) { + *Result = static_cast(read.Result); + return ERR::Okay; + } + else { *Result = 0; return error; } } - template ERROR read(APTR Buffer, T Size) { + template ERR read(APTR Buffer, T Size) noexcept { static_assert(std::is_integral::value, "Size value must be an integer type"); const LONG bytes = (Size > 0x7fffffff) ? 0x7fffffff : Size; struct acRead read = { (BYTE *)Buffer, bytes }; return Action(AC_Read, this, &read); } - inline ERROR write(CPTR Buffer, LONG Size, LONG *Result = NULL) { - ERROR error; + inline ERR write(CPTR Buffer, LONG Size, LONG *Result = NULL) noexcept { struct acWrite write = { (BYTE *)Buffer, Size }; - if (!(error = Action(AC_Write, this, &write))) { + if (auto error = Action(AC_Write, this, &write); error IS ERR::Okay) { if (Result) *Result = write.Result; + return ERR::Okay; + } + else { + if (Result) *Result = 0; + return error; } - else if (Result) *Result = 0; - return error; } - inline ERROR write(std::string Buffer, LONG *Result = NULL) { - ERROR error; + inline ERR write(std::string Buffer, LONG *Result = NULL) noexcept { struct acWrite write = { (BYTE *)Buffer.c_str(), LONG(Buffer.size()) }; - if (!(error = Action(AC_Write, this, &write))) { + if (auto error = Action(AC_Write, this, &write); error IS ERR::Okay) { if (Result) *Result = write.Result; + return ERR::Okay; + } + else { + if (Result) *Result = 0; + return error; } - else if (Result) *Result = 0; - return error; } - inline LONG writeResult(CPTR Buffer, LONG Size) { + inline LONG writeResult(CPTR Buffer, LONG Size) noexcept { struct acWrite write = { (BYTE *)Buffer, Size }; - if (!Action(AC_Write, this, &write)) return write.Result; + if (Action(AC_Write, this, &write) IS ERR::Okay) return write.Result; else return 0; } // Customised field setting - inline ERROR setUserData(APTR Value) { + inline ERR setUserData(APTR Value) noexcept { this->UserData = Value; - return ERR_Okay; + return ERR::Okay; } - template inline ERROR setAddress(T && Value) { + template inline ERR setAddress(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[5]; return field->WriteValue(target, field, 0x08800500, to_cstring(Value), 1); } - inline ERROR setState(const NTC Value) { + inline ERR setState(const NTC Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[4]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setPort(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setPort(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Port = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFlags(const NSF Value) { + inline ERR setFlags(const NSF Value) noexcept { this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setBacklog(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setBacklog(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Backlog = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setClientLimit(const LONG Value) { + inline ERR setClientLimit(const LONG Value) noexcept { this->ClientLimit = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setMsgLimit(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setMsgLimit(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->MsgLimit = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setSocketHandle(APTR Value) { + inline ERR setSocketHandle(APTR Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[11]; return field->WriteValue(target, field, 0x08000500, Value, 1); } - inline ERROR setFeedback(FUNCTION Value) { + inline ERR setFeedback(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[19]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } - inline ERROR setIncoming(FUNCTION Value) { + inline ERR setIncoming(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[10]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } - inline ERROR setOutgoing(FUNCTION Value) { + inline ERR setOutgoing(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[6]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); @@ -623,9 +633,9 @@ class objNetSocket : public BaseClass { }; -inline ERROR nsCreate(objNetSocket **NewNetSocketOut, OBJECTID ListenerID, APTR UserData) { - if ((*NewNetSocketOut = objNetSocket::create::global(fl::Listener(ListenerID), fl::UserData(UserData)))) return ERR_Okay; - else return ERR_CreateObject; +inline ERR nsCreate(objNetSocket **NewNetSocketOut, OBJECTID ListenerID, APTR UserData) { + if ((*NewNetSocketOut = objNetSocket::create::global(fl::Listener(ListenerID), fl::UserData(UserData)))) return ERR::Okay; + else return ERR::CreateObject; } #ifdef PARASOL_STATIC #define JUMPTABLE_NETWORK static struct NetworkBase *NetworkBase; @@ -635,35 +645,35 @@ inline ERROR nsCreate(objNetSocket **NewNetSocketOut, OBJECTID ListenerID, APTR struct NetworkBase { #ifndef PARASOL_STATIC - ERROR (*_StrToAddress)(CSTRING String, struct IPAddress * Address); + ERR (*_StrToAddress)(CSTRING String, struct IPAddress * Address); CSTRING (*_AddressToStr)(struct IPAddress * IPAddress); ULONG (*_HostToShort)(ULONG Value); ULONG (*_HostToLong)(ULONG Value); ULONG (*_ShortToHost)(ULONG Value); ULONG (*_LongToHost)(ULONG Value); - ERROR (*_SetSSL)(objNetSocket * NetSocket, ...); + ERR (*_SetSSL)(objNetSocket * NetSocket, ...); #endif // PARASOL_STATIC }; #ifndef PRV_NETWORK_MODULE #ifndef PARASOL_STATIC extern struct NetworkBase *NetworkBase; -inline ERROR netStrToAddress(CSTRING String, struct IPAddress * Address) { return NetworkBase->_StrToAddress(String,Address); } +inline ERR netStrToAddress(CSTRING String, struct IPAddress * Address) { return NetworkBase->_StrToAddress(String,Address); } inline CSTRING netAddressToStr(struct IPAddress * IPAddress) { return NetworkBase->_AddressToStr(IPAddress); } inline ULONG netHostToShort(ULONG Value) { return NetworkBase->_HostToShort(Value); } inline ULONG netHostToLong(ULONG Value) { return NetworkBase->_HostToLong(Value); } inline ULONG netShortToHost(ULONG Value) { return NetworkBase->_ShortToHost(Value); } inline ULONG netLongToHost(ULONG Value) { return NetworkBase->_LongToHost(Value); } -template ERROR netSetSSL(objNetSocket * NetSocket, Args... Tags) { return NetworkBase->_SetSSL(NetSocket,Tags...); } +template ERR netSetSSL(objNetSocket * NetSocket, Args... Tags) { return NetworkBase->_SetSSL(NetSocket,Tags...); } #else extern "C" { -extern ERROR netStrToAddress(CSTRING String, struct IPAddress * Address); +extern ERR netStrToAddress(CSTRING String, struct IPAddress * Address); extern CSTRING netAddressToStr(struct IPAddress * IPAddress); extern ULONG netHostToShort(ULONG Value); extern ULONG netHostToLong(ULONG Value); extern ULONG netShortToHost(ULONG Value); extern ULONG netLongToHost(ULONG Value); -extern ERROR netSetSSL(objNetSocket * NetSocket, ...); +extern ERR netSetSSL(objNetSocket * NetSocket, ...); } #endif // PARASOL_STATIC #endif diff --git a/include/parasol/modules/picture.h b/include/parasol/modules/picture.h index 9de56b197..088c959ae 100644 --- a/include/parasol/modules/picture.h +++ b/include/parasol/modules/picture.h @@ -1,7 +1,7 @@ #pragma once // Name: picture.h -// Copyright: Paul Manias © 2001-2023 +// Copyright: Paul Manias © 2001-2024 // Generator: idl-c #include @@ -16,16 +16,13 @@ class objPicture; enum class PCF : ULONG { NIL = 0, - RESIZE_X = 0x00000001, - NO_PALETTE = 0x00000002, - SCALABLE = 0x00000004, - RESIZE_Y = 0x00000008, - RESIZE = 0x00000009, - NEW = 0x00000010, - MASK = 0x00000020, - ALPHA = 0x00000040, - LAZY = 0x00000080, - FORCE_ALPHA_32 = 0x00000100, + NO_PALETTE = 0x00000001, + SCALABLE = 0x00000002, + NEW = 0x00000004, + MASK = 0x00000008, + ALPHA = 0x00000010, + LAZY = 0x00000020, + FORCE_ALPHA_32 = 0x00000040, }; DEFINE_ENUM_FLAG_OPERATORS(PCF) @@ -51,131 +48,136 @@ class objPicture : public BaseClass { // Action stubs - inline ERROR activate() { return Action(AC_Activate, this, NULL); } - inline ERROR init() { return InitObject(this); } - inline ERROR query() { return Action(AC_Query, this, NULL); } - template ERROR read(APTR Buffer, T Size, U *Result) { + inline ERR activate() noexcept { return Action(AC_Activate, this, NULL); } + inline ERR init() noexcept { return InitObject(this); } + inline ERR query() noexcept { return Action(AC_Query, this, NULL); } + template ERR read(APTR Buffer, T Size, U *Result) noexcept { static_assert(std::is_integral::value, "Result value must be an integer type"); static_assert(std::is_integral::value, "Size value must be an integer type"); - ERROR error; const LONG bytes = (Size > 0x7fffffff) ? 0x7fffffff : Size; struct acRead read = { (BYTE *)Buffer, bytes }; - if (!(error = Action(AC_Read, this, &read))) *Result = static_cast(read.Result); - else *Result = 0; - return error; + if (auto error = Action(AC_Read, this, &read); error IS ERR::Okay) { + *Result = static_cast(read.Result); + return ERR::Okay; + } + else { *Result = 0; return error; } } - template ERROR read(APTR Buffer, T Size) { + template ERR read(APTR Buffer, T Size) noexcept { static_assert(std::is_integral::value, "Size value must be an integer type"); const LONG bytes = (Size > 0x7fffffff) ? 0x7fffffff : Size; struct acRead read = { (BYTE *)Buffer, bytes }; return Action(AC_Read, this, &read); } - inline ERROR refresh() { return Action(AC_Refresh, this, NULL); } - inline ERROR saveImage(OBJECTPTR Dest, CLASSID ClassID = 0) { + inline ERR refresh() noexcept { return Action(AC_Refresh, this, NULL); } + inline ERR saveImage(OBJECTPTR Dest, CLASSID ClassID = 0) noexcept { struct acSaveImage args = { Dest, { ClassID } }; return Action(AC_SaveImage, this, &args); } - inline ERROR saveToObject(OBJECTPTR Dest, CLASSID ClassID = 0) { + inline ERR saveToObject(OBJECTPTR Dest, CLASSID ClassID = 0) noexcept { struct acSaveToObject args = { Dest, { ClassID } }; return Action(AC_SaveToObject, this, &args); } - inline ERROR seek(DOUBLE Offset, SEEK Position = SEEK::CURRENT) { + inline ERR seek(DOUBLE Offset, SEEK Position = SEEK::CURRENT) noexcept { struct acSeek args = { Offset, Position }; return Action(AC_Seek, this, &args); } - inline ERROR seekStart(DOUBLE Offset) { return seek(Offset, SEEK::START); } - inline ERROR seekEnd(DOUBLE Offset) { return seek(Offset, SEEK::END); } - inline ERROR seekCurrent(DOUBLE Offset) { return seek(Offset, SEEK::CURRENT); } - inline ERROR write(CPTR Buffer, LONG Size, LONG *Result = NULL) { - ERROR error; + inline ERR seekStart(DOUBLE Offset) noexcept { return seek(Offset, SEEK::START); } + inline ERR seekEnd(DOUBLE Offset) noexcept { return seek(Offset, SEEK::END); } + inline ERR seekCurrent(DOUBLE Offset) noexcept { return seek(Offset, SEEK::CURRENT); } + inline ERR write(CPTR Buffer, LONG Size, LONG *Result = NULL) noexcept { struct acWrite write = { (BYTE *)Buffer, Size }; - if (!(error = Action(AC_Write, this, &write))) { + if (auto error = Action(AC_Write, this, &write); error IS ERR::Okay) { if (Result) *Result = write.Result; + return ERR::Okay; + } + else { + if (Result) *Result = 0; + return error; } - else if (Result) *Result = 0; - return error; } - inline ERROR write(std::string Buffer, LONG *Result = NULL) { - ERROR error; + inline ERR write(std::string Buffer, LONG *Result = NULL) noexcept { struct acWrite write = { (BYTE *)Buffer.c_str(), LONG(Buffer.size()) }; - if (!(error = Action(AC_Write, this, &write))) { + if (auto error = Action(AC_Write, this, &write); error IS ERR::Okay) { if (Result) *Result = write.Result; + return ERR::Okay; + } + else { + if (Result) *Result = 0; + return error; } - else if (Result) *Result = 0; - return error; } - inline LONG writeResult(CPTR Buffer, LONG Size) { + inline LONG writeResult(CPTR Buffer, LONG Size) noexcept { struct acWrite write = { (BYTE *)Buffer, Size }; - if (!Action(AC_Write, this, &write)) return write.Result; + if (Action(AC_Write, this, &write) IS ERR::Okay) return write.Result; else return 0; } // Customised field setting - inline ERROR setFlags(const PCF Value) { + inline ERR setFlags(const PCF Value) noexcept { this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setDisplayHeight(const LONG Value) { + inline ERR setDisplayHeight(const LONG Value) noexcept { this->DisplayHeight = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setDisplayWidth(const LONG Value) { + inline ERR setDisplayWidth(const LONG Value) noexcept { this->DisplayWidth = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setQuality(const LONG Value) { + inline ERR setQuality(const LONG Value) noexcept { this->Quality = Value; - return ERR_Okay; + return ERR::Okay; } - template inline ERROR setAuthor(T && Value) { + template inline ERR setAuthor(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[18]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setCopyright(T && Value) { + template inline ERR setCopyright(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[8]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setDescription(T && Value) { + template inline ERR setDescription(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[14]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setDisclaimer(T && Value) { + template inline ERR setDisclaimer(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[10]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setHeader(APTR Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setHeader(APTR Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; auto target = this; auto field = &this->Class->Dictionary[0]; return field->WriteValue(target, field, 0x08000500, Value, 1); } - template inline ERROR setPath(T && Value) { + template inline ERR setPath(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[13]; return field->WriteValue(target, field, 0x08800500, to_cstring(Value), 1); } - template inline ERROR setSoftware(T && Value) { + template inline ERR setSoftware(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[20]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setTitle(T && Value) { + template inline ERR setTitle(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[5]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); @@ -183,3 +185,8 @@ class objPicture : public BaseClass { }; +namespace fl { + using namespace pf; +constexpr FieldValue DisplayWidth(LONG Value) { return FieldValue(FID_DisplayWidth, Value); } +constexpr FieldValue DisplayHeight(LONG Value) { return FieldValue(FID_DisplayHeight, Value); } +} diff --git a/include/parasol/modules/scintilla.h b/include/parasol/modules/scintilla.h index 00f669bc3..3766f3152 100644 --- a/include/parasol/modules/scintilla.h +++ b/include/parasol/modules/scintilla.h @@ -1,7 +1,7 @@ #pragma once // Name: scintilla.h -// Copyright: Paul Manias © 2005-2023 +// Copyright: Paul Manias © 2005-2024 // Generator: idl-c #include @@ -108,51 +108,51 @@ struct sciReplaceLine { LONG Line; CSTRING String; LONG Length; }; struct sciGotoLine { LONG Line; }; struct sciGetPos { LONG Line; LONG Column; LONG Pos; }; -INLINE ERROR sciSetFont(APTR Ob, CSTRING Face) { +INLINE ERR sciSetFont(APTR Ob, CSTRING Face) noexcept { struct sciSetFont args = { Face }; return(Action(MT_SciSetFont, (OBJECTPTR)Ob, &args)); } -INLINE ERROR sciReplaceText(APTR Ob, CSTRING Find, CSTRING Replace, STF Flags, LONG Start, LONG End) { +INLINE ERR sciReplaceText(APTR Ob, CSTRING Find, CSTRING Replace, STF Flags, LONG Start, LONG End) noexcept { struct sciReplaceText args = { Find, Replace, Flags, Start, End }; return(Action(MT_SciReplaceText, (OBJECTPTR)Ob, &args)); } -INLINE ERROR sciDeleteLine(APTR Ob, LONG Line) { +INLINE ERR sciDeleteLine(APTR Ob, LONG Line) noexcept { struct sciDeleteLine args = { Line }; return(Action(MT_SciDeleteLine, (OBJECTPTR)Ob, &args)); } -INLINE ERROR sciSelectRange(APTR Ob, LONG Start, LONG End) { +INLINE ERR sciSelectRange(APTR Ob, LONG Start, LONG End) noexcept { struct sciSelectRange args = { Start, End }; return(Action(MT_SciSelectRange, (OBJECTPTR)Ob, &args)); } -INLINE ERROR sciInsertText(APTR Ob, CSTRING String, LONG Pos) { +INLINE ERR sciInsertText(APTR Ob, CSTRING String, LONG Pos) noexcept { struct sciInsertText args = { String, Pos }; return(Action(MT_SciInsertText, (OBJECTPTR)Ob, &args)); } -INLINE ERROR sciGetLine(APTR Ob, LONG Line, STRING Buffer, LONG Length) { +INLINE ERR sciGetLine(APTR Ob, LONG Line, STRING Buffer, LONG Length) noexcept { struct sciGetLine args = { Line, Buffer, Length }; return(Action(MT_SciGetLine, (OBJECTPTR)Ob, &args)); } -INLINE ERROR sciReplaceLine(APTR Ob, LONG Line, CSTRING String, LONG Length) { +INLINE ERR sciReplaceLine(APTR Ob, LONG Line, CSTRING String, LONG Length) noexcept { struct sciReplaceLine args = { Line, String, Length }; return(Action(MT_SciReplaceLine, (OBJECTPTR)Ob, &args)); } -INLINE ERROR sciGotoLine(APTR Ob, LONG Line) { +INLINE ERR sciGotoLine(APTR Ob, LONG Line) noexcept { struct sciGotoLine args = { Line }; return(Action(MT_SciGotoLine, (OBJECTPTR)Ob, &args)); } #define sciTrimWhitespace(obj) Action(MT_SciTrimWhitespace,(obj),0) -INLINE ERROR sciGetPos(APTR Ob, LONG Line, LONG Column, LONG * Pos) { +INLINE ERR sciGetPos(APTR Ob, LONG Line, LONG Column, LONG * Pos) noexcept { struct sciGetPos args = { Line, Column, (LONG)0 }; - ERROR error = Action(MT_SciGetPos, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_SciGetPos, (OBJECTPTR)Ob, &args); if (Pos) *Pos = args.Pos; return(error); } @@ -189,217 +189,217 @@ class objScintilla : public BaseClass { // Action stubs - inline ERROR clear() { return Action(AC_Clear, this, NULL); } - inline ERROR clipboard(CLIPMODE Mode) { + inline ERR clear() noexcept { return Action(AC_Clear, this, NULL); } + inline ERR clipboard(CLIPMODE Mode) noexcept { struct acClipboard args = { Mode }; return Action(AC_Clipboard, this, &args); } - inline ERROR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) { + inline ERR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) noexcept { struct acDataFeed args = { Object, Datatype, Buffer, Size }; return Action(AC_DataFeed, this, &args); } - inline ERROR disable() { return Action(AC_Disable, this, NULL); } - inline ERROR draw() { return Action(AC_Draw, this, NULL); } - inline ERROR drawArea(LONG X, LONG Y, LONG Width, LONG Height) { + inline ERR disable() noexcept { return Action(AC_Disable, this, NULL); } + inline ERR draw() noexcept { return Action(AC_Draw, this, NULL); } + inline ERR drawArea(LONG X, LONG Y, LONG Width, LONG Height) noexcept { struct acDraw args = { X, Y, Width, Height }; return Action(AC_Draw, this, &args); } - inline ERROR enable() { return Action(AC_Enable, this, NULL); } - inline ERROR focus() { return Action(AC_Focus, this, NULL); } - inline ERROR hide() { return Action(AC_Hide, this, NULL); } - inline ERROR init() { return InitObject(this); } - inline ERROR redo(LONG Steps) { + inline ERR enable() noexcept { return Action(AC_Enable, this, NULL); } + inline ERR focus() noexcept { return Action(AC_Focus, this, NULL); } + inline ERR hide() noexcept { return Action(AC_Hide, this, NULL); } + inline ERR init() noexcept { return InitObject(this); } + inline ERR redo(LONG Steps) noexcept { struct acRedo args = { Steps }; return Action(AC_Redo, this, &args); } - inline ERROR saveToObject(OBJECTPTR Dest, CLASSID ClassID = 0) { + inline ERR saveToObject(OBJECTPTR Dest, CLASSID ClassID = 0) noexcept { struct acSaveToObject args = { Dest, { ClassID } }; return Action(AC_SaveToObject, this, &args); } - inline ERROR scrollToPoint(DOUBLE X, DOUBLE Y, DOUBLE Z, STP Flags) { + inline ERR scrollToPoint(DOUBLE X, DOUBLE Y, DOUBLE Z, STP Flags) noexcept { struct acScrollToPoint args = { X, Y, Z, Flags }; return Action(AC_ScrollToPoint, this, &args); } - inline ERROR show() { return Action(AC_Show, this, NULL); } - inline ERROR undo(LONG Steps) { + inline ERR show() noexcept { return Action(AC_Show, this, NULL); } + inline ERR undo(LONG Steps) noexcept { struct acUndo args = { Steps }; return Action(AC_Undo, this, &args); } // Customised field setting - template inline ERROR setPath(T && Value) { + template inline ERR setPath(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[22]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setEventFlags(const SEF Value) { + inline ERR setEventFlags(const SEF Value) noexcept { this->EventFlags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setSurface(const OBJECTID Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setSurface(OBJECTID Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->SurfaceID = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFlags(const SCIF Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setFlags(const SCIF Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFocus(const OBJECTID Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setFocus(OBJECTID Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->FocusID = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setVisible(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setVisible(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Visible = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setLeftMargin(const LONG Value) { + inline ERR setLeftMargin(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[32]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setRightMargin(const LONG Value) { + inline ERR setRightMargin(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[27]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setLineHighlight(const struct RGB8 * Value, LONG Elements) { + inline ERR setLineHighlight(const struct RGB8 * Value, LONG Elements) noexcept { auto target = this; auto field = &this->Class->Dictionary[5]; return field->WriteValue(target, field, 0x01081300, Value, Elements); } - inline ERROR setSelectFore(const struct RGB8 * Value, LONG Elements) { + inline ERR setSelectFore(const struct RGB8 * Value, LONG Elements) noexcept { auto target = this; auto field = &this->Class->Dictionary[34]; return field->WriteValue(target, field, 0x01081500, Value, Elements); } - inline ERROR setSelectBkgd(const struct RGB8 * Value, LONG Elements) { + inline ERR setSelectBkgd(const struct RGB8 * Value, LONG Elements) noexcept { auto target = this; auto field = &this->Class->Dictionary[33]; return field->WriteValue(target, field, 0x01081500, Value, Elements); } - inline ERROR setBkgdColour(const struct RGB8 * Value, LONG Elements) { + inline ERR setBkgdColour(const struct RGB8 * Value, LONG Elements) noexcept { auto target = this; auto field = &this->Class->Dictionary[23]; return field->WriteValue(target, field, 0x01081300, Value, Elements); } - inline ERROR setCursorColour(const struct RGB8 * Value, LONG Elements) { + inline ERR setCursorColour(const struct RGB8 * Value, LONG Elements) noexcept { auto target = this; auto field = &this->Class->Dictionary[0]; return field->WriteValue(target, field, 0x01081300, Value, Elements); } - inline ERROR setTextColour(const struct RGB8 * Value, LONG Elements) { + inline ERR setTextColour(const struct RGB8 * Value, LONG Elements) noexcept { auto target = this; auto field = &this->Class->Dictionary[24]; return field->WriteValue(target, field, 0x01081300, Value, Elements); } - inline ERROR setCursorRow(const LONG Value) { + inline ERR setCursorRow(const LONG Value) noexcept { this->CursorRow = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setCursorCol(const LONG Value) { + inline ERR setCursorCol(const LONG Value) noexcept { this->CursorCol = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setLexer(const SCLEX Value) { + inline ERR setLexer(const SCLEX Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[6]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setModified(const LONG Value) { + inline ERR setModified(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[17]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setAllowTabs(const LONG Value) { + inline ERR setAllowTabs(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[12]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setAutoIndent(const LONG Value) { + inline ERR setAutoIndent(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[18]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setFileDrop(FUNCTION Value) { + inline ERR setFileDrop(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[11]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } - inline ERROR setFoldingMarkers(const LONG Value) { + inline ERR setFoldingMarkers(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[13]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setLineNumbers(const LONG Value) { + inline ERR setLineNumbers(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[14]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - template inline ERROR setOrigin(T && Value) { + template inline ERR setOrigin(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[9]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setShowWhitespace(const LONG Value) { + inline ERR setShowWhitespace(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[8]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setEventCallback(FUNCTION Value) { + inline ERR setEventCallback(FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[35]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } - template inline ERROR setString(T && Value) { + template inline ERR setString(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[10]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setSymbols(const LONG Value) { + inline ERR setSymbols(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[28]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setTabWidth(const LONG Value) { + inline ERR setTabWidth(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[25]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setWordwrap(const LONG Value) { + inline ERR setWordwrap(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[29]; return field->WriteValue(target, field, FD_LONG, &Value, 1); @@ -421,23 +421,23 @@ struct ssNext { LONG Pos; }; struct ssPrev { LONG Pos; }; struct ssFind { LONG Pos; STF Flags; }; -INLINE ERROR ssNext(APTR Ob, LONG * Pos) { +INLINE ERR ssNext(APTR Ob, LONG * Pos) noexcept { struct ssNext args = { (LONG)0 }; - ERROR error = Action(MT_SsNext, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_SsNext, (OBJECTPTR)Ob, &args); if (Pos) *Pos = args.Pos; return(error); } -INLINE ERROR ssPrev(APTR Ob, LONG * Pos) { +INLINE ERR ssPrev(APTR Ob, LONG * Pos) noexcept { struct ssPrev args = { (LONG)0 }; - ERROR error = Action(MT_SsPrev, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_SsPrev, (OBJECTPTR)Ob, &args); if (Pos) *Pos = args.Pos; return(error); } -INLINE ERROR ssFind(APTR Ob, LONG * Pos, STF Flags) { +INLINE ERR ssFind(APTR Ob, LONG * Pos, STF Flags) noexcept { struct ssFind args = { (LONG)0, Flags }; - ERROR error = Action(MT_SsFind, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_SsFind, (OBJECTPTR)Ob, &args); if (Pos) *Pos = args.Pos; return(error); } @@ -458,21 +458,21 @@ class objScintillaSearch : public BaseClass { // Customised field setting - inline ERROR setScintilla(objScintilla * Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setScintilla(objScintilla * Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Scintilla = Value; - return ERR_Okay; + return ERR::Okay; } - template inline ERROR setText(T && Value) { + template inline ERR setText(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[5]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setFlags(const STF Value) { + inline ERR setFlags(const STF Value) noexcept { this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } }; diff --git a/include/parasol/modules/svg.h b/include/parasol/modules/svg.h index d635f282c..c3dc5ea95 100644 --- a/include/parasol/modules/svg.h +++ b/include/parasol/modules/svg.h @@ -1,7 +1,7 @@ #pragma once // Name: svg.h -// Copyright: Paul Manias © 2010-2023 +// Copyright: Paul Manias © 2010-2024 // Generator: idl-c #include @@ -27,14 +27,21 @@ DEFINE_ENUM_FLAG_OPERATORS(SVF) // SVG methods #define MT_SvgRender -1 +#define MT_SvgParseSymbol -2 struct svgRender { objBitmap * Bitmap; LONG X; LONG Y; LONG Width; LONG Height; }; +struct svgParseSymbol { CSTRING ID; objVectorViewport * Viewport; }; -INLINE ERROR svgRender(APTR Ob, objBitmap * Bitmap, LONG X, LONG Y, LONG Width, LONG Height) { +INLINE ERR svgRender(APTR Ob, objBitmap * Bitmap, LONG X, LONG Y, LONG Width, LONG Height) noexcept { struct svgRender args = { Bitmap, X, Y, Width, Height }; return(Action(MT_SvgRender, (OBJECTPTR)Ob, &args)); } +INLINE ERR svgParseSymbol(APTR Ob, CSTRING ID, objVectorViewport * Viewport) noexcept { + struct svgParseSymbol args = { ID, Viewport }; + return(Action(MT_SvgParseSymbol, (OBJECTPTR)Ob, &args)); +} + class objSVG : public BaseClass { public: @@ -43,70 +50,83 @@ class objSVG : public BaseClass { using create = pf::Create; - OBJECTPTR Target; // The root Viewport that is generated during SVG initialisation can be created as a child of this target object. - STRING Path; // The location of the source SVG data. + OBJECTPTR Target; // The container object for new SVG content can be declared here. + STRING Path; // A path referring to an SVG file. STRING Title; // The title of the SVG document. + STRING Statement; // A string containing SVG data. LONG Frame; // Forces the graphics to be drawn to a specific frame. SVF Flags; // Optional flags. LONG FrameRate; // The maximum frame rate to use when animating a vector scene. // Action stubs - inline ERROR activate() { return Action(AC_Activate, this, NULL); } - inline ERROR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) { + inline ERR activate() noexcept { return Action(AC_Activate, this, NULL); } + inline ERR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) noexcept { struct acDataFeed args = { Object, Datatype, Buffer, Size }; return Action(AC_DataFeed, this, &args); } - inline ERROR deactivate() { return Action(AC_Deactivate, this, NULL); } - inline ERROR init() { return InitObject(this); } - inline ERROR saveImage(OBJECTPTR Dest, CLASSID ClassID = 0) { + inline ERR deactivate() noexcept { return Action(AC_Deactivate, this, NULL); } + inline ERR init() noexcept { return InitObject(this); } + inline ERR saveImage(OBJECTPTR Dest, CLASSID ClassID = 0) noexcept { struct acSaveImage args = { Dest, { ClassID } }; return Action(AC_SaveImage, this, &args); } - inline ERROR saveToObject(OBJECTPTR Dest, CLASSID ClassID = 0) { + inline ERR saveToObject(OBJECTPTR Dest, CLASSID ClassID = 0) noexcept { struct acSaveToObject args = { Dest, { ClassID } }; return Action(AC_SaveToObject, this, &args); } // Customised field setting - inline ERROR setTarget(OBJECTPTR Value) { + inline ERR setTarget(OBJECTPTR Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[7]; return field->WriteValue(target, field, 0x08000501, Value, 1); } - template inline ERROR setPath(T && Value) { + template inline ERR setPath(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[9]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - template inline ERROR setTitle(T && Value) { + template inline ERR setTitle(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[6]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setFrame(const LONG Value) { + template inline ERR setStatement(T && Value) noexcept { + auto target = this; + auto field = &this->Class->Dictionary[10]; + return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); + } + + inline ERR setFrame(const LONG Value) noexcept { this->Frame = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFlags(const SVF Value) { + inline ERR setFlags(const SVF Value) noexcept { this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFrameRate(const LONG Value) { + inline ERR setFrameRate(const LONG Value) noexcept { auto target = this; - auto field = &this->Class->Dictionary[11]; + auto field = &this->Class->Dictionary[12]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setFrameCallback(const FUNCTION Value) { + template inline ERR setColour(T && Value) noexcept { auto target = this; - auto field = &this->Class->Dictionary[10]; + auto field = &this->Class->Dictionary[15]; + return field->WriteValue(target, field, 0x08800308, to_cstring(Value), 1); + } + + inline ERR setFrameCallback(const FUNCTION Value) noexcept { + auto target = this; + auto field = &this->Class->Dictionary[11]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } diff --git a/include/parasol/modules/vector.h b/include/parasol/modules/vector.h index 885ac1930..1d179985c 100644 --- a/include/parasol/modules/vector.h +++ b/include/parasol/modules/vector.h @@ -1,7 +1,7 @@ #pragma once // Name: vector.h -// Copyright: Paul Manias © 2010-2023 +// Copyright: Paul Manias © 2010-2024 // Generator: idl-c #include @@ -31,17 +31,18 @@ class objMorphologyFX; class objOffsetFX; class objRemapFX; class objTurbulenceFX; +class objVectorClip; class objVectorFilter; class objVector; class objVectorPath; class objVectorText; +class objVectorGroup; class objVectorWave; class objVectorRectangle; class objVectorPolygon; class objVectorShape; class objVectorSpiral; class objVectorEllipse; -class objVectorClip; class objVectorViewport; // Options for drawing arcs. @@ -54,6 +55,16 @@ enum class ARC : ULONG { DEFINE_ENUM_FLAG_OPERATORS(ARC) +// Options for VectorClip. + +enum class VCLF : ULONG { + NIL = 0, + APPLY_FILLS = 0x00000001, + APPLY_STROKES = 0x00000002, +}; + +DEFINE_ENUM_FLAG_OPERATORS(VCLF) + // Optional flags and indicators for the Vector class. enum class VF : ULONG { @@ -64,6 +75,14 @@ enum class VF : ULONG { DEFINE_ENUM_FLAG_OPERATORS(VF) +// Define the aspect ratio for VectorFilter unit scaling. + +enum class VFA : LONG { + NIL = 0, + MEET = 0, + NONE = 1, +}; + // Light source identifiers. enum class LS : LONG { @@ -281,12 +300,13 @@ enum class VTXF : ULONG { OVERLINE = 0x00000002, LINE_THROUGH = 0x00000004, BLINK = 0x00000008, - EDIT = 0x00000010, EDITABLE = 0x00000010, + EDIT = 0x00000010, AREA_SELECTED = 0x00000020, NO_SYS_KEYS = 0x00000040, OVERWRITE = 0x00000080, - RASTER = 0x00000100, + SECRET = 0x00000100, + RASTER = 0x00000200, }; DEFINE_ENUM_FLAG_OPERATORS(VTXF) @@ -370,15 +390,15 @@ enum class CM : LONG { enum class VGF : ULONG { NIL = 0, - RELATIVE_X1 = 0x00000001, - RELATIVE_Y1 = 0x00000002, - RELATIVE_X2 = 0x00000004, - RELATIVE_Y2 = 0x00000008, - RELATIVE_CX = 0x00000010, - RELATIVE_CY = 0x00000020, - RELATIVE_FX = 0x00000040, - RELATIVE_FY = 0x00000080, - RELATIVE_RADIUS = 0x00000100, + SCALED_X1 = 0x00000001, + SCALED_Y1 = 0x00000002, + SCALED_X2 = 0x00000004, + SCALED_Y2 = 0x00000008, + SCALED_CX = 0x00000010, + SCALED_CY = 0x00000020, + SCALED_FX = 0x00000040, + SCALED_FY = 0x00000080, + SCALED_RADIUS = 0x00000100, FIXED_X1 = 0x00000200, FIXED_Y1 = 0x00000400, FIXED_X2 = 0x00000800, @@ -499,27 +519,33 @@ struct Transition { }; struct VectorPoint { - DOUBLE X; // The X coordinate of this point. - DOUBLE Y; // The Y coordinate of this point. - UBYTE XRelative:1; // TRUE if the X value is relative to its viewport (between 0 and 1.0). - UBYTE YRelative:1; // TRUE if the Y value is relative to its viewport (between 0 and 1.0). + DOUBLE X; // The X coordinate of this point. + DOUBLE Y; // The Y coordinate of this point. + UBYTE XScaled:1; // TRUE if the X value is scaled to its viewport (between 0 and 1.0). + UBYTE YScaled:1; // TRUE if the Y value is scaled to its viewport (between 0 and 1.0). +}; + +struct VectorPainter { + objVectorPattern * Pattern; // A VectorPattern object, suitable for pattern based fills. + objVectorImage * Image; // A VectorImage object, suitable for image fills. + objVectorGradient * Gradient; // A VectorGradient object, suitable for gradient fills. + struct FRGB Colour; // A single RGB colour definition, suitable for block colour fills. }; struct PathCommand { - PE Type; // The command type (PE value) - UBYTE Curved; // Private - UBYTE LargeArc; // Equivalent to the large-arc-flag in SVG, it ensures that the arc follows the longest drawing path when TRUE. - UBYTE Sweep; // Equivalent to the sweep-flag in SVG, it inverts the default behaviour in generating arc paths. - UBYTE Pad1; // Private - DOUBLE X; // The targeted X coordinate (absolute or relative) for the command - DOUBLE Y; // The targeted Y coordinate (absolute or relative) for the command - DOUBLE AbsX; // Private - DOUBLE AbsY; // Private - DOUBLE X2; // The X2 coordinate for curve commands, or RX for arcs - DOUBLE Y2; // The Y2 coordinate for curve commands, or RY for arcs - DOUBLE X3; // The X3 coordinate for curve-to or smooth-curve-to - DOUBLE Y3; // The Y3 coordinate for curve-to or smooth-curve-to - DOUBLE Angle; // Arc angle + PE Type; // The command type (PE value) + UBYTE LargeArc; // Equivalent to the large-arc-flag in SVG, it ensures that the arc follows the longest drawing path when TRUE. + UBYTE Sweep; // Equivalent to the sweep-flag in SVG, it inverts the default behaviour in generating arc paths. + UBYTE Pad1; // Private + DOUBLE X; // The targeted X coordinate (absolute or scaled) for the command + DOUBLE Y; // The targeted Y coordinate (absolute or scaled) for the command + DOUBLE AbsX; // Private + DOUBLE AbsY; // Private + DOUBLE X2; // The X2 coordinate for curve commands, or RX for arcs + DOUBLE Y2; // The Y2 coordinate for curve commands, or RY for arcs + DOUBLE X3; // The X3 coordinate for curve-to or smooth-curve-to + DOUBLE Y3; // The Y3 coordinate for curve-to or smooth-curve-to + DOUBLE Angle; // Arc angle }; struct VectorMatrix { @@ -533,6 +559,13 @@ struct VectorMatrix { DOUBLE TranslateY; // Matrix value F }; +struct FontMetrics { + LONG Height; // Capitalised font height + LONG LineSpacing; // Vertical advance from one line to the next + LONG Ascent; // Height from the baseline to the top of the font, including accents. + LONG Descent; // Height from the baseline to the bottom of the font +}; + // VectorColour class definition #define VER_VECTORCOLOUR (1.000000) @@ -551,24 +584,24 @@ class objVectorColour : public BaseClass { // Customised field setting - inline ERROR setRed(const DOUBLE Value) { + inline ERR setRed(const DOUBLE Value) noexcept { this->Red = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setGreen(const DOUBLE Value) { + inline ERR setGreen(const DOUBLE Value) noexcept { this->Green = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setBlue(const DOUBLE Value) { + inline ERR setBlue(const DOUBLE Value) noexcept { this->Blue = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setAlpha(const DOUBLE Value) { + inline ERR setAlpha(const DOUBLE Value) noexcept { this->Alpha = Value; - return ERR_Okay; + return ERR::Okay; } }; @@ -588,21 +621,21 @@ struct scAddDef { CSTRING Name; OBJECTPTR Def; }; struct scSearchByID { LONG ID; OBJECTPTR Result; }; struct scFindDef { CSTRING Name; OBJECTPTR Def; }; -INLINE ERROR scAddDef(APTR Ob, CSTRING Name, OBJECTPTR Def) { +INLINE ERR scAddDef(APTR Ob, CSTRING Name, OBJECTPTR Def) noexcept { struct scAddDef args = { Name, Def }; return(Action(MT_ScAddDef, (OBJECTPTR)Ob, &args)); } -INLINE ERROR scSearchByID(APTR Ob, LONG ID, OBJECTPTR * Result) { +INLINE ERR scSearchByID(APTR Ob, LONG ID, OBJECTPTR * Result) noexcept { struct scSearchByID args = { ID, (OBJECTPTR)0 }; - ERROR error = Action(MT_ScSearchByID, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_ScSearchByID, (OBJECTPTR)Ob, &args); if (Result) *Result = args.Result; return(error); } -INLINE ERROR scFindDef(APTR Ob, CSTRING Name, OBJECTPTR * Def) { +INLINE ERR scFindDef(APTR Ob, CSTRING Name, OBJECTPTR * Def) noexcept { struct scFindDef args = { Name, (OBJECTPTR)0 }; - ERROR error = Action(MT_ScFindDef, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_ScFindDef, (OBJECTPTR)Ob, &args); if (Def) *Def = args.Def; return(error); } @@ -630,71 +663,71 @@ class objVectorScene : public BaseClass { // Action stubs - inline ERROR draw() { return Action(AC_Draw, this, NULL); } - inline ERROR drawArea(LONG X, LONG Y, LONG Width, LONG Height) { + inline ERR draw() noexcept { return Action(AC_Draw, this, NULL); } + inline ERR drawArea(LONG X, LONG Y, LONG Width, LONG Height) noexcept { struct acDraw args = { X, Y, Width, Height }; return Action(AC_Draw, this, &args); } - inline ERROR init() { return InitObject(this); } - inline ERROR redimension(DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE Width, DOUBLE Height, DOUBLE Depth) { + inline ERR init() noexcept { return InitObject(this); } + inline ERR redimension(DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE Width, DOUBLE Height, DOUBLE Depth) noexcept { struct acRedimension args = { X, Y, Z, Width, Height, Depth }; return Action(AC_Redimension, this, &args); } - inline ERROR redimension(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) { + inline ERR redimension(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) noexcept { struct acRedimension args = { X, Y, 0, Width, Height, 0 }; return Action(AC_Redimension, this, &args); } - inline ERROR reset() { return Action(AC_Reset, this, NULL); } - inline ERROR resize(DOUBLE Width, DOUBLE Height, DOUBLE Depth = 0) { + inline ERR reset() noexcept { return Action(AC_Reset, this, NULL); } + inline ERR resize(DOUBLE Width, DOUBLE Height, DOUBLE Depth = 0) noexcept { struct acResize args = { Width, Height, Depth }; return Action(AC_Resize, this, &args); } // Customised field setting - inline ERROR setGamma(const DOUBLE Value) { + inline ERR setGamma(const DOUBLE Value) noexcept { this->Gamma = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setHostScene(objVectorScene * Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setHostScene(objVectorScene * Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->HostScene = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setBitmap(objBitmap * Value) { + inline ERR setBitmap(objBitmap * Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[14]; return field->WriteValue(target, field, 0x08000301, Value, 1); } - inline ERROR setSurface(const OBJECTID Value) { + inline ERR setSurface(OBJECTID Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[11]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setFlags(const VPF Value) { + inline ERR setFlags(const VPF Value) noexcept { this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setPageWidth(const LONG Value) { + inline ERR setPageWidth(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[4]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setPageHeight(const LONG Value) { + inline ERR setPageHeight(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[9]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setSampleMethod(const VSM Value) { + inline ERR setSampleMethod(const VSM Value) noexcept { this->SampleMethod = Value; - return ERR_Okay; + return ERR::Okay; } }; @@ -715,52 +748,52 @@ class objVectorImage : public BaseClass { objPicture * Picture; // Refers to a @Picture from which the source #Bitmap is acquired. objBitmap * Bitmap; // Reference to a source bitmap for the rendering algorithm. VUNIT Units; // Declares the coordinate system to use for the #X and #Y values. - LONG Dimensions; // Dimension flags define whether individual dimension fields contain fixed or relative values. - VSPREAD SpreadMethod; // Defines the drawing mode. + LONG Dimensions; // Dimension flags define whether individual dimension fields contain fixed or scaled values. + VSPREAD SpreadMethod; // Defines image tiling behaviour, if desired. ARF AspectRatio; // Flags that affect the aspect ratio of the image within its target vector. // Customised field setting - inline ERROR setX(const DOUBLE Value) { + inline ERR setX(const DOUBLE Value) noexcept { this->X = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setY(const DOUBLE Value) { + inline ERR setY(const DOUBLE Value) noexcept { this->Y = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setPicture(objPicture * Value) { + inline ERR setPicture(objPicture * Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[9]; return field->WriteValue(target, field, 0x08000301, Value, 1); } - inline ERROR setBitmap(objBitmap * Value) { + inline ERR setBitmap(objBitmap * Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[11]; return field->WriteValue(target, field, 0x08000301, Value, 1); } - inline ERROR setUnits(const VUNIT Value) { + inline ERR setUnits(const VUNIT Value) noexcept { this->Units = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setDimensions(const LONG Value) { + inline ERR setDimensions(const LONG Value) noexcept { this->Dimensions = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setSpreadMethod(const VSPREAD Value) { + inline ERR setSpreadMethod(const VSPREAD Value) noexcept { this->SpreadMethod = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setAspectRatio(const ARF Value) { + inline ERR setAspectRatio(const ARF Value) noexcept { this->AspectRatio = Value; - return ERR_Okay; + return ERR::Okay; } }; @@ -790,68 +823,68 @@ class objVectorPattern : public BaseClass { // Customised field setting - inline ERROR setX(const DOUBLE Value) { + inline ERR setX(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[0]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setY(const DOUBLE Value) { + inline ERR setY(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[1]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setWidth(const DOUBLE Value) { + inline ERR setWidth(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[8]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setHeight(const DOUBLE Value) { + inline ERR setHeight(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[2]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setOpacity(const DOUBLE Value) { + inline ERR setOpacity(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[11]; return field->WriteValue(target, field, FD_DOUBLE, &Value, 1); } - inline ERROR setInherit(objVectorPattern * Value) { + inline ERR setInherit(objVectorPattern * Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[14]; return field->WriteValue(target, field, 0x08000301, Value, 1); } - inline ERROR setSpreadMethod(const VSPREAD Value) { + inline ERR setSpreadMethod(const VSPREAD Value) noexcept { this->SpreadMethod = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setUnits(const VUNIT Value) { + inline ERR setUnits(const VUNIT Value) noexcept { this->Units = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setContentUnits(const VUNIT Value) { + inline ERR setContentUnits(const VUNIT Value) noexcept { this->ContentUnits = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setMatrices(APTR Value) { + inline ERR setMatrices(APTR Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[10]; return field->WriteValue(target, field, 0x08000318, Value, 1); } - template inline ERROR setTransform(T && Value) { + template inline ERR setTransform(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[9]; return field->WriteValue(target, field, 0x08800208, to_cstring(Value), 1); @@ -889,132 +922,132 @@ class objVectorGradient : public BaseClass { // Action stubs - inline ERROR init() { return InitObject(this); } + inline ERR init() noexcept { return InitObject(this); } // Customised field setting - inline ERROR setX1(const DOUBLE Value) { + inline ERR setX1(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[3]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setY1(const DOUBLE Value) { + inline ERR setY1(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[5]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setX2(const DOUBLE Value) { + inline ERR setX2(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[4]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setY2(const DOUBLE Value) { + inline ERR setY2(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[6]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setCenterX(const DOUBLE Value) { + inline ERR setCenterX(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[21]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setCenterY(const DOUBLE Value) { + inline ERR setCenterY(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[22]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setFX(const DOUBLE Value) { + inline ERR setFX(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[0]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setFY(const DOUBLE Value) { + inline ERR setFY(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[1]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setRadius(const DOUBLE Value) { + inline ERR setRadius(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[14]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setInherit(objVectorGradient * Value) { + inline ERR setInherit(objVectorGradient * Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[19]; return field->WriteValue(target, field, 0x08000301, Value, 1); } - inline ERROR setSpreadMethod(const VSPREAD Value) { + inline ERR setSpreadMethod(const VSPREAD Value) noexcept { this->SpreadMethod = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setUnits(const VUNIT Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setUnits(const VUNIT Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Units = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setType(const VGT Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setType(const VGT Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Type = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFlags(const VGF Value) { + inline ERR setFlags(const VGF Value) noexcept { this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setColourSpace(const VCS Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setColourSpace(const VCS Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->ColourSpace = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setMatrices(APTR Value) { + inline ERR setMatrices(APTR Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[16]; return field->WriteValue(target, field, 0x08000318, Value, 1); } - inline ERROR setNumeric(const LONG Value) { + inline ERR setNumeric(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[20]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - template inline ERROR setID(T && Value) { + template inline ERR setID(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[2]; return field->WriteValue(target, field, 0x08800308, to_cstring(Value), 1); } - inline ERROR setStops(const APTR Value, LONG Elements) { + inline ERR setStops(const APTR Value, LONG Elements) noexcept { auto target = this; auto field = &this->Class->Dictionary[11]; return field->WriteValue(target, field, 0x00001318, Value, Elements); } - template inline ERROR setTransform(T && Value) { + template inline ERR setTransform(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[15]; return field->WriteValue(target, field, 0x08800208, to_cstring(Value), 1); @@ -1048,75 +1081,75 @@ class objFilterEffect : public BaseClass { // Action stubs - inline ERROR init() { return InitObject(this); } - inline ERROR moveToBack() { return Action(AC_MoveToBack, this, NULL); } - inline ERROR moveToFront() { return Action(AC_MoveToFront, this, NULL); } + inline ERR init() noexcept { return InitObject(this); } + inline ERR moveToBack() noexcept { return Action(AC_MoveToBack, this, NULL); } + inline ERR moveToFront() noexcept { return Action(AC_MoveToFront, this, NULL); } // Customised field setting - inline ERROR setNext(objFilterEffect * Value) { + inline ERR setNext(objFilterEffect * Value) noexcept { this->Next = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setPrev(objFilterEffect * Value) { + inline ERR setPrev(objFilterEffect * Value) noexcept { this->Prev = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setTarget(objBitmap * Value) { + inline ERR setTarget(objBitmap * Value) noexcept { this->Target = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setInput(objFilterEffect * Value) { + inline ERR setInput(objFilterEffect * Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[5]; return field->WriteValue(target, field, 0x08000301, Value, 1); } - inline ERROR setMix(objFilterEffect * Value) { + inline ERR setMix(objFilterEffect * Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[3]; return field->WriteValue(target, field, 0x08000301, Value, 1); } - inline ERROR setX(const DOUBLE Value) { + inline ERR setX(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[0]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setY(const DOUBLE Value) { + inline ERR setY(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[1]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setWidth(const DOUBLE Value) { + inline ERR setWidth(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[7]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setHeight(const DOUBLE Value) { + inline ERR setHeight(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[2]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setSourceType(const VSF Value) { + inline ERR setSourceType(const VSF Value) noexcept { this->SourceType = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setMixType(const VSF Value) { + inline ERR setMixType(const VSF Value) noexcept { this->MixType = Value; - return ERR_Okay; + return ERR::Okay; } }; @@ -1237,17 +1270,17 @@ struct ltSetDistantLight { DOUBLE Azimuth; DOUBLE Elevation; }; struct ltSetPointLight { DOUBLE X; DOUBLE Y; DOUBLE Z; }; struct ltSetSpotLight { DOUBLE X; DOUBLE Y; DOUBLE Z; DOUBLE PX; DOUBLE PY; DOUBLE PZ; DOUBLE Exponent; DOUBLE ConeAngle; }; -INLINE ERROR ltSetDistantLight(APTR Ob, DOUBLE Azimuth, DOUBLE Elevation) { +INLINE ERR ltSetDistantLight(APTR Ob, DOUBLE Azimuth, DOUBLE Elevation) noexcept { struct ltSetDistantLight args = { Azimuth, Elevation }; return(Action(MT_LTSetDistantLight, (OBJECTPTR)Ob, &args)); } -INLINE ERROR ltSetPointLight(APTR Ob, DOUBLE X, DOUBLE Y, DOUBLE Z) { +INLINE ERR ltSetPointLight(APTR Ob, DOUBLE X, DOUBLE Y, DOUBLE Z) noexcept { struct ltSetPointLight args = { X, Y, Z }; return(Action(MT_LTSetPointLight, (OBJECTPTR)Ob, &args)); } -INLINE ERROR ltSetSpotLight(APTR Ob, DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE PX, DOUBLE PY, DOUBLE PZ, DOUBLE Exponent, DOUBLE ConeAngle) { +INLINE ERR ltSetSpotLight(APTR Ob, DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE PX, DOUBLE PY, DOUBLE PZ, DOUBLE Exponent, DOUBLE ConeAngle) noexcept { struct ltSetSpotLight args = { X, Y, Z, PX, PY, PZ, Exponent, ConeAngle }; return(Action(MT_LTSetSpotLight, (OBJECTPTR)Ob, &args)); } @@ -1319,37 +1352,37 @@ struct rfSelectDiscrete { CMP Component; DOUBLE * Values; LONG Size; }; struct rfSelectInvert { CMP Component; }; struct rfSelectMask { CMP Component; LONG Mask; }; -INLINE ERROR rfSelectGamma(APTR Ob, CMP Component, DOUBLE Amplitude, DOUBLE Offset, DOUBLE Exponent) { +INLINE ERR rfSelectGamma(APTR Ob, CMP Component, DOUBLE Amplitude, DOUBLE Offset, DOUBLE Exponent) noexcept { struct rfSelectGamma args = { Component, Amplitude, Offset, Exponent }; return(Action(MT_RFSelectGamma, (OBJECTPTR)Ob, &args)); } -INLINE ERROR rfSelectTable(APTR Ob, CMP Component, DOUBLE * Values, LONG Size) { +INLINE ERR rfSelectTable(APTR Ob, CMP Component, DOUBLE * Values, LONG Size) noexcept { struct rfSelectTable args = { Component, Values, Size }; return(Action(MT_RFSelectTable, (OBJECTPTR)Ob, &args)); } -INLINE ERROR rfSelectLinear(APTR Ob, CMP Component, DOUBLE Slope, DOUBLE Intercept) { +INLINE ERR rfSelectLinear(APTR Ob, CMP Component, DOUBLE Slope, DOUBLE Intercept) noexcept { struct rfSelectLinear args = { Component, Slope, Intercept }; return(Action(MT_RFSelectLinear, (OBJECTPTR)Ob, &args)); } -INLINE ERROR rfSelectIdentity(APTR Ob, CMP Component) { +INLINE ERR rfSelectIdentity(APTR Ob, CMP Component) noexcept { struct rfSelectIdentity args = { Component }; return(Action(MT_RFSelectIdentity, (OBJECTPTR)Ob, &args)); } -INLINE ERROR rfSelectDiscrete(APTR Ob, CMP Component, DOUBLE * Values, LONG Size) { +INLINE ERR rfSelectDiscrete(APTR Ob, CMP Component, DOUBLE * Values, LONG Size) noexcept { struct rfSelectDiscrete args = { Component, Values, Size }; return(Action(MT_RFSelectDiscrete, (OBJECTPTR)Ob, &args)); } -INLINE ERROR rfSelectInvert(APTR Ob, CMP Component) { +INLINE ERR rfSelectInvert(APTR Ob, CMP Component) noexcept { struct rfSelectInvert args = { Component }; return(Action(MT_RFSelectInvert, (OBJECTPTR)Ob, &args)); } -INLINE ERROR rfSelectMask(APTR Ob, CMP Component, LONG Mask) { +INLINE ERR rfSelectMask(APTR Ob, CMP Component, LONG Mask) noexcept { struct rfSelectMask args = { Component, Mask }; return(Action(MT_RFSelectMask, (OBJECTPTR)Ob, &args)); } @@ -1375,6 +1408,37 @@ class objTurbulenceFX : public objFilterEffect { using create = pf::Create; }; +// VectorClip class definition + +#define VER_VECTORCLIP (1.000000) + +class objVectorClip : public BaseClass { + public: + static constexpr CLASSID CLASS_ID = ID_VECTORCLIP; + static constexpr CSTRING CLASS_NAME = "VectorClip"; + + using create = pf::Create; + + objVectorViewport * Viewport; // This viewport hosts the Vector objects that will contribute to the clip path. + VUNIT Units; // Defines the coordinate system for fields X, Y, Width and Height. + VCLF Flags; // Optional flags. + + // Customised field setting + + inline ERR setUnits(const VUNIT Value) noexcept { + auto target = this; + auto field = &this->Class->Dictionary[3]; + return field->WriteValue(target, field, FD_LONG, &Value, 1); + } + + inline ERR setFlags(const VCLF Value) noexcept { + auto target = this; + auto field = &this->Class->Dictionary[1]; + return field->WriteValue(target, field, FD_LONG, &Value, 1); + } + +}; + // VectorFilter class definition #define VER_VECTORFILTER (1.000000) @@ -1388,89 +1452,95 @@ class objVectorFilter : public BaseClass { DOUBLE X; // X coordinate for the filter. DOUBLE Y; // Y coordinate for the filter. - DOUBLE Width; // The width of the filter area. Can be expressed as a fixed or relative coordinate. - DOUBLE Height; // The height of the filter area. Can be expressed as a fixed or relative coordinate. + DOUBLE Width; // The width of the filter area. Can be expressed as a fixed or scaled coordinate. + DOUBLE Height; // The height of the filter area. Can be expressed as a fixed or scaled coordinate. DOUBLE Opacity; // The opacity of the filter. objVectorFilter * Inherit; // Inherit attributes from a VectorFilter referenced here. LONG ResX; // Width of the intermediate images, measured in pixels. LONG ResY; // Height of the intermediate images, measured in pixels. VUNIT Units; // Defines the coordinate system for fields X, Y, Width and Height. VUNIT PrimitiveUnits; // Alters the behaviour of some effects that support alternative position calculations. - LONG Dimensions; // Dimension flags define whether individual dimension fields contain fixed or relative values. + LONG Dimensions; // Dimension flags define whether individual dimension fields contain fixed or scaled values. VCS ColourSpace; // The colour space of the filter graphics (SRGB or linear RGB). + VFA AspectRatio; // Aspect ratio to use when scaling X/Y values // Action stubs - inline ERROR clear() { return Action(AC_Clear, this, NULL); } - inline ERROR init() { return InitObject(this); } + inline ERR clear() noexcept { return Action(AC_Clear, this, NULL); } + inline ERR init() noexcept { return InitObject(this); } // Customised field setting - inline ERROR setX(const DOUBLE Value) { + inline ERR setX(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[0]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setY(const DOUBLE Value) { + inline ERR setY(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[1]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setWidth(const DOUBLE Value) { + inline ERR setWidth(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[6]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setHeight(const DOUBLE Value) { + inline ERR setHeight(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[2]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setOpacity(const DOUBLE Value) { + inline ERR setOpacity(const DOUBLE Value) noexcept { auto target = this; - auto field = &this->Class->Dictionary[8]; + auto field = &this->Class->Dictionary[9]; return field->WriteValue(target, field, FD_DOUBLE, &Value, 1); } - inline ERROR setInherit(objVectorFilter * Value) { + inline ERR setInherit(objVectorFilter * Value) noexcept { auto target = this; - auto field = &this->Class->Dictionary[13]; + auto field = &this->Class->Dictionary[14]; return field->WriteValue(target, field, 0x08000301, Value, 1); } - inline ERROR setResX(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setResX(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->ResX = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setResY(const LONG Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setResY(const LONG Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->ResY = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setUnits(const VUNIT Value) { + inline ERR setUnits(const VUNIT Value) noexcept { this->Units = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setPrimitiveUnits(const VUNIT Value) { + inline ERR setPrimitiveUnits(const VUNIT Value) noexcept { this->PrimitiveUnits = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setColourSpace(const VCS Value) { + inline ERR setColourSpace(const VCS Value) noexcept { this->ColourSpace = Value; - return ERR_Okay; + return ERR::Okay; + } + + inline ERR setAspectRatio(const VFA Value) noexcept { + this->AspectRatio = Value; + return ERR::Okay; } }; @@ -1502,19 +1572,19 @@ struct vecSubscribeFeedback { FM Mask; FUNCTION * Callback; }; struct vecNewMatrix { struct VectorMatrix * Transform; }; struct vecFreeMatrix { struct VectorMatrix * Matrix; }; -INLINE ERROR vecPush(APTR Ob, LONG Position) { +INLINE ERR vecPush(APTR Ob, LONG Position) noexcept { struct vecPush args = { Position }; return(Action(MT_VecPush, (OBJECTPTR)Ob, &args)); } -INLINE ERROR vecTracePath(APTR Ob, FUNCTION * Callback) { +INLINE ERR vecTracePath(APTR Ob, FUNCTION * Callback) noexcept { struct vecTracePath args = { Callback }; return(Action(MT_VecTracePath, (OBJECTPTR)Ob, &args)); } -INLINE ERROR vecGetBoundary(APTR Ob, VBF Flags, DOUBLE * X, DOUBLE * Y, DOUBLE * Width, DOUBLE * Height) { +INLINE ERR vecGetBoundary(APTR Ob, VBF Flags, DOUBLE * X, DOUBLE * Y, DOUBLE * Width, DOUBLE * Height) noexcept { struct vecGetBoundary args = { Flags, (DOUBLE)0, (DOUBLE)0, (DOUBLE)0, (DOUBLE)0 }; - ERROR error = Action(MT_VecGetBoundary, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_VecGetBoundary, (OBJECTPTR)Ob, &args); if (X) *X = args.X; if (Y) *Y = args.Y; if (Width) *Width = args.Width; @@ -1522,36 +1592,36 @@ INLINE ERROR vecGetBoundary(APTR Ob, VBF Flags, DOUBLE * X, DOUBLE * Y, DOUBLE * return(error); } -INLINE ERROR vecPointInPath(APTR Ob, DOUBLE X, DOUBLE Y) { +INLINE ERR vecPointInPath(APTR Ob, DOUBLE X, DOUBLE Y) noexcept { struct vecPointInPath args = { X, Y }; return(Action(MT_VecPointInPath, (OBJECTPTR)Ob, &args)); } -INLINE ERROR vecSubscribeInput(APTR Ob, JTYPE Mask, FUNCTION * Callback) { +INLINE ERR vecSubscribeInput(APTR Ob, JTYPE Mask, FUNCTION * Callback) noexcept { struct vecSubscribeInput args = { Mask, Callback }; return(Action(MT_VecSubscribeInput, (OBJECTPTR)Ob, &args)); } -INLINE ERROR vecSubscribeKeyboard(APTR Ob, FUNCTION * Callback) { +INLINE ERR vecSubscribeKeyboard(APTR Ob, FUNCTION * Callback) noexcept { struct vecSubscribeKeyboard args = { Callback }; return(Action(MT_VecSubscribeKeyboard, (OBJECTPTR)Ob, &args)); } -INLINE ERROR vecSubscribeFeedback(APTR Ob, FM Mask, FUNCTION * Callback) { +INLINE ERR vecSubscribeFeedback(APTR Ob, FM Mask, FUNCTION * Callback) noexcept { struct vecSubscribeFeedback args = { Mask, Callback }; return(Action(MT_VecSubscribeFeedback, (OBJECTPTR)Ob, &args)); } #define vecDebug(obj) Action(MT_VecDebug,(obj),0) -INLINE ERROR vecNewMatrix(APTR Ob, struct VectorMatrix ** Transform) { +INLINE ERR vecNewMatrix(APTR Ob, struct VectorMatrix ** Transform) noexcept { struct vecNewMatrix args = { (struct VectorMatrix *)0 }; - ERROR error = Action(MT_VecNewMatrix, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_VecNewMatrix, (OBJECTPTR)Ob, &args); if (Transform) *Transform = args.Transform; return(error); } -INLINE ERROR vecFreeMatrix(APTR Ob, struct VectorMatrix * Matrix) { +INLINE ERR vecFreeMatrix(APTR Ob, struct VectorMatrix * Matrix) noexcept { struct vecFreeMatrix args = { Matrix }; return(Action(MT_VecFreeMatrix, (OBJECTPTR)Ob, &args)); } @@ -1584,217 +1654,217 @@ class objVector : public BaseClass { // Action stubs - inline ERROR disable() { return Action(AC_Disable, this, NULL); } - inline ERROR draw() { return Action(AC_Draw, this, NULL); } - inline ERROR drawArea(LONG X, LONG Y, LONG Width, LONG Height) { + inline ERR disable() noexcept { return Action(AC_Disable, this, NULL); } + inline ERR draw() noexcept { return Action(AC_Draw, this, NULL); } + inline ERR drawArea(LONG X, LONG Y, LONG Width, LONG Height) noexcept { struct acDraw args = { X, Y, Width, Height }; return Action(AC_Draw, this, &args); } - inline ERROR enable() { return Action(AC_Enable, this, NULL); } - inline ERROR hide() { return Action(AC_Hide, this, NULL); } - inline ERROR init() { return InitObject(this); } - inline ERROR moveToBack() { return Action(AC_MoveToBack, this, NULL); } - inline ERROR moveToFront() { return Action(AC_MoveToFront, this, NULL); } - inline ERROR show() { return Action(AC_Show, this, NULL); } + inline ERR enable() noexcept { return Action(AC_Enable, this, NULL); } + inline ERR hide() noexcept { return Action(AC_Hide, this, NULL); } + inline ERR init() noexcept { return InitObject(this); } + inline ERR moveToBack() noexcept { return Action(AC_MoveToBack, this, NULL); } + inline ERR moveToFront() noexcept { return Action(AC_MoveToFront, this, NULL); } + inline ERR show() noexcept { return Action(AC_Show, this, NULL); } // Customised field setting - inline ERROR setNext(objVector * Value) { + inline ERR setNext(objVector * Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[26]; return field->WriteValue(target, field, 0x08000301, Value, 1); } - inline ERROR setPrev(objVector * Value) { + inline ERR setPrev(objVector * Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[27]; return field->WriteValue(target, field, 0x08000301, Value, 1); } - inline ERROR setStrokeOpacity(const DOUBLE Value) { + inline ERR setStrokeOpacity(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[34]; return field->WriteValue(target, field, FD_DOUBLE, &Value, 1); } - inline ERROR setFillOpacity(const DOUBLE Value) { + inline ERR setFillOpacity(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[40]; return field->WriteValue(target, field, FD_DOUBLE, &Value, 1); } - inline ERROR setOpacity(const DOUBLE Value) { + inline ERR setOpacity(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[20]; return field->WriteValue(target, field, FD_DOUBLE, &Value, 1); } - inline ERROR setMiterLimit(const DOUBLE Value) { + inline ERR setMiterLimit(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[13]; return field->WriteValue(target, field, FD_DOUBLE, &Value, 1); } - inline ERROR setInnerMiterLimit(const DOUBLE Value) { + inline ERR setInnerMiterLimit(const DOUBLE Value) noexcept { this->InnerMiterLimit = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setDashOffset(const DOUBLE Value) { + inline ERR setDashOffset(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[19]; return field->WriteValue(target, field, FD_DOUBLE, &Value, 1); } - inline ERROR setVisibility(const VIS Value) { + inline ERR setVisibility(const VIS Value) noexcept { this->Visibility = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFlags(const VF Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setFlags(const VF Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setCursor(const PTC Value) { + inline ERR setCursor(const PTC Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[41]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setPathQuality(const RQ Value) { + inline ERR setPathQuality(const RQ Value) noexcept { this->PathQuality = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setColourSpace(const VCS Value) { + inline ERR setColourSpace(const VCS Value) noexcept { this->ColourSpace = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setClipRule(const LONG Value) { + inline ERR setClipRule(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[17]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setDashArray(const DOUBLE * Value, LONG Elements) { + inline ERR setDashArray(const DOUBLE * Value, LONG Elements) noexcept { auto target = this; auto field = &this->Class->Dictionary[28]; return field->WriteValue(target, field, 0x80001308, Value, Elements); } - inline ERROR setMask(OBJECTPTR Value) { + inline ERR setMask(OBJECTPTR Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[24]; return field->WriteValue(target, field, 0x08000309, Value, 1); } - inline ERROR setMorph(OBJECTPTR Value) { + inline ERR setMorph(OBJECTPTR Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[5]; return field->WriteValue(target, field, 0x08000309, Value, 1); } - inline ERROR setMorphFlags(const LONG Value) { + inline ERR setMorphFlags(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[16]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setNumeric(const LONG Value) { + inline ERR setNumeric(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[33]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - template inline ERROR setID(T && Value) { + template inline ERR setID(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[0]; return field->WriteValue(target, field, 0x08800308, to_cstring(Value), 1); } - inline ERROR setResizeEvent(const FUNCTION Value) { + inline ERR setResizeEvent(const FUNCTION Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[36]; return field->WriteValue(target, field, FD_FUNCTION, &Value, 1); } - template inline ERROR setStroke(T && Value) { + template inline ERR setStroke(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[11]; return field->WriteValue(target, field, 0x08800308, to_cstring(Value), 1); } - inline ERROR setStrokeColour(const FLOAT * Value, LONG Elements) { + inline ERR setStrokeColour(const FLOAT * Value, LONG Elements) noexcept { auto target = this; auto field = &this->Class->Dictionary[12]; return field->WriteValue(target, field, 0x10001308, Value, Elements); } - inline ERROR setStrokeWidth(const DOUBLE Value) { + inline ERR setStrokeWidth(const DOUBLE Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[10]; Variable var(Value); return field->WriteValue(target, field, FD_VARIABLE, &var, 1); } - inline ERROR setTransition(OBJECTPTR Value) { + inline ERR setTransition(OBJECTPTR Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[29]; return field->WriteValue(target, field, 0x08000309, Value, 1); } - inline ERROR setEnableBkgd(const LONG Value) { + inline ERR setEnableBkgd(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[39]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - template inline ERROR setFill(T && Value) { + template inline ERR setFill(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[23]; return field->WriteValue(target, field, 0x08800308, to_cstring(Value), 1); } - inline ERROR setFillColour(const FLOAT * Value, LONG Elements) { + inline ERR setFillColour(const FLOAT * Value, LONG Elements) noexcept { auto target = this; auto field = &this->Class->Dictionary[32]; return field->WriteValue(target, field, 0x10001308, Value, Elements); } - inline ERROR setFillRule(const LONG Value) { + inline ERR setFillRule(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[14]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - template inline ERROR setFilter(T && Value) { + template inline ERR setFilter(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[42]; return field->WriteValue(target, field, 0x08800308, to_cstring(Value), 1); } - inline ERROR setLineJoin(const LONG Value) { + inline ERR setLineJoin(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[35]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setLineCap(const LONG Value) { + inline ERR setLineCap(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[22]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setInnerJoin(const LONG Value) { + inline ERR setInnerJoin(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[15]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - inline ERROR setTabOrder(const LONG Value) { + inline ERR setTabOrder(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[30]; return field->WriteValue(target, field, FD_LONG, &Value, 1); @@ -1820,29 +1890,29 @@ struct vpSetCommand { LONG Index; struct PathCommand * Command; LONG Size; }; struct vpGetCommand { LONG Index; struct PathCommand * Command; }; struct vpSetCommandList { APTR Commands; LONG Size; }; -INLINE ERROR vpAddCommand(APTR Ob, struct PathCommand * Commands, LONG Size) { +INLINE ERR vpAddCommand(APTR Ob, struct PathCommand * Commands, LONG Size) noexcept { struct vpAddCommand args = { Commands, Size }; return(Action(MT_VPAddCommand, (OBJECTPTR)Ob, &args)); } -INLINE ERROR vpRemoveCommand(APTR Ob, LONG Index, LONG Total) { +INLINE ERR vpRemoveCommand(APTR Ob, LONG Index, LONG Total) noexcept { struct vpRemoveCommand args = { Index, Total }; return(Action(MT_VPRemoveCommand, (OBJECTPTR)Ob, &args)); } -INLINE ERROR vpSetCommand(APTR Ob, LONG Index, struct PathCommand * Command, LONG Size) { +INLINE ERR vpSetCommand(APTR Ob, LONG Index, struct PathCommand * Command, LONG Size) noexcept { struct vpSetCommand args = { Index, Command, Size }; return(Action(MT_VPSetCommand, (OBJECTPTR)Ob, &args)); } -INLINE ERROR vpGetCommand(APTR Ob, LONG Index, struct PathCommand ** Command) { +INLINE ERR vpGetCommand(APTR Ob, LONG Index, struct PathCommand ** Command) noexcept { struct vpGetCommand args = { Index, (struct PathCommand *)0 }; - ERROR error = Action(MT_VPGetCommand, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_VPGetCommand, (OBJECTPTR)Ob, &args); if (Command) *Command = args.Command; return(error); } -INLINE ERROR vpSetCommandList(APTR Ob, APTR Commands, LONG Size) { +INLINE ERR vpSetCommandList(APTR Ob, APTR Commands, LONG Size) noexcept { struct vpSetCommandList args = { Commands, Size }; return(Action(MT_VPSetCommandList, (OBJECTPTR)Ob, &args)); } @@ -1866,7 +1936,7 @@ class objVectorPath : public objVector { struct vtDeleteLine { LONG Line; }; -INLINE ERROR vtDeleteLine(APTR Ob, LONG Line) { +INLINE ERR vtDeleteLine(APTR Ob, LONG Line) noexcept { struct vtDeleteLine args = { Line }; return(Action(MT_VTDeleteLine, (OBJECTPTR)Ob, &args)); } @@ -1880,6 +1950,18 @@ class objVectorText : public objVector { using create = pf::Create; }; +// VectorGroup class definition + +#define VER_VECTORGROUP (1.000000) + +class objVectorGroup : public objVector { + public: + static constexpr CLASSID CLASS_ID = ID_VECTORGROUP; + static constexpr CSTRING CLASS_NAME = "VectorGroup"; + + using create = pf::Create; +}; + // VectorWave class definition #define VER_VECTORWAVE (1.000000) @@ -1952,18 +2034,6 @@ class objVectorEllipse : public objVector { using create = pf::Create; }; -// VectorClip class definition - -#define VER_VECTORCLIP (1.000000) - -class objVectorClip : public objVector { - public: - static constexpr CLASSID CLASS_ID = ID_VECTORCLIP; - static constexpr CSTRING CLASS_NAME = "VectorClip"; - - using create = pf::Create; -}; - // VectorViewport class definition #define VER_VECTORVIEWPORT (1.000000) @@ -1984,12 +2054,12 @@ class objVectorViewport : public objVector { struct VectorBase { #ifndef PARASOL_STATIC - ERROR (*_DrawPath)(objBitmap * Bitmap, APTR Path, DOUBLE StrokeWidth, OBJECTPTR StrokeStyle, OBJECTPTR FillStyle); + ERR (*_DrawPath)(objBitmap * Bitmap, APTR Path, DOUBLE StrokeWidth, OBJECTPTR StrokeStyle, OBJECTPTR FillStyle); void (*_FreePath)(APTR Path); - ERROR (*_GenerateEllipse)(DOUBLE CX, DOUBLE CY, DOUBLE RX, DOUBLE RY, LONG Vertices, APTR Path); - ERROR (*_GeneratePath)(CSTRING Sequence, APTR Path); - ERROR (*_GenerateRectangle)(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height, APTR Path); - ERROR (*_ReadPainter)(objVectorScene * Scene, CSTRING IRI, struct FRGB * RGB, objVectorGradient ** Gradient, objVectorImage ** Image, objVectorPattern ** Pattern); + ERR (*_GenerateEllipse)(DOUBLE CX, DOUBLE CY, DOUBLE RX, DOUBLE RY, LONG Vertices, APTR Path); + ERR (*_GeneratePath)(CSTRING Sequence, APTR Path); + ERR (*_GenerateRectangle)(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height, APTR Path); + ERR (*_ReadPainter)(objVectorScene * Scene, CSTRING IRI, struct VectorPainter * Painter, CSTRING * Result); void (*_TranslatePath)(APTR Path, DOUBLE X, DOUBLE Y); void (*_MoveTo)(APTR Path, DOUBLE X, DOUBLE Y); void (*_LineTo)(APTR Path, DOUBLE X, DOUBLE Y); @@ -2001,27 +2071,32 @@ struct VectorBase { void (*_ClosePath)(APTR Path); void (*_RewindPath)(APTR Path); LONG (*_GetVertex)(APTR Path, DOUBLE * X, DOUBLE * Y); - ERROR (*_ApplyPath)(APTR Path, OBJECTPTR VectorPath); - ERROR (*_Rotate)(struct VectorMatrix * Matrix, DOUBLE Angle, DOUBLE CenterX, DOUBLE CenterY); - ERROR (*_Translate)(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y); - ERROR (*_Skew)(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y); - ERROR (*_Multiply)(struct VectorMatrix * Matrix, DOUBLE ScaleX, DOUBLE ShearY, DOUBLE ShearX, DOUBLE ScaleY, DOUBLE TranslateX, DOUBLE TranslateY); - ERROR (*_MultiplyMatrix)(struct VectorMatrix * Target, struct VectorMatrix * Source); - ERROR (*_Scale)(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y); - ERROR (*_ParseTransform)(struct VectorMatrix * Matrix, CSTRING Transform); - ERROR (*_ResetMatrix)(struct VectorMatrix * Matrix); + ERR (*_ApplyPath)(APTR Path, OBJECTPTR VectorPath); + ERR (*_Rotate)(struct VectorMatrix * Matrix, DOUBLE Angle, DOUBLE CenterX, DOUBLE CenterY); + ERR (*_Translate)(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y); + ERR (*_Skew)(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y); + ERR (*_Multiply)(struct VectorMatrix * Matrix, DOUBLE ScaleX, DOUBLE ShearY, DOUBLE ShearX, DOUBLE ScaleY, DOUBLE TranslateX, DOUBLE TranslateY); + ERR (*_MultiplyMatrix)(struct VectorMatrix * Target, struct VectorMatrix * Source); + ERR (*_Scale)(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y); + ERR (*_ParseTransform)(struct VectorMatrix * Matrix, CSTRING Transform); + ERR (*_ResetMatrix)(struct VectorMatrix * Matrix); + ERR (*_GetFontHandle)(CSTRING Family, CSTRING Style, LONG Weight, LONG Size, APTR Handle); + ERR (*_GetFontMetrics)(APTR Handle, struct FontMetrics * Info); + DOUBLE (*_CharWidth)(APTR FontHandle, ULONG Char, ULONG KChar, DOUBLE * Kerning); + DOUBLE (*_StringWidth)(APTR FontHandle, CSTRING String, LONG Chars); + ERR (*_FlushMatrix)(struct VectorMatrix * Matrix); #endif // PARASOL_STATIC }; #ifndef PRV_VECTOR_MODULE #ifndef PARASOL_STATIC extern struct VectorBase *VectorBase; -inline ERROR vecDrawPath(objBitmap * Bitmap, APTR Path, DOUBLE StrokeWidth, OBJECTPTR StrokeStyle, OBJECTPTR FillStyle) { return VectorBase->_DrawPath(Bitmap,Path,StrokeWidth,StrokeStyle,FillStyle); } +inline ERR vecDrawPath(objBitmap * Bitmap, APTR Path, DOUBLE StrokeWidth, OBJECTPTR StrokeStyle, OBJECTPTR FillStyle) { return VectorBase->_DrawPath(Bitmap,Path,StrokeWidth,StrokeStyle,FillStyle); } inline void vecFreePath(APTR Path) { return VectorBase->_FreePath(Path); } -inline ERROR vecGenerateEllipse(DOUBLE CX, DOUBLE CY, DOUBLE RX, DOUBLE RY, LONG Vertices, APTR Path) { return VectorBase->_GenerateEllipse(CX,CY,RX,RY,Vertices,Path); } -inline ERROR vecGeneratePath(CSTRING Sequence, APTR Path) { return VectorBase->_GeneratePath(Sequence,Path); } -inline ERROR vecGenerateRectangle(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height, APTR Path) { return VectorBase->_GenerateRectangle(X,Y,Width,Height,Path); } -inline ERROR vecReadPainter(objVectorScene * Scene, CSTRING IRI, struct FRGB * RGB, objVectorGradient ** Gradient, objVectorImage ** Image, objVectorPattern ** Pattern) { return VectorBase->_ReadPainter(Scene,IRI,RGB,Gradient,Image,Pattern); } +inline ERR vecGenerateEllipse(DOUBLE CX, DOUBLE CY, DOUBLE RX, DOUBLE RY, LONG Vertices, APTR Path) { return VectorBase->_GenerateEllipse(CX,CY,RX,RY,Vertices,Path); } +inline ERR vecGeneratePath(CSTRING Sequence, APTR Path) { return VectorBase->_GeneratePath(Sequence,Path); } +inline ERR vecGenerateRectangle(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height, APTR Path) { return VectorBase->_GenerateRectangle(X,Y,Width,Height,Path); } +inline ERR vecReadPainter(objVectorScene * Scene, CSTRING IRI, struct VectorPainter * Painter, CSTRING * Result) { return VectorBase->_ReadPainter(Scene,IRI,Painter,Result); } inline void vecTranslatePath(APTR Path, DOUBLE X, DOUBLE Y) { return VectorBase->_TranslatePath(Path,X,Y); } inline void vecMoveTo(APTR Path, DOUBLE X, DOUBLE Y) { return VectorBase->_MoveTo(Path,X,Y); } inline void vecLineTo(APTR Path, DOUBLE X, DOUBLE Y) { return VectorBase->_LineTo(Path,X,Y); } @@ -2033,23 +2108,28 @@ inline void vecSmooth4(APTR Path, DOUBLE CtrlX, DOUBLE CtrlY, DOUBLE X, DOUBLE Y inline void vecClosePath(APTR Path) { return VectorBase->_ClosePath(Path); } inline void vecRewindPath(APTR Path) { return VectorBase->_RewindPath(Path); } inline LONG vecGetVertex(APTR Path, DOUBLE * X, DOUBLE * Y) { return VectorBase->_GetVertex(Path,X,Y); } -inline ERROR vecApplyPath(APTR Path, OBJECTPTR VectorPath) { return VectorBase->_ApplyPath(Path,VectorPath); } -inline ERROR vecRotate(struct VectorMatrix * Matrix, DOUBLE Angle, DOUBLE CenterX, DOUBLE CenterY) { return VectorBase->_Rotate(Matrix,Angle,CenterX,CenterY); } -inline ERROR vecTranslate(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y) { return VectorBase->_Translate(Matrix,X,Y); } -inline ERROR vecSkew(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y) { return VectorBase->_Skew(Matrix,X,Y); } -inline ERROR vecMultiply(struct VectorMatrix * Matrix, DOUBLE ScaleX, DOUBLE ShearY, DOUBLE ShearX, DOUBLE ScaleY, DOUBLE TranslateX, DOUBLE TranslateY) { return VectorBase->_Multiply(Matrix,ScaleX,ShearY,ShearX,ScaleY,TranslateX,TranslateY); } -inline ERROR vecMultiplyMatrix(struct VectorMatrix * Target, struct VectorMatrix * Source) { return VectorBase->_MultiplyMatrix(Target,Source); } -inline ERROR vecScale(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y) { return VectorBase->_Scale(Matrix,X,Y); } -inline ERROR vecParseTransform(struct VectorMatrix * Matrix, CSTRING Transform) { return VectorBase->_ParseTransform(Matrix,Transform); } -inline ERROR vecResetMatrix(struct VectorMatrix * Matrix) { return VectorBase->_ResetMatrix(Matrix); } +inline ERR vecApplyPath(APTR Path, OBJECTPTR VectorPath) { return VectorBase->_ApplyPath(Path,VectorPath); } +inline ERR vecRotate(struct VectorMatrix * Matrix, DOUBLE Angle, DOUBLE CenterX, DOUBLE CenterY) { return VectorBase->_Rotate(Matrix,Angle,CenterX,CenterY); } +inline ERR vecTranslate(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y) { return VectorBase->_Translate(Matrix,X,Y); } +inline ERR vecSkew(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y) { return VectorBase->_Skew(Matrix,X,Y); } +inline ERR vecMultiply(struct VectorMatrix * Matrix, DOUBLE ScaleX, DOUBLE ShearY, DOUBLE ShearX, DOUBLE ScaleY, DOUBLE TranslateX, DOUBLE TranslateY) { return VectorBase->_Multiply(Matrix,ScaleX,ShearY,ShearX,ScaleY,TranslateX,TranslateY); } +inline ERR vecMultiplyMatrix(struct VectorMatrix * Target, struct VectorMatrix * Source) { return VectorBase->_MultiplyMatrix(Target,Source); } +inline ERR vecScale(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y) { return VectorBase->_Scale(Matrix,X,Y); } +inline ERR vecParseTransform(struct VectorMatrix * Matrix, CSTRING Transform) { return VectorBase->_ParseTransform(Matrix,Transform); } +inline ERR vecResetMatrix(struct VectorMatrix * Matrix) { return VectorBase->_ResetMatrix(Matrix); } +inline ERR vecGetFontHandle(CSTRING Family, CSTRING Style, LONG Weight, LONG Size, APTR Handle) { return VectorBase->_GetFontHandle(Family,Style,Weight,Size,Handle); } +inline ERR vecGetFontMetrics(APTR Handle, struct FontMetrics * Info) { return VectorBase->_GetFontMetrics(Handle,Info); } +inline DOUBLE vecCharWidth(APTR FontHandle, ULONG Char, ULONG KChar, DOUBLE * Kerning) { return VectorBase->_CharWidth(FontHandle,Char,KChar,Kerning); } +inline DOUBLE vecStringWidth(APTR FontHandle, CSTRING String, LONG Chars) { return VectorBase->_StringWidth(FontHandle,String,Chars); } +inline ERR vecFlushMatrix(struct VectorMatrix * Matrix) { return VectorBase->_FlushMatrix(Matrix); } #else extern "C" { -extern ERROR vecDrawPath(objBitmap * Bitmap, APTR Path, DOUBLE StrokeWidth, OBJECTPTR StrokeStyle, OBJECTPTR FillStyle); +extern ERR vecDrawPath(objBitmap * Bitmap, APTR Path, DOUBLE StrokeWidth, OBJECTPTR StrokeStyle, OBJECTPTR FillStyle); extern void vecFreePath(APTR Path); -extern ERROR vecGenerateEllipse(DOUBLE CX, DOUBLE CY, DOUBLE RX, DOUBLE RY, LONG Vertices, APTR Path); -extern ERROR vecGeneratePath(CSTRING Sequence, APTR Path); -extern ERROR vecGenerateRectangle(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height, APTR Path); -extern ERROR vecReadPainter(objVectorScene * Scene, CSTRING IRI, struct FRGB * RGB, objVectorGradient ** Gradient, objVectorImage ** Image, objVectorPattern ** Pattern); +extern ERR vecGenerateEllipse(DOUBLE CX, DOUBLE CY, DOUBLE RX, DOUBLE RY, LONG Vertices, APTR Path); +extern ERR vecGeneratePath(CSTRING Sequence, APTR Path); +extern ERR vecGenerateRectangle(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height, APTR Path); +extern ERR vecReadPainter(objVectorScene * Scene, CSTRING IRI, struct VectorPainter * Painter, CSTRING * Result); extern void vecTranslatePath(APTR Path, DOUBLE X, DOUBLE Y); extern void vecMoveTo(APTR Path, DOUBLE X, DOUBLE Y); extern void vecLineTo(APTR Path, DOUBLE X, DOUBLE Y); @@ -2061,22 +2141,43 @@ extern void vecSmooth4(APTR Path, DOUBLE CtrlX, DOUBLE CtrlY, DOUBLE X, DOUBLE Y extern void vecClosePath(APTR Path); extern void vecRewindPath(APTR Path); extern LONG vecGetVertex(APTR Path, DOUBLE * X, DOUBLE * Y); -extern ERROR vecApplyPath(APTR Path, OBJECTPTR VectorPath); -extern ERROR vecRotate(struct VectorMatrix * Matrix, DOUBLE Angle, DOUBLE CenterX, DOUBLE CenterY); -extern ERROR vecTranslate(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y); -extern ERROR vecSkew(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y); -extern ERROR vecMultiply(struct VectorMatrix * Matrix, DOUBLE ScaleX, DOUBLE ShearY, DOUBLE ShearX, DOUBLE ScaleY, DOUBLE TranslateX, DOUBLE TranslateY); -extern ERROR vecMultiplyMatrix(struct VectorMatrix * Target, struct VectorMatrix * Source); -extern ERROR vecScale(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y); -extern ERROR vecParseTransform(struct VectorMatrix * Matrix, CSTRING Transform); -extern ERROR vecResetMatrix(struct VectorMatrix * Matrix); +extern ERR vecApplyPath(APTR Path, OBJECTPTR VectorPath); +extern ERR vecRotate(struct VectorMatrix * Matrix, DOUBLE Angle, DOUBLE CenterX, DOUBLE CenterY); +extern ERR vecTranslate(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y); +extern ERR vecSkew(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y); +extern ERR vecMultiply(struct VectorMatrix * Matrix, DOUBLE ScaleX, DOUBLE ShearY, DOUBLE ShearX, DOUBLE ScaleY, DOUBLE TranslateX, DOUBLE TranslateY); +extern ERR vecMultiplyMatrix(struct VectorMatrix * Target, struct VectorMatrix * Source); +extern ERR vecScale(struct VectorMatrix * Matrix, DOUBLE X, DOUBLE Y); +extern ERR vecParseTransform(struct VectorMatrix * Matrix, CSTRING Transform); +extern ERR vecResetMatrix(struct VectorMatrix * Matrix); +extern ERR vecGetFontHandle(CSTRING Family, CSTRING Style, LONG Weight, LONG Size, APTR Handle); +extern ERR vecGetFontMetrics(APTR Handle, struct FontMetrics * Info); +extern DOUBLE vecCharWidth(APTR FontHandle, ULONG Char, ULONG KChar, DOUBLE * Kerning); +extern DOUBLE vecStringWidth(APTR FontHandle, CSTRING String, LONG Chars); +extern ERR vecFlushMatrix(struct VectorMatrix * Matrix); } #endif // PARASOL_STATIC #endif + //******************************************************************************************************************** -INLINE void SET_VECTOR_COLOUR(objVectorColour *Colour, DOUBLE Red, DOUBLE Green, DOUBLE Blue, DOUBLE Alpha) { +inline void operator*=(VectorMatrix &This, const VectorMatrix &Other) +{ + DOUBLE t0 = This.ScaleX * Other.ScaleX + This.ShearY * Other.ShearX; + DOUBLE t2 = This.ShearX * Other.ScaleX + This.ScaleY * Other.ShearX; + DOUBLE t4 = This.TranslateX * Other.ScaleX + This.TranslateY * Other.ShearX + Other.TranslateX; + This.ShearY = This.ScaleX * Other.ShearY + This.ShearY * Other.ScaleY; + This.ScaleY = This.ShearX * Other.ShearY + This.ScaleY * Other.ScaleY; + This.TranslateY = This.TranslateX * Other.ShearY + This.TranslateY * Other.ScaleY + Other.TranslateY; + This.ScaleX = t0; + This.ShearX = t2; + This.TranslateX = t4; +} + +//******************************************************************************************************************** + +inline void SET_VECTOR_COLOUR(objVectorColour *Colour, DOUBLE Red, DOUBLE Green, DOUBLE Blue, DOUBLE Alpha) { Colour->Class->ClassID = ID_VECTORCOLOUR; Colour->Red = Red; Colour->Green = Green; @@ -2087,6 +2188,7 @@ INLINE void SET_VECTOR_COLOUR(objVectorColour *Colour, DOUBLE Red, DOUBLE Green, #define SVF_ACHROMATOMALY 0xc3f37036 #define SVF_ACHROMATOPSIA 0xc3f56170 #define SVF_ALIGN 0x0f174e50 +#define SVF_ALT_FILL 0x8c3507fa #define SVF_AMPLITUDE 0x5e60600a #define SVF_ANIMATEMOTION 0x8a27c6ba #define SVF_ANIMATETRANSFORM 0x6349c940 @@ -2151,6 +2253,7 @@ INLINE void SET_VECTOR_COLOUR(objVectorColour *Colour, DOUBLE Red, DOUBLE Green, #define SVF_FEDIFFUSELIGHTING 0xf094ecac #define SVF_FEDISPLACEMENTMAP 0xb9cf0a67 #define SVF_FEDISTANTLIGHT 0x12a0c2ff +#define SVF_FEDROPSHADOW 0x1c907ecb #define SVF_FEFLOOD 0xa27fbd04 #define SVF_FEGAUSSIANBLUR 0xfdba17c0 #define SVF_FEIMAGE 0xa2b65653 @@ -2312,6 +2415,7 @@ INLINE void SET_VECTOR_COLOUR(objVectorColour *Colour, DOUBLE Red, DOUBLE Green, #define SVF_X 0x0002b61d #define SVF_X1 0x005979ee #define SVF_X2 0x005979ef +#define SVF_XOFFSET 0x23685e64 #define SVF_XLINK_HREF 0x379480aa #define SVF_XML_SPACE 0x2db612fc #define SVF_XMLNS 0x10b81bf7 @@ -2319,6 +2423,7 @@ INLINE void SET_VECTOR_COLOUR(objVectorColour *Colour, DOUBLE Red, DOUBLE Green, #define SVF_Y 0x0002b61e #define SVF_Y1 0x00597a0f #define SVF_Y2 0x00597a10 +#define SVF_YOFFSET 0x70629b25 #define SVF_Z 0x0002b61f #define SVF_ACCUMULATE 0x5c660bc9 @@ -2541,6 +2646,9 @@ INLINE void SET_VECTOR_COLOUR(objVectorColour *Colour, DOUBLE Red, DOUBLE Green, #define SVF_LIGHTING_COLOR 0x020fc127 #define SVF_LIGHTING_COLOUR 0x4407e6dc #define SVF_LIMITINGCONEANGLE 0xbb90036e +#define SVF_LOOP_LIMIT 0xfaf3e6cb +#define SVF_MASKCONTENTUNITS 0x3fe629df +#define SVF_MASKUNITS 0xa68eea04 #define SVF_POINTSATX 0xf4c77f0f #define SVF_POINTSATY 0xf4c77f10 #define SVF_POINTSATZ 0xf4c77f11 @@ -2566,3 +2674,48 @@ INLINE void SET_VECTOR_COLOUR(objVectorColour *Colour, DOUBLE Red, DOUBLE Green, #define SVF_EXTRA_EXPANDED 0x8c599b5f #define SVF_ULTRA_EXPANDED 0x87e8c363 + +INLINE ERR vecSubscribeInput(APTR Ob, JTYPE Mask, FUNCTION Callback) { + struct vecSubscribeInput args = { Mask, &Callback }; + return(Action(MT_VecSubscribeInput, (OBJECTPTR)Ob, &args)); +} + +INLINE ERR vecSubscribeKeyboard(APTR Ob, FUNCTION Callback) { + struct vecSubscribeKeyboard args = { &Callback }; + return(Action(MT_VecSubscribeKeyboard, (OBJECTPTR)Ob, &args)); +} + +INLINE ERR vecSubscribeFeedback(APTR Ob, FM Mask, FUNCTION Callback) { + struct vecSubscribeFeedback args = { Mask, &Callback }; + return(Action(MT_VecSubscribeFeedback, (OBJECTPTR)Ob, &args)); +} + +namespace fl { + using namespace pf; + +constexpr FieldValue Flags(VCLF Value) { return FieldValue(FID_Flags, LONG(Value)); } + +constexpr FieldValue DragCallback(const FUNCTION &Value) { return FieldValue(FID_DragCallback, &Value); } +constexpr FieldValue DragCallback(const FUNCTION *Value) { return FieldValue(FID_DragCallback, Value); } + +constexpr FieldValue TextFlags(VTXF Value) { return FieldValue(FID_TextFlags, LONG(Value)); } +constexpr FieldValue Overflow(VOF Value) { return FieldValue(FID_Overflow, LONG(Value)); } + +constexpr FieldValue Sequence(CSTRING Value) { return FieldValue(FID_Sequence, Value); } +inline FieldValue Sequence(std::string &Value) { return FieldValue(FID_Sequence, Value.c_str()); } + +constexpr FieldValue FontStyle(CSTRING Value) { return FieldValue(FID_FontStyle, Value); } +inline FieldValue FontStyle(std::string &Value) { return FieldValue(FID_FontStyle, Value.c_str()); } + +template FieldValue RoundX(T Value) { + static_assert(std::is_arithmetic::value || std::is_base_of_v, "RoundX value must be numeric"); + return FieldValue(FID_RoundX, Value); +} + +template FieldValue RoundY(T Value) { + static_assert(std::is_arithmetic::value || std::is_base_of_v, "RoundY value must be numeric"); + return FieldValue(FID_RoundY, Value); +} + +} + diff --git a/include/parasol/modules/xml.h b/include/parasol/modules/xml.h index d695555f4..b916bc38a 100644 --- a/include/parasol/modules/xml.h +++ b/include/parasol/modules/xml.h @@ -1,7 +1,7 @@ #pragma once // Name: xml.h -// Copyright: Paul Manias © 2001-2023 +// Copyright: Paul Manias © 2001-2024 // Generator: idl-c #include @@ -10,6 +10,7 @@ #ifdef __cplusplus #include +#include #endif class objXML; @@ -109,10 +110,21 @@ typedef struct XMLTag { inline const std::string * attrib(const std::string &Name) const { for (unsigned a=1; a < Attribs.size(); a++) { - if (!StrMatch(Attribs[a].Name, Name)) return &Attribs[a].Value; + if (StrMatch(Attribs[a].Name, Name) IS ERR::Okay) return &Attribs[a].Value; } return NULL; } + + inline std::string getContent() const { + if (Children.empty()) return std::string(""); + + std::ostringstream str; + for (auto &scan : Children) { + if (scan.Attribs.empty()) continue; // Sanity check + if (scan.Attribs[0].isContent()) str << scan.Attribs[0].Value; + } + return str.str(); + } } XMLTAG; // XML class definition @@ -122,7 +134,7 @@ typedef struct XMLTag { // XML methods #define MT_XMLSetAttrib -1 -#define MT_XMLGetString -2 +#define MT_XMLSerialise -2 #define MT_XMLInsertXML -3 #define MT_XMLGetContent -4 #define MT_XMLSort -5 @@ -138,7 +150,7 @@ typedef struct XMLTag { #define MT_XMLGetTag -18 struct xmlSetAttrib { LONG Index; LONG Attrib; CSTRING Name; CSTRING Value; }; -struct xmlGetString { LONG Index; XMF Flags; STRING Result; }; +struct xmlSerialise { LONG Index; XMF Flags; STRING Result; }; struct xmlInsertXML { LONG Index; XMI Where; CSTRING XML; LONG Result; }; struct xmlGetContent { LONG Index; STRING Buffer; LONG Length; }; struct xmlSort { CSTRING XPath; CSTRING Sort; XSF Flags; }; @@ -153,93 +165,93 @@ struct xmlInsertContent { LONG Index; XMI Where; CSTRING Content; LONG Result; struct xmlRemoveXPath { CSTRING XPath; LONG Limit; }; struct xmlGetTag { LONG Index; struct XMLTag * Result; }; -INLINE ERROR xmlSetAttrib(APTR Ob, LONG Index, LONG Attrib, CSTRING Name, CSTRING Value) { +INLINE ERR xmlSetAttrib(APTR Ob, LONG Index, LONG Attrib, CSTRING Name, CSTRING Value) noexcept { struct xmlSetAttrib args = { Index, Attrib, Name, Value }; return(Action(MT_XMLSetAttrib, (OBJECTPTR)Ob, &args)); } -INLINE ERROR xmlGetString(APTR Ob, LONG Index, XMF Flags, STRING * Result) { - struct xmlGetString args = { Index, Flags, (STRING)0 }; - ERROR error = Action(MT_XMLGetString, (OBJECTPTR)Ob, &args); +INLINE ERR xmlSerialise(APTR Ob, LONG Index, XMF Flags, STRING * Result) noexcept { + struct xmlSerialise args = { Index, Flags, (STRING)0 }; + ERR error = Action(MT_XMLSerialise, (OBJECTPTR)Ob, &args); if (Result) *Result = args.Result; return(error); } -INLINE ERROR xmlInsertXML(APTR Ob, LONG Index, XMI Where, CSTRING XML, LONG * Result) { +INLINE ERR xmlInsertXML(APTR Ob, LONG Index, XMI Where, CSTRING XML, LONG * Result) noexcept { struct xmlInsertXML args = { Index, Where, XML, (LONG)0 }; - ERROR error = Action(MT_XMLInsertXML, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_XMLInsertXML, (OBJECTPTR)Ob, &args); if (Result) *Result = args.Result; return(error); } -INLINE ERROR xmlGetContent(APTR Ob, LONG Index, STRING Buffer, LONG Length) { +INLINE ERR xmlGetContent(APTR Ob, LONG Index, STRING Buffer, LONG Length) noexcept { struct xmlGetContent args = { Index, Buffer, Length }; return(Action(MT_XMLGetContent, (OBJECTPTR)Ob, &args)); } -INLINE ERROR xmlSort(APTR Ob, CSTRING XPath, CSTRING Sort, XSF Flags) { +INLINE ERR xmlSort(APTR Ob, CSTRING XPath, CSTRING Sort, XSF Flags) noexcept { struct xmlSort args = { XPath, Sort, Flags }; return(Action(MT_XMLSort, (OBJECTPTR)Ob, &args)); } -INLINE ERROR xmlRemoveTag(APTR Ob, LONG Index, LONG Total) { +INLINE ERR xmlRemoveTag(APTR Ob, LONG Index, LONG Total) noexcept { struct xmlRemoveTag args = { Index, Total }; return(Action(MT_XMLRemoveTag, (OBJECTPTR)Ob, &args)); } -INLINE ERROR xmlMoveTags(APTR Ob, LONG Index, LONG Total, LONG DestIndex, XMI Where) { +INLINE ERR xmlMoveTags(APTR Ob, LONG Index, LONG Total, LONG DestIndex, XMI Where) noexcept { struct xmlMoveTags args = { Index, Total, DestIndex, Where }; return(Action(MT_XMLMoveTags, (OBJECTPTR)Ob, &args)); } -INLINE ERROR xmlGetAttrib(APTR Ob, LONG Index, CSTRING Attrib, CSTRING * Value) { +INLINE ERR xmlGetAttrib(APTR Ob, LONG Index, CSTRING Attrib, CSTRING * Value) noexcept { struct xmlGetAttrib args = { Index, Attrib, (CSTRING)0 }; - ERROR error = Action(MT_XMLGetAttrib, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_XMLGetAttrib, (OBJECTPTR)Ob, &args); if (Value) *Value = args.Value; return(error); } -INLINE ERROR xmlInsertXPath(APTR Ob, CSTRING XPath, XMI Where, CSTRING XML, LONG * Result) { +INLINE ERR xmlInsertXPath(APTR Ob, CSTRING XPath, XMI Where, CSTRING XML, LONG * Result) noexcept { struct xmlInsertXPath args = { XPath, Where, XML, (LONG)0 }; - ERROR error = Action(MT_XMLInsertXPath, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_XMLInsertXPath, (OBJECTPTR)Ob, &args); if (Result) *Result = args.Result; return(error); } -INLINE ERROR xmlFindTag(APTR Ob, CSTRING XPath, FUNCTION * Callback, LONG * Result) { +INLINE ERR xmlFindTag(APTR Ob, CSTRING XPath, FUNCTION * Callback, LONG * Result) noexcept { struct xmlFindTag args = { XPath, Callback, (LONG)0 }; - ERROR error = Action(MT_XMLFindTag, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_XMLFindTag, (OBJECTPTR)Ob, &args); if (Result) *Result = args.Result; return(error); } -INLINE ERROR xmlFilter(APTR Ob, CSTRING XPath) { +INLINE ERR xmlFilter(APTR Ob, CSTRING XPath) noexcept { struct xmlFilter args = { XPath }; return(Action(MT_XMLFilter, (OBJECTPTR)Ob, &args)); } -INLINE ERROR xmlCount(APTR Ob, CSTRING XPath, LONG * Result) { +INLINE ERR xmlCount(APTR Ob, CSTRING XPath, LONG * Result) noexcept { struct xmlCount args = { XPath, (LONG)0 }; - ERROR error = Action(MT_XMLCount, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_XMLCount, (OBJECTPTR)Ob, &args); if (Result) *Result = args.Result; return(error); } -INLINE ERROR xmlInsertContent(APTR Ob, LONG Index, XMI Where, CSTRING Content, LONG * Result) { +INLINE ERR xmlInsertContent(APTR Ob, LONG Index, XMI Where, CSTRING Content, LONG * Result) noexcept { struct xmlInsertContent args = { Index, Where, Content, (LONG)0 }; - ERROR error = Action(MT_XMLInsertContent, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_XMLInsertContent, (OBJECTPTR)Ob, &args); if (Result) *Result = args.Result; return(error); } -INLINE ERROR xmlRemoveXPath(APTR Ob, CSTRING XPath, LONG Limit) { +INLINE ERR xmlRemoveXPath(APTR Ob, CSTRING XPath, LONG Limit) noexcept { struct xmlRemoveXPath args = { XPath, Limit }; return(Action(MT_XMLRemoveXPath, (OBJECTPTR)Ob, &args)); } -INLINE ERROR xmlGetTag(APTR Ob, LONG Index, struct XMLTag ** Result) { +INLINE ERR xmlGetTag(APTR Ob, LONG Index, struct XMLTag ** Result) noexcept { struct xmlGetTag args = { Index, (struct XMLTag *)0 }; - ERROR error = Action(MT_XMLGetTag, (OBJECTPTR)Ob, &args); + ERR error = Action(MT_XMLGetTag, (OBJECTPTR)Ob, &args); if (Result) *Result = args.Result; return(error); } @@ -257,7 +269,7 @@ class objXML : public BaseClass { XMF Flags; // Optional flags. LONG Start; // Set a starting cursor to affect the starting point for some XML operations. LONG Modified; // A timestamp of when the XML data was last modified. - LONG ParseError; // Private + ERR ParseError; // Private LONG LineNo; // Private public: typedef pf::vector TAGS; @@ -266,59 +278,59 @@ class objXML : public BaseClass { // Action stubs - inline ERROR clear() { return Action(AC_Clear, this, NULL); } - inline ERROR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) { + inline ERR clear() noexcept { return Action(AC_Clear, this, NULL); } + inline ERR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) noexcept { struct acDataFeed args = { Object, Datatype, Buffer, Size }; return Action(AC_DataFeed, this, &args); } - inline ERROR getVar(CSTRING FieldName, STRING Buffer, LONG Size) { + inline ERR getVar(CSTRING FieldName, STRING Buffer, LONG Size) noexcept { struct acGetVar args = { FieldName, Buffer, Size }; - ERROR error = Action(AC_GetVar, this, &args); - if ((error) and (Buffer)) Buffer[0] = 0; + auto error = Action(AC_GetVar, this, &args); + if ((error != ERR::Okay) and (Buffer)) Buffer[0] = 0; return error; } - inline ERROR init() { return InitObject(this); } - inline ERROR reset() { return Action(AC_Reset, this, NULL); } - inline ERROR saveToObject(OBJECTPTR Dest, CLASSID ClassID = 0) { + inline ERR init() noexcept { return InitObject(this); } + inline ERR reset() noexcept { return Action(AC_Reset, this, NULL); } + inline ERR saveToObject(OBJECTPTR Dest, CLASSID ClassID = 0) noexcept { struct acSaveToObject args = { Dest, { ClassID } }; return Action(AC_SaveToObject, this, &args); } - inline ERROR acSetVar(CSTRING FieldName, CSTRING Value) { + inline ERR acSetVar(CSTRING FieldName, CSTRING Value) noexcept { struct acSetVar args = { FieldName, Value }; return Action(AC_SetVar, this, &args); } // Customised field setting - template inline ERROR setPath(T && Value) { + template inline ERR setPath(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[9]; return field->WriteValue(target, field, 0x08800300, to_cstring(Value), 1); } - inline ERROR setSource(OBJECTPTR Value) { - if (this->initialised()) return ERR_NoFieldAccess; + inline ERR setSource(OBJECTPTR Value) noexcept { + if (this->initialised()) return ERR::NoFieldAccess; this->Source = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setFlags(const XMF Value) { + inline ERR setFlags(const XMF Value) noexcept { this->Flags = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setStart(const LONG Value) { + inline ERR setStart(const LONG Value) noexcept { this->Start = Value; - return ERR_Okay; + return ERR::Okay; } - inline ERROR setReadOnly(const LONG Value) { + inline ERR setReadOnly(const LONG Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[14]; return field->WriteValue(target, field, FD_LONG, &Value, 1); } - template inline ERROR setStatement(T && Value) { + template inline ERR setStatement(T && Value) noexcept { auto target = this; auto field = &this->Class->Dictionary[11]; return field->WriteValue(target, field, 0x08800320, to_cstring(Value), 1); @@ -328,13 +340,13 @@ class objXML : public BaseClass { //******************************************************************************************************************** -template inline ERROR xmlSetAttribValue(objXML *XML, LONG Tag, LONG Flags, T &&Attrib, LONG Value) { +template inline ERR xmlSetAttribValue(objXML *XML, LONG Tag, LONG Flags, T &&Attrib, LONG Value) { auto attrib = to_cstring(Attrib); auto buffer = std::to_string(Value); return xmlSetAttrib(XML, Tag, Flags, attrib, buffer.c_str()); } -template inline ERROR xmlSetAttribValue(objXML *XML, LONG Tag, LONG Flags, T &&Attrib, DOUBLE Value) { +template inline ERR xmlSetAttribValue(objXML *XML, LONG Tag, LONG Flags, T &&Attrib, DOUBLE Value) { auto attrib = to_cstring(Attrib); auto buffer = std::to_string(Value); return xmlSetAttrib(XML, Tag, Flags, attrib, buffer.c_str()); @@ -343,7 +355,7 @@ template inline ERROR xmlSetAttribValue(objXML *XML, LONG Tag, LONG Fl inline void xmlUpdateAttrib(XMLTag &Tag, const std::string Name, const std::string Value, bool CanCreate = false) { for (auto a = Tag.Attribs.begin(); a != Tag.Attribs.end(); a++) { - if (!StrMatch(Name, a->Name)) { + if (StrMatch(Name, a->Name) IS ERR::Okay) { a->Name = Name; a->Value = Value; return; @@ -370,15 +382,16 @@ inline std::string xmlGetContent(const XMLTag &Tag) { return value; } -template inline ERROR xmlInsertStatement(APTR Ob, LONG Index, XMI Where, T Statement, XMLTag **Result) { +template inline ERR xmlInsertStatement(APTR Ob, LONG Index, XMI Where, T Statement, XMLTag **Result) { struct xmlInsertXML insert = { Index, Where, to_cstring(Statement) }; - auto error = Action(MT_XMLInsertXML, (OBJECTPTR)Ob, &insert); - if (!error) { + + if (auto error = Action(MT_XMLInsertXML, (OBJECTPTR)Ob, &insert); error IS ERR::Okay) { struct xmlGetTag get = { insert.Result }; error = Action(MT_XMLGetTag, (OBJECTPTR)Ob, &get); *Result = get.Result; + return error; } - return(error); + else return error; } //******************************************************************************************************************** diff --git a/include/parasol/strings.hpp b/include/parasol/strings.hpp index 77bdd48b1..e61aadc70 100644 --- a/include/parasol/strings.hpp +++ b/include/parasol/strings.hpp @@ -5,6 +5,8 @@ namespace pf { +// USAGE: std::vector list; pf::split(value, std::back_inserter(list)); + template void split(InType Input, OutIt Output) { @@ -21,19 +23,19 @@ void split(InType Input, OutIt Output) *Output++ = std::string(current, begin); } -inline void ltrim(std::string &String, const std::string &Whitespace = " \t") +inline void ltrim(std::string &String, const std::string &Whitespace = " \n\r\t") { const auto start = String.find_first_not_of(Whitespace); if ((start != std::string::npos) and (start != 0)) String.erase(0, start); } -inline void rtrim(std::string &String, const std::string &Whitespace = " \t") +inline void rtrim(std::string &String, const std::string &Whitespace = " \n\r\t") { const auto end = String.find_last_not_of(Whitespace); if ((end != std::string::npos) and (end != String.size()-1)) String.erase(end+1, String.size()-end); } -inline void trim(std::string &String, const std::string &Whitespace = " \t") +inline void trim(std::string &String, const std::string &Whitespace = " \n\r\t") { const auto start = String.find_first_not_of(Whitespace); if ((start != std::string::npos) and (start != 0)) String.erase(0, start); diff --git a/include/parasol/system/errors.h b/include/parasol/system/errors.h index a6153b30d..c534c2851 100644 --- a/include/parasol/system/errors.h +++ b/include/parasol/system/errors.h @@ -1,223 +1,228 @@ #pragma once // Name: system/errors.h -// Copyright: Paul Manias © 1996-2023 +// Copyright: Paul Manias © 1996-2024 // Generator: idl-c +#ifdef __cplusplus +#include +#endif + // Universal error codes -#define ERR_Okay 0 -#define ERR_True 0 -#define ERR_False 1 -#define ERR_LimitedSuccess 2 -#define ERR_Cancelled 3 -#define ERR_NothingDone 4 -#define ERR_Continue 5 -#define ERR_Skip 6 -#define ERR_Retry 7 -#define ERR_DirEmpty 8 -#define ERR_Terminate 9 -#define ERR_ExceptionThreshold 9 -#define ERR_NoMemory 10 -#define ERR_NoPointer 11 -#define ERR_InUse 12 -#define ERR_Failed 13 -#define ERR_File 14 -#define ERR_InvalidData 15 -#define ERR_Search 16 -#define ERR_NotFound 16 -#define ERR_InitModule 17 -#define ERR_FileNotFound 18 -#define ERR_FileDoesNotExist 18 -#define ERR_WrongVersion 19 -#define ERR_Args 20 -#define ERR_NoData 21 -#define ERR_Read 22 -#define ERR_Write 23 -#define ERR_LockFailed 24 -#define ERR_Lock 24 -#define ERR_ExamineFailed 25 -#define ERR_LostClass 26 -#define ERR_NoAction 27 -#define ERR_NoSupport 28 -#define ERR_Memory 29 -#define ERR_TimeOut 30 -#define ERR_NoStats 31 -#define ERR_LowCapacity 32 -#define ERR_Init 33 -#define ERR_NoPermission 34 -#define ERR_Permissions 34 -#define ERR_PermissionDenied 34 -#define ERR_SystemCorrupt 35 -#define ERR_NeedOwner 36 -#define ERR_OwnerNeedsBitmap 37 -#define ERR_CoreVersion 38 -#define ERR_NeedWidthHeight 39 -#define ERR_NegativeSubClassID 40 -#define ERR_NegativeClassID 41 -#define ERR_MissingClassName 42 -#define ERR_OutOfRange 43 -#define ERR_ObtainMethod 44 -#define ERR_ArrayFull 45 -#define ERR_Query 46 -#define ERR_LostOwner 47 -#define ERR_DoNotExpunge 48 -#define ERR_MemoryCorrupt 49 -#define ERR_FieldSearch 50 -#define ERR_InvalidPath 51 -#define ERR_SetField 52 -#define ERR_MarkedForDeletion 53 -#define ERR_IllegalMethodID 54 -#define ERR_IllegalActionID 55 -#define ERR_ModuleOpenFailed 56 -#define ERR_IllegalActionAttempt 57 -#define ERR_EntryMissingHeader 58 -#define ERR_ModuleMissingInit 59 -#define ERR_ModuleInitFailed 60 -#define ERR_MemoryDoesNotExist 61 -#define ERR_DeadLock 62 -#define ERR_SystemLocked 63 -#define ERR_ModuleMissingName 64 -#define ERR_AddClass 65 -#define ERR_Activate 66 -#define ERR_DoubleInit 67 -#define ERR_UndefinedField 68 -#define ERR_FieldNotSet 68 -#define ERR_MissingClass 69 -#define ERR_FileReadFlag 70 -#define ERR_FileWriteFlag 71 -#define ERR_Draw 72 -#define ERR_NoMethods 73 -#define ERR_NoMatchingObject 74 -#define ERR_AccessMemory 75 -#define ERR_MissingPath 76 -#define ERR_NotLocked 77 -#define ERR_NoSearchResult 78 -#define ERR_StatementUnsatisfied 79 -#define ERR_ObjectCorrupt 80 -#define ERR_OwnerPassThrough 81 -#define ERR_UnsupportedOwner 82 -#define ERR_BadOwner 82 -#define ERR_ExclusiveDenied 83 -#define ERR_AccessObject 83 -#define ERR_AllocMemory 84 -#define ERR_NewObject 85 -#define ERR_GetField 86 -#define ERR_NoFieldAccess 87 -#define ERR_VirtualVolume 88 -#define ERR_InvalidDimension 89 -#define ERR_FieldTypeMismatch 90 -#define ERR_UnrecognisedFieldType 91 -#define ERR_BufferOverflow 92 -#define ERR_UnsupportedField 93 -#define ERR_Mismatch 94 -#define ERR_OutOfBounds 95 -#define ERR_Seek 96 -#define ERR_ReallocMemory 97 -#define ERR_Loop 98 -#define ERR_FileExists 99 -#define ERR_ResolvePath 100 -#define ERR_CreateObject 101 -#define ERR_MemoryInfo 102 -#define ERR_NotInitialised 103 -#define ERR_ResourceExists 104 -#define ERR_Refresh 105 -#define ERR_ListChildren 106 -#define ERR_SystemCall 107 -#define ERR_SmallMask 108 -#define ERR_EmptyString 109 -#define ERR_ObjectExists 110 -#define ERR_ExpectedFile 111 -#define ERR_Resize 112 -#define ERR_Redimension 113 -#define ERR_AllocSemaphore 114 -#define ERR_AccessSemaphore 115 -#define ERR_CreateFile 116 -#define ERR_DeleteFile 117 -#define ERR_OpenFile 118 -#define ERR_ReadOnly 119 -#define ERR_DoesNotExist 120 -#define ERR_IdenticalPaths 121 -#define ERR_Exists 122 -#define ERR_SanityFailure 123 -#define ERR_OutOfSpace 124 -#define ERR_GetSurfaceInfo 125 -#define ERR_Finished 126 -#define ERR_EOF 126 -#define ERR_EndOfFile 126 -#define ERR_OutOfData 126 -#define ERR_Syntax 127 -#define ERR_StringFormat 127 -#define ERR_InvalidState 128 -#define ERR_HostNotFound 129 -#define ERR_InvalidURI 130 -#define ERR_ConnectionRefused 131 -#define ERR_NetworkUnreachable 132 -#define ERR_HostUnreachable 133 -#define ERR_Disconnected 134 -#define ERR_TaskStillExists 135 -#define ERR_IntegrityViolation 136 -#define ERR_ConstraintViolation 136 -#define ERR_SchemaViolation 137 -#define ERR_DataSize 138 -#define ERR_Busy 139 -#define ERR_ConnectionAborted 140 -#define ERR_NullArgs 141 -#define ERR_InvalidObject 142 -#define ERR_WrongObjectType 142 -#define ERR_WrongClass 142 -#define ERR_ExecViolation 143 -#define ERR_Recursion 144 -#define ERR_IllegalAddress 145 -#define ERR_UnbalancedXML 146 -#define ERR_WouldBlock 147 -#define ERR_InputOutput 148 -#define ERR_LoadModule 149 -#define ERR_InvalidHandle 150 -#define ERR_Security 151 -#define ERR_InvalidValue 152 -#define ERR_ServiceUnavailable 153 -#define ERR_Deactivated 154 -#define ERR_LockRequired 155 -#define ERR_AlreadyLocked 156 -#define ERR_Locked 156 -#define ERR_CardReaderUnknown 157 -#define ERR_NoMediaInserted 158 -#define ERR_CardReaderUnavailable 159 -#define ERR_ProxySSLTunnel 160 -#define ERR_InvalidHTTPResponse 161 -#define ERR_InvalidReference 162 -#define ERR_Exception 163 -#define ERR_ThreadAlreadyActive 164 -#define ERR_OpenGL 165 -#define ERR_OutsideMainThread 166 -#define ERR_UseSubClass 167 -#define ERR_WrongType 168 -#define ERR_ThreadNotLocked 169 -#define ERR_LockMutex 170 -#define ERR_SetVolume 171 -#define ERR_Decompression 172 -#define ERR_Compression 173 -#define ERR_ExpectedFolder 174 -#define ERR_Immutable 175 -#define ERR_ReadFileToBuffer 176 -#define ERR_Obsolete 177 -#define ERR_CreateResource 178 -#define ERR_NotPossible 179 -#define ERR_ResolveSymbol 180 -#define ERR_Function 181 -#define ERR_AlreadyDefined 182 -#define ERR_SetValueNotNumeric 183 -#define ERR_SetValueNotString 184 -#define ERR_SetValueNotObject 185 -#define ERR_SetValueNotFunction 186 -#define ERR_SetValueNotPointer 187 -#define ERR_SetValueNotArray 188 -#define ERR_SetValueNotLookup 189 -#define ERR_END 190 +enum class ERR : int32_t { + NIL = 0, + Okay = 0, + True = 0, + False = 1, + LimitedSuccess = 2, + Cancelled = 3, + NothingDone = 4, + Continue = 5, + Skip = 6, + Retry = 7, + DirEmpty = 8, + Terminate = 9, + ExceptionThreshold = 9, + NoMemory = 10, + NoPointer = 11, + InUse = 12, + Failed = 13, + File = 14, + InvalidData = 15, + Search = 16, + NotFound = 16, + InitModule = 17, + FileNotFound = 18, + FileDoesNotExist = 18, + WrongVersion = 19, + Args = 20, + NoData = 21, + Read = 22, + Write = 23, + LockFailed = 24, + Lock = 24, + ExamineFailed = 25, + LostClass = 26, + NoAction = 27, + NoSupport = 28, + Memory = 29, + TimeOut = 30, + NoStats = 31, + LowCapacity = 32, + Init = 33, + NoPermission = 34, + Permissions = 34, + PermissionDenied = 34, + SystemCorrupt = 35, + NeedOwner = 36, + OwnerNeedsBitmap = 37, + CoreVersion = 38, + NeedWidthHeight = 39, + NegativeSubClassID = 40, + NegativeClassID = 41, + MissingClassName = 42, + OutOfRange = 43, + ObtainMethod = 44, + ArrayFull = 45, + Query = 46, + LostOwner = 47, + DoNotExpunge = 48, + MemoryCorrupt = 49, + FieldSearch = 50, + InvalidPath = 51, + SetField = 52, + MarkedForDeletion = 53, + IllegalMethodID = 54, + IllegalActionID = 55, + ModuleOpenFailed = 56, + IllegalActionAttempt = 57, + EntryMissingHeader = 58, + ModuleMissingInit = 59, + ModuleInitFailed = 60, + MemoryDoesNotExist = 61, + DeadLock = 62, + SystemLocked = 63, + ModuleMissingName = 64, + AddClass = 65, + Activate = 66, + DoubleInit = 67, + UndefinedField = 68, + FieldNotSet = 68, + MissingClass = 69, + FileReadFlag = 70, + FileWriteFlag = 71, + Draw = 72, + NoMethods = 73, + NoMatchingObject = 74, + AccessMemory = 75, + MissingPath = 76, + NotLocked = 77, + NoSearchResult = 78, + StatementUnsatisfied = 79, + ObjectCorrupt = 80, + OwnerPassThrough = 81, + UnsupportedOwner = 82, + ExclusiveDenied = 83, + AccessObject = 83, + AllocMemory = 84, + NewObject = 85, + GetField = 86, + NoFieldAccess = 87, + VirtualVolume = 88, + InvalidDimension = 89, + FieldTypeMismatch = 90, + UnrecognisedFieldType = 91, + BufferOverflow = 92, + UnsupportedField = 93, + Mismatch = 94, + OutOfBounds = 95, + Seek = 96, + ReallocMemory = 97, + Loop = 98, + FileExists = 99, + ResolvePath = 100, + CreateObject = 101, + MemoryInfo = 102, + NotInitialised = 103, + ResourceExists = 104, + Refresh = 105, + ListChildren = 106, + SystemCall = 107, + SmallMask = 108, + EmptyString = 109, + ObjectExists = 110, + ExpectedFile = 111, + Resize = 112, + Redimension = 113, + AllocSemaphore = 114, + AccessSemaphore = 115, + CreateFile = 116, + DeleteFile = 117, + OpenFile = 118, + ReadOnly = 119, + DoesNotExist = 120, + IdenticalPaths = 121, + Exists = 122, + SanityFailure = 123, + OutOfSpace = 124, + GetSurfaceInfo = 125, + Finished = 126, + EndOfFile = 126, + OutOfData = 126, + Syntax = 127, + StringFormat = 127, + InvalidState = 128, + HostNotFound = 129, + InvalidURI = 130, + ConnectionRefused = 131, + NetworkUnreachable = 132, + HostUnreachable = 133, + Disconnected = 134, + TaskStillExists = 135, + IntegrityViolation = 136, + ConstraintViolation = 136, + SchemaViolation = 137, + DataSize = 138, + Busy = 139, + ConnectionAborted = 140, + NullArgs = 141, + InvalidObject = 142, + WrongObjectType = 142, + WrongClass = 142, + ExecViolation = 143, + Recursion = 144, + IllegalAddress = 145, + UnbalancedXML = 146, + WouldBlock = 147, + InputOutput = 148, + LoadModule = 149, + InvalidHandle = 150, + Security = 151, + InvalidValue = 152, + ServiceUnavailable = 153, + Deactivated = 154, + LockRequired = 155, + AlreadyLocked = 156, + Locked = 156, + CardReaderUnknown = 157, + NoMediaInserted = 158, + CardReaderUnavailable = 159, + ProxySSLTunnel = 160, + InvalidHTTPResponse = 161, + InvalidReference = 162, + Exception = 163, + ThreadAlreadyActive = 164, + OpenGL = 165, + OutsideMainThread = 166, + UseSubClass = 167, + WrongType = 168, + ThreadNotLocked = 169, + LockMutex = 170, + SetVolume = 171, + Decompression = 172, + Compression = 173, + ExpectedFolder = 174, + Immutable = 175, + ReadFileToBuffer = 176, + Obsolete = 177, + CreateResource = 178, + NotPossible = 179, + ResolveSymbol = 180, + Function = 181, + AlreadyDefined = 182, + SetValueNotNumeric = 183, + SetValueNotString = 184, + SetValueNotObject = 185, + SetValueNotFunction = 186, + SetValueNotPointer = 187, + SetValueNotArray = 188, + SetValueNotLookup = 189, + END = 190, + Notified = 1073741824, +}; // Special error flags -#define ERF_Delay 536870912 #define ERF_Notified 1073741824 diff --git a/include/parasol/system/errors_c.h b/include/parasol/system/errors_c.h new file mode 100644 index 000000000..f63acfd84 --- /dev/null +++ b/include/parasol/system/errors_c.h @@ -0,0 +1,221 @@ +#pragma once + +// Name: system/errors.h +// Copyright: Paul Manias © 1996-2024 +// Generator: idl-c + +// Universal error codes + +#define ERR_Okay 0 +#define ERR_True 0 +#define ERR_False 1 +#define ERR_LimitedSuccess 2 +#define ERR_Cancelled 3 +#define ERR_NothingDone 4 +#define ERR_Continue 5 +#define ERR_Skip 6 +#define ERR_Retry 7 +#define ERR_DirEmpty 8 +#define ERR_Terminate 9 +#define ERR_ExceptionThreshold 9 +#define ERR_NoMemory 10 +#define ERR_NoPointer 11 +#define ERR_InUse 12 +#define ERR_Failed 13 +#define ERR_File 14 +#define ERR_InvalidData 15 +#define ERR_Search 16 +#define ERR_NotFound 16 +#define ERR_InitModule 17 +#define ERR_FileNotFound 18 +#define ERR_FileDoesNotExist 18 +#define ERR_WrongVersion 19 +#define ERR_Args 20 +#define ERR_NoData 21 +#define ERR_Read 22 +#define ERR_Write 23 +#define ERR_LockFailed 24 +#define ERR_Lock 24 +#define ERR_ExamineFailed 25 +#define ERR_LostClass 26 +#define ERR_NoAction 27 +#define ERR_NoSupport 28 +#define ERR_Memory 29 +#define ERR_TimeOut 30 +#define ERR_NoStats 31 +#define ERR_LowCapacity 32 +#define ERR_Init 33 +#define ERR_NoPermission 34 +#define ERR_Permissions 34 +#define ERR_PermissionDenied 34 +#define ERR_SystemCorrupt 35 +#define ERR_NeedOwner 36 +#define ERR_OwnerNeedsBitmap 37 +#define ERR_CoreVersion 38 +#define ERR_NeedWidthHeight 39 +#define ERR_NegativeSubClassID 40 +#define ERR_NegativeClassID 41 +#define ERR_MissingClassName 42 +#define ERR_OutOfRange 43 +#define ERR_ObtainMethod 44 +#define ERR_ArrayFull 45 +#define ERR_Query 46 +#define ERR_LostOwner 47 +#define ERR_DoNotExpunge 48 +#define ERR_MemoryCorrupt 49 +#define ERR_FieldSearch 50 +#define ERR_InvalidPath 51 +#define ERR_SetField 52 +#define ERR_MarkedForDeletion 53 +#define ERR_IllegalMethodID 54 +#define ERR_IllegalActionID 55 +#define ERR_ModuleOpenFailed 56 +#define ERR_IllegalActionAttempt 57 +#define ERR_EntryMissingHeader 58 +#define ERR_ModuleMissingInit 59 +#define ERR_ModuleInitFailed 60 +#define ERR_MemoryDoesNotExist 61 +#define ERR_DeadLock 62 +#define ERR_SystemLocked 63 +#define ERR_ModuleMissingName 64 +#define ERR_AddClass 65 +#define ERR_Activate 66 +#define ERR_DoubleInit 67 +#define ERR_UndefinedField 68 +#define ERR_FieldNotSet 68 +#define ERR_MissingClass 69 +#define ERR_FileReadFlag 70 +#define ERR_FileWriteFlag 71 +#define ERR_Draw 72 +#define ERR_NoMethods 73 +#define ERR_NoMatchingObject 74 +#define ERR_AccessMemory 75 +#define ERR_MissingPath 76 +#define ERR_NotLocked 77 +#define ERR_NoSearchResult 78 +#define ERR_StatementUnsatisfied 79 +#define ERR_ObjectCorrupt 80 +#define ERR_OwnerPassThrough 81 +#define ERR_UnsupportedOwner 82 +#define ERR_ExclusiveDenied 83 +#define ERR_AccessObject 83 +#define ERR_AllocMemory 84 +#define ERR_NewObject 85 +#define ERR_GetField 86 +#define ERR_NoFieldAccess 87 +#define ERR_VirtualVolume 88 +#define ERR_InvalidDimension 89 +#define ERR_FieldTypeMismatch 90 +#define ERR_UnrecognisedFieldType 91 +#define ERR_BufferOverflow 92 +#define ERR_UnsupportedField 93 +#define ERR_Mismatch 94 +#define ERR_OutOfBounds 95 +#define ERR_Seek 96 +#define ERR_ReallocMemory 97 +#define ERR_Loop 98 +#define ERR_FileExists 99 +#define ERR_ResolvePath 100 +#define ERR_CreateObject 101 +#define ERR_MemoryInfo 102 +#define ERR_NotInitialised 103 +#define ERR_ResourceExists 104 +#define ERR_Refresh 105 +#define ERR_ListChildren 106 +#define ERR_SystemCall 107 +#define ERR_SmallMask 108 +#define ERR_EmptyString 109 +#define ERR_ObjectExists 110 +#define ERR_ExpectedFile 111 +#define ERR_Resize 112 +#define ERR_Redimension 113 +#define ERR_AllocSemaphore 114 +#define ERR_AccessSemaphore 115 +#define ERR_CreateFile 116 +#define ERR_DeleteFile 117 +#define ERR_OpenFile 118 +#define ERR_ReadOnly 119 +#define ERR_DoesNotExist 120 +#define ERR_IdenticalPaths 121 +#define ERR_Exists 122 +#define ERR_SanityFailure 123 +#define ERR_OutOfSpace 124 +#define ERR_GetSurfaceInfo 125 +#define ERR_Finished 126 +#define ERR_EOF 126 +#define ERR_EndOfFile 126 +#define ERR_OutOfData 126 +#define ERR_Syntax 127 +#define ERR_StringFormat 127 +#define ERR_InvalidState 128 +#define ERR_HostNotFound 129 +#define ERR_InvalidURI 130 +#define ERR_ConnectionRefused 131 +#define ERR_NetworkUnreachable 132 +#define ERR_HostUnreachable 133 +#define ERR_Disconnected 134 +#define ERR_TaskStillExists 135 +#define ERR_IntegrityViolation 136 +#define ERR_ConstraintViolation 136 +#define ERR_SchemaViolation 137 +#define ERR_DataSize 138 +#define ERR_Busy 139 +#define ERR_ConnectionAborted 140 +#define ERR_NullArgs 141 +#define ERR_InvalidObject 142 +#define ERR_WrongObjectType 142 +#define ERR_WrongClass 142 +#define ERR_ExecViolation 143 +#define ERR_Recursion 144 +#define ERR_IllegalAddress 145 +#define ERR_UnbalancedXML 146 +#define ERR_WouldBlock 147 +#define ERR_InputOutput 148 +#define ERR_LoadModule 149 +#define ERR_InvalidHandle 150 +#define ERR_Security 151 +#define ERR_InvalidValue 152 +#define ERR_ServiceUnavailable 153 +#define ERR_Deactivated 154 +#define ERR_LockRequired 155 +#define ERR_AlreadyLocked 156 +#define ERR_Locked 156 +#define ERR_CardReaderUnknown 157 +#define ERR_NoMediaInserted 158 +#define ERR_CardReaderUnavailable 159 +#define ERR_ProxySSLTunnel 160 +#define ERR_InvalidHTTPResponse 161 +#define ERR_InvalidReference 162 +#define ERR_Exception 163 +#define ERR_ThreadAlreadyActive 164 +#define ERR_OpenGL 165 +#define ERR_OutsideMainThread 166 +#define ERR_UseSubClass 167 +#define ERR_WrongType 168 +#define ERR_ThreadNotLocked 169 +#define ERR_LockMutex 170 +#define ERR_SetVolume 171 +#define ERR_Decompression 172 +#define ERR_Compression 173 +#define ERR_ExpectedFolder 174 +#define ERR_Immutable 175 +#define ERR_ReadFileToBuffer 176 +#define ERR_Obsolete 177 +#define ERR_CreateResource 178 +#define ERR_NotPossible 179 +#define ERR_ResolveSymbol 180 +#define ERR_Function 181 +#define ERR_AlreadyDefined 182 +#define ERR_SetValueNotNumeric 183 +#define ERR_SetValueNotString 184 +#define ERR_SetValueNotObject 185 +#define ERR_SetValueNotFunction 186 +#define ERR_SetValueNotPointer 187 +#define ERR_SetValueNotArray 188 +#define ERR_SetValueNotLookup 189 +#define ERR_END 190 + +// Special error flags + +#define ERF_Notified 1073741824 + diff --git a/include/parasol/system/fields.h b/include/parasol/system/fields.h index 5f464c6ca..f6e03db29 100644 --- a/include/parasol/system/fields.h +++ b/include/parasol/system/fields.h @@ -1,7 +1,7 @@ #pragma once // Name: system/fields.h -// Copyright: Paul Manias © 1996-2023 +// Copyright: Paul Manias © 1996-2024 // Generator: idl-c #define FID_Category 0x19ee1863LL @@ -216,7 +216,7 @@ #define FID_ActionScript 0xab19ce38LL #define FID_LabelWidth 0xe1c93545LL #define FID_Template 0xeeaba201LL -#define FID_FocusFrame 0xf362fb10LL +#define FID_FontStyle 0xf6bc116dLL #define FID_Bottom 0xf492ca7aLL #define FID_IgnoreFocus 0xf730cb69LL #define FID_Header 0x01d218aeLL @@ -532,17 +532,14 @@ #define FID_Tabs 0x7c9e552fLL #define FID_Outline 0x7d9ba745LL #define FID_WrapEdge 0x80248354LL -#define FID_WrapCallback 0x878b8aecLL #define FID_StrWidth 0x913a3abeLL #define FID_FixedWidth 0xa86c5cd5LL -#define FID_EscapeChar 0xb6a3bf14LL #define FID_Underline 0xb8ea5b4bLL #define FID_LineSpacing 0xbb0bc1d2LL #define FID_TotalChars 0xc8396dbaLL #define FID_GlyphSpacing 0xc896c32eLL #define FID_AlignWidth 0xcb1970d0LL #define FID_TabSize 0xce95c997LL -#define FID_EscapeCallback 0xd07112a3LL #define FID_Ascent 0xf27c7183LL #define FID_InputFile 0x044358d5LL #define FID_Datatype 0x05eed661LL @@ -854,6 +851,7 @@ #define FID_Degree 0xf880fbf1LL #define FID_DestBitmap 0xae246132LL #define FID_DeviceID 0x3f093642LL +#define FID_DragCallback 0xcd1ba3b0LL #define FID_EffectXML 0xa7fe50e3LL #define FID_EnableBkgd 0xdb56fba4LL #define FID_FX 0x005977e3LL @@ -935,19 +933,25 @@ #define FID_Weight 0x24d3ea4dLL #define FID_Bias 0x7c949844LL +#define FID_ClipFlags 0x4959653aLL #define FID_Constant 0x42a2b30fLL #define FID_Def 0x0b8869b4LL #define FID_Dictionary 0xccb60b7bLL #define FID_Divisor 0x12ffda05LL #define FID_EdgeMode 0xbb10b09fLL +#define FID_EventCallback 0xfc356c74LL +#define FID_EventMask 0x354f38b3LL #define FID_Exponent 0xd4513596LL +#define FID_LoopLimit 0xf4c76a9eLL #define FID_MatrixRows 0x64419145LL #define FID_MatrixColumns 0x54dc215bLL #define FID_Matrix 0x0d3e291aLL #define FID_PreserveAlpha 0xf9b49d57LL +#define FID_Pretext 0xc28b4df1LL #define FID_ResX 0x7c9d4fa7LL #define FID_ResY 0x7c9d4fa8LL #define FID_RootModule 0xdc9a16cfLL +#define FID_Rounding 0x2a6f2a0bLL #define FID_SourceName 0xb837c737LL #define FID_Structs 0xaf10175dLL #define FID_TargetX 0xcfb0ab64LL @@ -978,4 +982,5 @@ #define FID_Numeric 0x301f0df8LL #define FID_ResizeEvent 0xc404ebf9LL #define FID_TabOrder 0xa10b2cb8LL +#define FID_TextFlags 0x1bce45f7LL diff --git a/include/parasol/system/registry.h b/include/parasol/system/registry.h index ab3566669..52ffce7a2 100644 --- a/include/parasol/system/registry.h +++ b/include/parasol/system/registry.h @@ -1,7 +1,7 @@ #pragma once // Name: system/registry.h -// Copyright: Paul Manias 1996-2023 +// Copyright: Paul Manias 1996-2024 // Generator: idl-c #define ID_PICTURE 0xad68f281UL diff --git a/include/parasol/system/types.h b/include/parasol/system/types.h index 111091f8a..d9745a55b 100644 --- a/include/parasol/system/types.h +++ b/include/parasol/system/types.h @@ -7,12 +7,16 @@ #include #include +//******************************************************************************************************************** + template class strong_typedef { public: + // Constructors strong_typedef() : val() { } - constexpr explicit strong_typedef(const T &Value) : val(Value) { } + + // Accessors explicit operator T&() noexcept { return val; } explicit operator const T&() const noexcept { return val; } @@ -20,11 +24,12 @@ class strong_typedef { T val; }; -struct PERCENT : strong_typedef { +struct SCALE : strong_typedef { // Make constructors available using strong_typedef::strong_typedef; }; +//******************************************************************************************************************** // Function structure, typically used for defining callbacks to functions and procedures of any kind (e.g. standard C, // Fluid). @@ -34,24 +39,41 @@ enum { CALL_SCRIPT }; -typedef struct rkFunction { +struct FUNCTION { unsigned char Type; unsigned char PadA; unsigned short ID; // Unused. Unique identifier for the function. union { struct { - OBJECTPTR Context; + OBJECTPTR Context; // The context at the time the function was created void * Routine; + void * Meta; // Additional meta data provided by the client. } StdC; struct { - OBJECTPTR Script; + class objScript *Script; // Equivalent to the StdC Context LARGE ProcedureID; // Function identifier, usually a hash } Script; }; -} rkFunction, FUNCTION; -inline bool operator==(const struct rkFunction &A, const struct rkFunction &B) + FUNCTION() : Type(0) { } + + template FUNCTION(T *pRoutine); + template FUNCTION(T *pRoutine, OBJECTPTR pContext, APTR pMeta); + template FUNCTION(T *pRoutine, APTR pMeta); + + FUNCTION(class objScript *pScript, LARGE pProcedure) { + Type = CALL_SCRIPT; + Script = { pScript, pProcedure }; + } + + void clear() { Type = CALL_NONE; } + bool isC() const { return Type IS CALL_STDC; } + bool isScript() const { return Type IS CALL_SCRIPT; } + bool defined() const { return Type != CALL_NONE; } +}; + +inline bool operator==(const struct FUNCTION &A, const struct FUNCTION &B) { if (A.Type == CALL_STDC) return (A.Type == B.Type) and (A.StdC.Context == B.StdC.Context) and (A.StdC.Routine == B.StdC.Routine); else if (A.Type == CALL_SCRIPT) return (A.Type == B.Type) and (A.Script.Script == B.Script.Script) and (A.Script.ProcedureID == B.Script.ProcedureID); diff --git a/include/parasol/vector.hpp b/include/parasol/vector.hpp index 2d66b65c8..4ca0f0178 100644 --- a/include/parasol/vector.hpp +++ b/include/parasol/vector.hpp @@ -129,13 +129,19 @@ template class vector { } void erase(iterator Start, iterator Stop) { - size_t count = 0; - for (auto it=Stop, st=Start; it != end(); it++, st++) { - *st = std::move(*it); - count++; + if (Stop IS end()) { + for (auto it = Start; it != Stop; it++) { + (*it).~T(); + length--; + } + } + else { + for (auto it=Stop, start=Start; it != end(); it++, start++) { + *start = std::move(*it); + } + auto total_removed = Stop - Start; + length -= total_removed; } - - length -= count; } iterator insert(const_iterator pTarget, T &pValue) { diff --git a/scripts/dev/idl/common-graphics.fdl b/scripts/dev/idl/common-graphics.fdl index 32086029c..c026a4580 100644 --- a/scripts/dev/idl/common-graphics.fdl +++ b/scripts/dev/idl/common-graphics.fdl @@ -29,45 +29,45 @@ enum("PTC", { type="int", start=0, comment="Predefined cursor styles" }, "END") -- Any new cursor images must be added to the CursorLookup array in pointer_class.c flags("DMF", { weak=true, bits=32 }, - "RELATIVE_X: The X field is relative to this object's parent.", - "RELATIVE_Y: The Y field is relative to this object's parent.", + "SCALED_X: The X field is scaled to this object's parent.", + "SCALED_Y: The Y field is scaled to this object's parent.", "FIXED_X: The X field is a fixed coordinate.", "FIXED_Y: The Y field is a fixed coordinate.", - "RELATIVE_X_OFFSET: The XOffset field is relative to this object's parent.", - "RELATIVE_Y_OFFSET: The YOffset field is relative to this object's parent.", + "SCALED_X_OFFSET: The XOffset field is scaled to this object's parent.", + "SCALED_Y_OFFSET: The YOffset field is scaled to this object's parent.", "FIXED_X_OFFSET: The XOffset field is a fixed coordinate.", "FIXED_Y_OFFSET: The YOffset field is a fixed coordinate.", "FIXED_HEIGHT: The Height field is a fixed size.", "FIXED_WIDTH: The Width field is a fixed suze.", - "RELATIVE_HEIGHT: The Height field is relative to this object's parent.", - "RELATIVE_WIDTH: The Width field is relative to this object's parent.", + "SCALED_HEIGHT: The Height field is scaled to this object's parent.", + "SCALED_WIDTH: The Width field is scaled to this object's parent.", "FIXED_DEPTH: The Depth field is a fixed size.", - "RELATIVE_DEPTH: The Depth field is a relative size to this object's parent.", + "SCALED_DEPTH: The Depth field is scaled to this object's parent.", "FIXED_Z: The Z field is a fixed coordinate.", - "RELATIVE_Z: The Z field is a relative coordinate to this object's parent.", - { RELATIVE_RADIUS_X = "0x00010000: The RadiusX field is a relative size to this object's parent.", + "SCALED_Z: The Z field is a scaled coordinate to this object's parent.", + { SCALED_RADIUS_X = "0x00010000: The RadiusX field is scaled to this object's parent.", FIXED_RADIUS_X = "0x00020000: The RadiusX field is a fixed size.", - RELATIVE_CENTER_X = "0x00040000: The CenterX field is a relative size to this object's parent.", - RELATIVE_CENTER_Y = "0x00080000: The CenterY field is a relative size to this object's parent.", + SCALED_CENTER_X = "0x00040000: The CenterX field is scaled to this object's parent.", + SCALED_CENTER_Y = "0x00080000: The CenterY field is scaled to this object's parent.", FIXED_CENTER_X = "0x00100000: The CenterX field is a fixed size.", FIXED_CENTER_Y = "0x00200000: The CenterY field is a fixed size.", STATUS_CHANGE_H = 0x00400000, STATUS_CHANGE_V = 0x00800000, - RELATIVE_RADIUS_Y = "0x01000000: The RadiusY field is a relative size to this object's parent.", + SCALED_RADIUS_Y = "0x01000000: The RadiusY field is a scaled size to this object's parent.", FIXED_RADIUS_Y = "0x02000000: The RadiusY field is a fixed size." }, - { X = "FIXED_X|RELATIVE_X", - Y = "FIXED_Y|RELATIVE_Y", - WIDTH = "FIXED_WIDTH|RELATIVE_WIDTH", - HEIGHT = "FIXED_HEIGHT|RELATIVE_HEIGHT", - X_OFFSET = "FIXED_X_OFFSET|RELATIVE_X_OFFSET", - Y_OFFSET = "FIXED_Y_OFFSET|RELATIVE_Y_OFFSET", - RELATIVE_RADIUS = "RELATIVE_RADIUS_X|RELATIVE_RADIUS_Y", + { X = "FIXED_X|SCALED_X", + Y = "FIXED_Y|SCALED_Y", + WIDTH = "FIXED_WIDTH|SCALED_WIDTH", + HEIGHT = "FIXED_HEIGHT|SCALED_HEIGHT", + X_OFFSET = "FIXED_X_OFFSET|SCALED_X_OFFSET", + Y_OFFSET = "FIXED_Y_OFFSET|SCALED_Y_OFFSET", + SCALED_RADIUS = "SCALED_RADIUS_X|SCALED_RADIUS_Y", FIXED_RADIUS = "FIXED_RADIUS_X|FIXED_RADIUS_Y", STATUS_CHANGE = "STATUS_CHANGE_H|STATUS_CHANGE_V", - HORIZONTAL_FLAGS = "FIXED_WIDTH|RELATIVE_WIDTH|FIXED_X_OFFSET|RELATIVE_X_OFFSET|FIXED_X|RELATIVE_X", - VERTICAL_FLAGS = "FIXED_HEIGHT|RELATIVE_HEIGHT|FIXED_Y_OFFSET|RELATIVE_Y_OFFSET|FIXED_Y|RELATIVE_Y", - WIDTH_FLAGS = "FIXED_WIDTH|RELATIVE_WIDTH|FIXED_X_OFFSET|RELATIVE_X_OFFSET", - HEIGHT_FLAGS = "FIXED_HEIGHT|RELATIVE_HEIGHT|FIXED_Y_OFFSET|RELATIVE_Y_OFFSET" + HORIZONTAL_FLAGS = "FIXED_WIDTH|SCALED_WIDTH|FIXED_X_OFFSET|SCALED_X_OFFSET|FIXED_X|SCALED_X", + VERTICAL_FLAGS = "FIXED_HEIGHT|SCALED_HEIGHT|FIXED_Y_OFFSET|SCALED_Y_OFFSET|FIXED_Y|SCALED_Y", + WIDTH_FLAGS = "FIXED_WIDTH|SCALED_WIDTH|FIXED_X_OFFSET|SCALED_X_OFFSET", + HEIGHT_FLAGS = "FIXED_HEIGHT|SCALED_HEIGHT|FIXED_Y_OFFSET|SCALED_Y_OFFSET" } ) @@ -181,6 +181,7 @@ struct("ClipRectangle", { comment="Generic structure for rectangular clipping." ]], [[ ClipRectangle() { } + ClipRectangle(LONG Value) : Left(Value), Top(Value), Right(Value), Bottom(Value) { } ClipRectangle(LONG pLeft, LONG pTop, LONG pRight, LONG pBottom) : Left(pLeft), Top(pTop), Right(pRight), Bottom(pBottom) { } int width() const { return Right - Left; } int height() const { return Bottom - Top; } diff --git a/scripts/dev/idl/common.fdl b/scripts/dev/idl/common.fdl index 8465838d9..5e28fef1f 100644 --- a/scripts/dev/idl/common.fdl +++ b/scripts/dev/idl/common.fdl @@ -1,17 +1,17 @@ -- These common constants are re-usable across all modules. -flags("CLIPMODE", { comment="Clipboard modes" }, +flags("CLIPMODE", { comment="Clipboard modes", module="Core" }, "CUT: Cut from the clipboard.", "COPY: Copy from the clipboard.", "PASTE: Paste from the clipboard.") -enum("SEEK", { type="int", start=0, comment="Seek positions" }, +enum("SEEK", { type="int", start=0, comment="Seek positions", module="Core" }, "START: Use an index at position zero.", "CURRENT: Use an index at the end of the last read/write operation.", "END: Use an index at the end of the data buffer.", "RELATIVE: The index is between 0 and 1.0 and relative to the data size.") -flags("DEVICE", { bits=64 }, +flags("DEVICE", { bits=64, module="Core" }, "COMPACT_DISC: Compact disc style device", "HARD_DISK: Hard disk style device", "FLOPPY_DISK: Floppy disk style device", @@ -30,7 +30,7 @@ flags("DEVICE", { bits=64 }, "PRINTER_3D: Device is a three dimensional printer.", "SCANNER_3D: Device is a three dimensional scanner.") -flags("CCF", { comment="Class categories" }, +flags("CCF", { comment="Class categories", module="Core" }, "COMMAND: Command classes perform specific procedures, like copying or moving a file, managing volumes or executing a program.", "DRAWABLE: Drawable classes provide graphical areas that are designed to be drawn to.", "EFFECT: Effect classes draw graphics and/or play audio for non-productive demonstration purposes.", @@ -46,7 +46,7 @@ flags("CCF", { comment="Class categories" }, "NETWORK: Network classes interface with network drivers to simplify network communications for the developer.", "MULTIMEDIA") -enum("AC", { weak=true, start=1, comment="Action identifiers." }, +enum("AC", { weak=true, start=1, comment="Action identifiers.", module="Core" }, "Signal", "Activate", "SelectArea", "Clear", "FreeWarning", "Sort", "CopyData", "DataFeed", "Deactivate", "Draw", "Flush", "Focus", "Free", "SaveSettings", "GetVar", "DragDrop", "Hide", "Init", "Lock", "LostFocus", "Move", @@ -57,7 +57,7 @@ enum("AC", { weak=true, start=1, comment="Action identifiers." }, "MoveToPoint", "ScrollToPoint", "Custom", "END") -flags("PERMIT", { comment="Permission flags" }, +flags("PERMIT", { comment="Permission flags", module="Core" }, "READ: User/Owner has read access. This will not allow compiled code to be executed.", "WRITE: User/Owner can write.", "EXEC: User/Owner can execute.", @@ -96,7 +96,7 @@ flags("PERMIT", { comment="Permission flags" }, { OTHERS = "OTHERS_READ|OTHERS_WRITE|OTHERS_EXEC|OTHERS_DELETE" } ) -flags("KQ", { comment="Special qualifier flags" }, +flags("KQ", { comment="Special qualifier flags", module="Core" }, "L_SHIFT: Left Shift is held", "R_SHIFT: Right Shift is held", "CAPS_LOCK: Caps-Lock is on", @@ -126,7 +126,7 @@ flags("KQ", { comment="Special qualifier flags" }, { INFO = "REPEAT|RELEASED|PRESSED|NOT_PRINTABLE|CAPS_LOCK" } ) -flags("MEM", { comment="Memory types used by AllocMemory(). The lower 16 bits are stored with allocated blocks, the upper 16 bits are function-relative only." }, +flags("MEM", { comment="Memory types used by AllocMemory(). The lower 16 bits are stored with allocated blocks, the upper 16 bits are function-relative only.", module="Core" }, "MANAGED: Enables custom resource management for the memory block. The start of the block will need to be reserved with a pointer to a ResourceManager structure, which is included as part of the block's declared Size. The Free() callback will be called when the block is removed.", "VIDEO: The memory space is reserved by a video device such as a graphics card for display purposes, e.g. framebuffer.", "TEXTURE: The memory space is reserved by a video driver for hosting texture graphics.", @@ -149,7 +149,7 @@ flags("MEM", { comment="Memory types used by AllocMemory(). The lower 16 bits a { CALLER = "0x00800000: This flag is usable only in routines that are supporting a class method. It forces the memory allocation to be tracked to the object that made the method call. This is particularly important in methods that return memory blocks that do not form a part of the object itself." }, { READ_WRITE = "READ|WRITE" }) -enum("EVG", { type="int", start=1, comment="Event categories." }, -- 5 bit limit (max 32 entries). These constants are also managed in core.fluid and fluid_functions.c, line 493 +enum("EVG", { type="int", start=1, comment="Event categories.", module="Core" }, -- 5 bit limit (max 32 entries). These constants are also managed in core.fluid and fluid_functions.c, line 493 "FILESYSTEM: File system events.", "NETWORK: Network events.", "SYSTEM: System-wide events", @@ -165,7 +165,7 @@ enum("EVG", { type="int", start=1, comment="Event categories." }, -- 5 bit limit "ANDROID: Android specific events that do not already fit existing categories.", "END: Private") -enum("DATA", { type="int", start=1, comment="Data codes" }, -- NB: Duplicated in display/win32/windows.c +enum("DATA", { type="int", start=1, comment="Data codes", module="Core" }, -- NB: Duplicated in display/win32/windows.c "TEXT: Standard ASCII text", "RAW: Raw unprocessed data", "DEVICE_INPUT: Device activity", @@ -179,23 +179,22 @@ enum("DATA", { type="int", start=1, comment="Data codes" }, -- NB: Duplicated in "CONTENT: Document content (between XML tags) - sent by document objects only", "INPUT_READY: Device input that has been transformed into user input") -flags("JTYPE", { comment="JTYPE flags are used to categorise input types." }, +flags("JTYPE", { comment="JTYPE flags are used to categorise input types.", module="Core" }, "SECONDARY: Indicates to the receiver of this message that it is not the primary/original recipient", "ANCHORED: Cursor has been anchored with LockCursor()", "DRAGGED: Set if sufficient movement occurred between the original click and its point of release (usually requires a 3 or more pixel difference).", - "FEEDBACK: Device feedback - e.g. vibration, tilt", + "CROSSING: Crossing events manage the entering and leaving of an area.", "DIGITAL: D-Pad or digital joystick source (restricted to +/- 1)", "ANALOG: Analog movement (ranging from -1.0 to 1.0)", - "EXT_MOVEMENT: Extended movement information. This covers all types of movement that are unconnected to coordinate positioning - mouse wheel movement and pen tilt are two such examples.", + "EXT_MOVEMENT: Extended or indirect movement information. This covers all types of movement that are unconnected to coordinate positioning - mouse wheel movement and pen tilt are two such examples.", "BUTTON: Input is a physical button or switch", "MOVEMENT: X/Y coordinate movement only. Movement such as the wheel mouse spinning is not covered by this type as it does not influence the coordinate system.", "DBL_CLICK: Set by the input system if the Type is a button and the button has been clicked in quick succession so as to be classed as a double-click.", "REPEATED: Input is a repeated entry (i.e. user is holding down a button and a repetition timer is being triggered)", "DRAG_ITEM: This special flag is set by the input system if the pointer is click-dragging an object at the time of the event.") -enum("JET", { type="int", start=1, comment="JET constants are documented in GetInputEvent()" }, - "DIGITAL_X: Horizontal digital movement from a relative location. Value is +/- n, where n is the number of units moved horizontally. Mouse movement will normally exceed a value of 1, whereas gamepad movement is limited to a value of +/- 1 except in the case of successive presses.", - "DIGITAL_Y: Vertical digital movement from a relative location.", +enum("JET", { type="int", start=1, comment="JET constants are documented in GetInputEvent()", module="Core" }, + "DIGITAL_XY: Digital movement from a relative location. Value is +/- n, where n is the number of units moved horizontally. Mouse movement will normally exceed a value of 1, whereas gamepad movement is limited to a value of +/- 1 except in the case of successive presses.", "BUTTON_1|LMB: Left mouse button, XBox A button, PS square button. Value is pressure sensitive, ranging between 0 - 1.0 (0 is released, 1.0 is fully depressed).", "BUTTON_2|RMB: Right mouse button, XBox X button, PS cross button.", "BUTTON_3|MMB: Middle mouse button, XBox Y button, PS triangle.", @@ -214,23 +213,18 @@ enum("JET", { type="int", start=1, comment="JET constants are documented in GetI "LEFT_BUMPER_2: Gamepad left-hand bumper 2 (lower) - pressure sensitive value from 0 - 1.0.", "RIGHT_BUMPER_1: Gamepad right-hand bumper 1 (top) - pressure sensitive value from 0 - 1.0.", "RIGHT_BUMPER_2: Gamepad right-hand bumper 2 (lower) - pressure sensitive value from 0 - 1.0.", - "ANALOG_X: Horizontal position for the default analog control (on gamepads this is the left analog control). Analog values range between -1.0 and 1.0. A value of zero indicates that the control is at rest.", - "ANALOG_Y: Vertical position for the default analog control.", + "ANALOG_XY: Position for the default analog control (on gamepads this is the left analog control). Analog values range between -1.0 and 1.0. A value of zero indicates that the control is at rest.", "ANALOG_Z: 3D or yoke position for the default analog control. A negative value indicates that the control has been pulled out and a positive value indicates that it has been pushed in.", - "ANALOG2_X: As for ANALOG_X, this type covers a second analog stick if present.", - "ANALOG2_Y: As for ANALOG_Y, this type covers a second analog stick if present.", + "ANALOG2_XY: As for ANALOG_XY, this type covers a second analog stick if present.", "ANALOG2_Z: As for ANALOG_Z, this type covers a second analog stick if present.", "WHEEL: Mouse wheel rotation - the value generally reflects the number of 'clicks' rotated on the wheel.", "WHEEL_TILT: Some mouse wheels can be tilted to the left or right. Ranges from -1.0 to +1.0", - "PEN_TILT_VERTICAL: For pen-based input, this type indicates the vertical tilt of the pen device. A value of 0 indicates that the pen is laid flat with nib at the bottom, 0.5 is 90 degrees, 1.0 is laid flat with nib at the top.", - "PEN_TILT_HORIZONTAL: For pen-based input, this type indicates the horizontal tilt of the pen device.", - "ABS_X: Value is an absolute horizontal coordinate that corresponds to a page area (usually the display or touchpad).", - "ABS_Y: Value is an absolute vertical coordinate that corresponds to a page area (usually the display or touchpad).", - "ENTERED_SURFACE|ENTERED: This message is sent by the input system when the mouse pointer enters a surface for the first time. The message value refers to the surface ID, which will be the same as the recipient.", - "LEFT_SURFACE|LEFT: This message is sent by the input system when the mouse pointer leaves a surface. The message value refers to the ID of the surface that has been left, which will be the same as the recipient.", + "PEN_TILT_XY: For pen-based input, this type indicates the vertical tilt of the pen device. A value of 0 indicates that the pen is laid flat with nib at the bottom, 0.5 is 90 degrees, 1.0 is laid flat with nib at the top.", + "ABS_XY: The X, Y values are defined as absolute coordinates, relative to the top-left of the display.", + "CROSSED_IN: This message is sent by the input system when the mouse pointer enters an area for the first time. The message value refers to the object ID of the container being monitored for movement.", + "CROSSED_OUT: This message is sent by the input system when the mouse pointer leaves an area. The message value refers to the object ID of the container being monitored for movement.", "PRESSURE: Amount of pressure applied, ranges from 0 (none) to 1.0 (normal) and possibly higher if user presses hard enough", - "DEVICE_TILT_X: Controller tilted on the X axis (left/right). Value indicates angle, -ve = left, +ve = right", - "DEVICE_TILT_Y: Controller tilted on the Y axis (up/down). Value indicates angle -ve = pull/up, +ve = push/down", + "DEVICE_TILT_XY: Controller tilted on the X/Y axis. Value indicates angle, -ve = left, +ve = right", "DEVICE_TILT_Z: Controller is rising or falling. Value expressed as 'speed',", "DISPLAY_EDGE: Recently supplied input occurred at the edge of the display.", "END: Private") @@ -238,7 +232,7 @@ enum("JET", { type="int", start=1, comment="JET constants are documented in GetI -- Flags for defining fields, methods, actions and functions. CLASSDEF's can only be used in field definitions for -- classes. FUNCDEF's can only be used in argument definitions for methods, actions and functions. -flags("FD", { weak=true, comment="Field descriptors." }, +flags("FD", { weak=true, comment="Field descriptors.", module="Core" }, { DOUBLE = "0x80000000: 64 bit float." }, { LONG = "0x40000000: 32 bit integer." }, { VARIABLE = "0x20000000: Supports multiple primitive types (long, double, large or pointer)." }, @@ -249,7 +243,7 @@ flags("FD", { weak=true, comment="Field descriptors." }, { BYTE = "0x01000000: 8 bit integer." }, { STRING = "0x00800000: Pointer to a string." }, { WORD = "0x00400000: 16 bit integer." }, - { PERCENTAGE = "0x00200000: Supplementary, indicates integer or float value is a percentage." }, + { SCALED = "0x00200000: Supplementary, indicates a float value for multiplicative scaling." }, { RGB = "0x00080000: Supplementary, if a long type then format is 0xAARRGGBB, if pointer then refers to an RGB structure." }, { UNSIGNED = "0x00040000: Supplementary, integer value is unsigned." }, { SYNONYM = "0x00020000: CLASSDEF Use to declare fields that duplicate the functionality of another field." }, @@ -301,7 +295,7 @@ flags("FD", { weak=true, comment="Field descriptors." }, { PTR_DOUBLERESULT = "DOUBLE|PTR|RESULT: Use for pointer-based value results only." } ) - struct("InputEvent", { }, [[ + struct("InputEvent", { module="Core" }, [[ cstruct(*InputEvent) Next # Next event in the chain double Value # The value associated with the Type large Timestamp # PreciseTime() of the recorded input @@ -317,37 +311,37 @@ flags("FD", { weak=true, comment="Field descriptors." }, int(JTYPE) Mask # Mask to use for checking against subscribers ]]) - struct("dcRequest", { comment="Data feed item request" }, [[ + struct("dcRequest", { comment="Data feed item request", module="Core" }, [[ int Item # Identifier for retrieval from the source char(4) Preference # Data preferences for the returned item(s) ]]) - struct("dcAudio", { comment="Data feed structure for Audio" }, [[ + struct("dcAudio", { comment="Data feed structure for Audio", module="Core" }, [[ int Size # Byte size of this structure int Format # Format of the audio data ]]) - struct("dcKeyEntry", { comment="Data feed structure for Keypress" }, [[ + struct("dcKeyEntry", { comment="Data feed structure for Keypress", module="Core" }, [[ int Flags # Shift/Control/CapsLock... int Value # ASCII value of the key A/B/C/D... large Timestamp # PreciseTime() at which the keypress was recorded int Unicode # Unicode value for pre-calculated key translations ]]) - struct("dcDeviceInput", { }, [[ - double Value # The value associated with the Type + struct("dcDeviceInput", { module="Core" }, [[ + double(2) Values # The value(s) associated with the Type large Timestamp # PreciseTime() of the recorded input oid DeviceID # The hardware device that this event originated from (note: This ID can be to a private/inaccessible object, the point is that the ID is unique) int(JTYPE) Flags # Broad descriptors for the given Type. Automatically defined when delivered to the pointer object int(JET) Type # JET constant ]]) - struct("DateTime", { comment="Generic structure for date-time management." }, [[ - int Year # Year - int Month # Month 1 to 12 - int Day # Day 1 to 31 - int Hour # Hour 0 to 23 - int Minute # Minute 0 to 59 - int Second # Second 0 to 59 - int TimeZone # TimeZone -13 to +13 + struct("DateTime", { comment="Generic structure for date-time management.", module="Core" }, [[ + short Year # Year + char Month # Month 1 to 12 + char Day # Day 1 to 31 + char Hour # Hour 0 to 23 + char Minute # Minute 0 to 59 + char Second # Second 0 to 59 + char TimeZone # TimeZone -13 to +13 ]]) diff --git a/scripts/dev/idl/idl-c.fluid b/scripts/dev/idl/idl-c.fluid index 0b69cbb63..bb1fdf8f0 100644 --- a/scripts/dev/idl/idl-c.fluid +++ b/scripts/dev/idl/idl-c.fluid @@ -26,193 +26,198 @@ glActionStubs = { NewOwner = "", -- Actions without parameters - Activate = " inline ERROR activate() { return Action(AC_Activate, this, NULL); }", - Clear = " inline ERROR clear() { return Action(AC_Clear, this, NULL); }", - Deactivate = " inline ERROR deactivate() { return Action(AC_Deactivate, this, NULL); }", - Disable = " inline ERROR disable() { return Action(AC_Disable, this, NULL); }", - Enable = " inline ERROR enable() { return Action(AC_Enable, this, NULL); }", - Flush = " inline ERROR flush() { return Action(AC_Flush, this, NULL); }", - Focus = " inline ERROR focus() { return Action(AC_Focus, this, NULL); }", - Hide = " inline ERROR hide() { return Action(AC_Hide, this, NULL); }", - Init = " inline ERROR init() { return InitObject(this); }", - Lock = " inline ERROR lock() { return Action(AC_Lock, this, NULL); }", - LostFocus = " inline ERROR lostFocus() { return Action(AC_LostFocus, this, NULL); }", - MoveToBack = " inline ERROR moveToBack() { return Action(AC_MoveToBack, this, NULL); }", - MoveToFront = " inline ERROR moveToFront() { return Action(AC_MoveToFront, this, NULL); }", - Next = " inline ERROR next() { return Action(AC_Next, this, NULL); }", - Prev = " inline ERROR prev() { return Action(AC_Prev, this, NULL); }", - Query = " inline ERROR query() { return Action(AC_Query, this, NULL); }", - Refresh = " inline ERROR refresh() { return Action(AC_Refresh, this, NULL); }", - Reset = " inline ERROR reset() { return Action(AC_Reset, this, NULL); }", - SaveSettings = " inline ERROR saveSettings() { return Action(AC_SaveSettings, this, NULL); }", - Show = " inline ERROR show() { return Action(AC_Show, this, NULL); }", - Sort = " inline ERROR sort() { return Action(AC_Sort, this, NULL); }", - Unlock = " inline ERROR unlock() { return Action(AC_Unlock, this, NULL); }", + Activate = " inline ERR activate() noexcept { return Action(AC_Activate, this, NULL); }", + Clear = " inline ERR clear() noexcept { return Action(AC_Clear, this, NULL); }", + Deactivate = " inline ERR deactivate() noexcept { return Action(AC_Deactivate, this, NULL); }", + Disable = " inline ERR disable() noexcept { return Action(AC_Disable, this, NULL); }", + Enable = " inline ERR enable() noexcept { return Action(AC_Enable, this, NULL); }", + Flush = " inline ERR flush() noexcept { return Action(AC_Flush, this, NULL); }", + Focus = " inline ERR focus() noexcept { return Action(AC_Focus, this, NULL); }", + Hide = " inline ERR hide() noexcept { return Action(AC_Hide, this, NULL); }", + Init = " inline ERR init() noexcept { return InitObject(this); }", + Lock = " inline ERR lock() noexcept { return Action(AC_Lock, this, NULL); }", + LostFocus = " inline ERR lostFocus() noexcept { return Action(AC_LostFocus, this, NULL); }", + MoveToBack = " inline ERR moveToBack() noexcept { return Action(AC_MoveToBack, this, NULL); }", + MoveToFront = " inline ERR moveToFront() noexcept { return Action(AC_MoveToFront, this, NULL); }", + Next = " inline ERR next() noexcept { return Action(AC_Next, this, NULL); }", + Prev = " inline ERR prev() noexcept { return Action(AC_Prev, this, NULL); }", + Query = " inline ERR query() noexcept { return Action(AC_Query, this, NULL); }", + Refresh = " inline ERR refresh() noexcept { return Action(AC_Refresh, this, NULL); }", + Reset = " inline ERR reset() noexcept { return Action(AC_Reset, this, NULL); }", + SaveSettings = " inline ERR saveSettings() noexcept { return Action(AC_SaveSettings, this, NULL); }", + Show = " inline ERR show() noexcept { return Action(AC_Show, this, NULL); }", + Sort = " inline ERR sort() noexcept { return Action(AC_Sort, this, NULL); }", + Unlock = " inline ERR unlock() noexcept { return Action(AC_Unlock, this, NULL); }", CopyData = [[ - inline ERROR copyData(OBJECTPTR Dest) { + inline ERR copyData(OBJECTPTR Dest) noexcept { struct acCopyData args = { .Dest = Dest }; return Action(AC_CopyData, this, &args); }]], DragDrop = [[ - inline ERROR dragDrop(OBJECTPTR Source, LONG Item, CSTRING Datatype) { + inline ERR dragDrop(OBJECTPTR Source, LONG Item, CSTRING Datatype) noexcept { struct acDragDrop args = { .Source = Source, .Item = Item, .Datatype = Datatype }; return Action(AC_DragDrop, this, &args); }]], Clipboard = [[ - inline ERROR clipboard(CLIPMODE Mode) { + inline ERR clipboard(CLIPMODE Mode) noexcept { struct acClipboard args = { Mode }; return Action(AC_Clipboard, this, &args); }]], Draw = [[ - inline ERROR draw() { return Action(AC_Draw, this, NULL); } - inline ERROR drawArea(LONG X, LONG Y, LONG Width, LONG Height) { + inline ERR draw() noexcept { return Action(AC_Draw, this, NULL); } + inline ERR drawArea(LONG X, LONG Y, LONG Width, LONG Height) noexcept { struct acDraw args = { X, Y, Width, Height }; return Action(AC_Draw, this, &args); }]], DataFeed = [[ - inline ERROR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) { + inline ERR dataFeed(OBJECTPTR Object, DATA Datatype, const void *Buffer, LONG Size) noexcept { struct acDataFeed args = { Object, Datatype, Buffer, Size }; return Action(AC_DataFeed, this, &args); }]], Move = [[ - inline ERROR move(DOUBLE X, DOUBLE Y, DOUBLE Z) { + inline ERR move(DOUBLE X, DOUBLE Y, DOUBLE Z) noexcept { struct acMove args = { X, Y, Z }; return Action(AC_Move, this, &args); }]], Read = [[ - template ERROR read(APTR Buffer, T Size, U *Result) { + template ERR read(APTR Buffer, T Size, U *Result) noexcept { static_assert(std::is_integral::value, "Result value must be an integer type"); static_assert(std::is_integral::value, "Size value must be an integer type"); - ERROR error; const LONG bytes = (Size > 0x7fffffff) ? 0x7fffffff : Size; struct acRead read = { (BYTE *)Buffer, bytes }; - if (!(error = Action(AC_Read, this, &read))) *Result = static_cast(read.Result); - else *Result = 0; - return error; + if (auto error = Action(AC_Read, this, &read); error IS ERR::Okay) { + *Result = static_cast(read.Result); + return ERR::Okay; + } + else { *Result = 0; return error; } } - template ERROR read(APTR Buffer, T Size) { + template ERR read(APTR Buffer, T Size) noexcept { static_assert(std::is_integral::value, "Size value must be an integer type"); const LONG bytes = (Size > 0x7fffffff) ? 0x7fffffff : Size; struct acRead read = { (BYTE *)Buffer, bytes }; return Action(AC_Read, this, &read); }]], Redo = [[ - inline ERROR redo(LONG Steps) { + inline ERR redo(LONG Steps) noexcept { struct acRedo args = { Steps }; return Action(AC_Redo, this, &args); }]], Redimension = [[ - inline ERROR redimension(DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE Width, DOUBLE Height, DOUBLE Depth) { + inline ERR redimension(DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE Width, DOUBLE Height, DOUBLE Depth) noexcept { struct acRedimension args = { X, Y, Z, Width, Height, Depth }; return Action(AC_Redimension, this, &args); } - inline ERROR redimension(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) { + inline ERR redimension(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) noexcept { struct acRedimension args = { X, Y, 0, Width, Height, 0 }; return Action(AC_Redimension, this, &args); }]], Rename = [[ - inline ERROR rename(CSTRING Name) { + inline ERR rename(CSTRING Name) noexcept { struct acRename args = { Name }; return Action(AC_Rename, this, &args); }]], Resize = [[ - inline ERROR resize(DOUBLE Width, DOUBLE Height, DOUBLE Depth = 0) { + inline ERR resize(DOUBLE Width, DOUBLE Height, DOUBLE Depth = 0) noexcept { struct acResize args = { Width, Height, Depth }; return Action(AC_Resize, this, &args); }]], Scroll = [[ - inline ERROR scroll(DOUBLE X, DOUBLE Y, DOUBLE Z = 0) { + inline ERR scroll(DOUBLE X, DOUBLE Y, DOUBLE Z = 0) noexcept { struct acScroll args = { X, Y, Z }; return Action(AC_Scroll, this, &args); }]], ScrollToPoint = [[ - inline ERROR scrollToPoint(DOUBLE X, DOUBLE Y, DOUBLE Z, STP Flags) { + inline ERR scrollToPoint(DOUBLE X, DOUBLE Y, DOUBLE Z, STP Flags) noexcept { struct acScrollToPoint args = { X, Y, Z, Flags }; return Action(AC_ScrollToPoint, this, &args); }]], Undo = [[ - inline ERROR undo(LONG Steps) { + inline ERR undo(LONG Steps) noexcept { struct acUndo args = { Steps }; return Action(AC_Undo, this, &args); }]], GetVar = [[ - inline ERROR getVar(CSTRING FieldName, STRING Buffer, LONG Size) { + inline ERR getVar(CSTRING FieldName, STRING Buffer, LONG Size) noexcept { struct acGetVar args = { FieldName, Buffer, Size }; - ERROR error = Action(AC_GetVar, this, &args); - if ((error) and (Buffer)) Buffer[0] = 0; + auto error = Action(AC_GetVar, this, &args); + if ((error != ERR::Okay) and (Buffer)) Buffer[0] = 0; return error; }]], MoveToPoint = [[ - inline ERROR moveToPoint(DOUBLE X, DOUBLE Y, DOUBLE Z, MTF Flags) { + inline ERR moveToPoint(DOUBLE X, DOUBLE Y, DOUBLE Z, MTF Flags) noexcept { struct acMoveToPoint moveto = { X, Y, Z, Flags }; return Action(AC_MoveToPoint, this, &moveto); }]], SaveImage = [[ - inline ERROR saveImage(OBJECTPTR Dest, CLASSID ClassID = 0) { + inline ERR saveImage(OBJECTPTR Dest, CLASSID ClassID = 0) noexcept { struct acSaveImage args = { Dest, { ClassID } }; return Action(AC_SaveImage, this, &args); }]], SaveToObject = [[ - inline ERROR saveToObject(OBJECTPTR Dest, CLASSID ClassID = 0) { + inline ERR saveToObject(OBJECTPTR Dest, CLASSID ClassID = 0) noexcept { struct acSaveToObject args = { Dest, { ClassID } }; return Action(AC_SaveToObject, this, &args); }]], Seek = [[ - inline ERROR seek(DOUBLE Offset, SEEK Position = SEEK::CURRENT) { + inline ERR seek(DOUBLE Offset, SEEK Position = SEEK::CURRENT) noexcept { struct acSeek args = { Offset, Position }; return Action(AC_Seek, this, &args); } - inline ERROR seekStart(DOUBLE Offset) { return seek(Offset, SEEK::START); } - inline ERROR seekEnd(DOUBLE Offset) { return seek(Offset, SEEK::END); } - inline ERROR seekCurrent(DOUBLE Offset) { return seek(Offset, SEEK::CURRENT); } + inline ERR seekStart(DOUBLE Offset) noexcept { return seek(Offset, SEEK::START); } + inline ERR seekEnd(DOUBLE Offset) noexcept { return seek(Offset, SEEK::END); } + inline ERR seekCurrent(DOUBLE Offset) noexcept { return seek(Offset, SEEK::CURRENT); } ]], SetVars = [[ - inline ERROR setVars(CSTRING tags, ...) { + inline ERR setVars(CSTRING tags, ...) noexcept { struct acSetVar args; va_list list; va_start(list, tags); while ((args.Field = va_arg(list, STRING)) != TAGEND) { args.Value = va_arg(list, STRING); - if (Action(AC_SetVar, this, &args) != ERR_Okay) { + if (Action(AC_SetVar, this, &args) != ERR::Okay) { va_end(list); - return ERR_Failed; + return ERR::Failed; } } va_end(list); - return ERR_Okay; + return ERR::Okay; }]], Write = [[ - inline ERROR write(CPTR Buffer, LONG Size, LONG *Result = NULL) { - ERROR error; + inline ERR write(CPTR Buffer, LONG Size, LONG *Result = NULL) noexcept { struct acWrite write = { (BYTE *)Buffer, Size }; - if (!(error = Action(AC_Write, this, &write))) { + if (auto error = Action(AC_Write, this, &write); error IS ERR::Okay) { if (Result) *Result = write.Result; + return ERR::Okay; + } + else { + if (Result) *Result = 0; + return error; } - else if (Result) *Result = 0; - return error; } - inline ERROR write(std::string Buffer, LONG *Result = NULL) { - ERROR error; + inline ERR write(std::string Buffer, LONG *Result = NULL) noexcept { struct acWrite write = { (BYTE *)Buffer.c_str(), LONG(Buffer.size()) }; - if (!(error = Action(AC_Write, this, &write))) { + if (auto error = Action(AC_Write, this, &write); error IS ERR::Okay) { if (Result) *Result = write.Result; + return ERR::Okay; + } + else { + if (Result) *Result = 0; + return error; } - else if (Result) *Result = 0; - return error; } - inline LONG writeResult(CPTR Buffer, LONG Size) { + inline LONG writeResult(CPTR Buffer, LONG Size) noexcept { struct acWrite write = { (BYTE *)Buffer, Size }; - if (!Action(AC_Write, this, &write)) return write.Result; + if (Action(AC_Write, this, &write) IS ERR::Okay) return write.Result; else return 0; }]], SelectArea = [[ - inline ERROR acSelectArea(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) { + inline ERR acSelectArea(DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) noexcept { struct acSelectArea area = { X, Y, Width, Height }; return Action(AC_SelectArea, this, &area); }]], SetVar = [[ - inline ERROR acSetVar(CSTRING FieldName, CSTRING Value) { + inline ERR acSetVar(CSTRING FieldName, CSTRING Value) noexcept { struct acSetVar args = { FieldName, Value }; return Action(AC_SetVar, this, &args); }]], @@ -223,6 +228,7 @@ glActionStubs = { glHeader = { } glOutput = { } glConstants = { } +glConstantOptions = { } glActiveRefs = { } -- For cType() function output(String) @@ -496,7 +502,9 @@ function flags(Prefix, Options, ...) table.insert(out, '') - if (glRestrict == nil) then + if nz(Options.module) and (Options.module:lower() != glModule.name:lower()) then + -- Do nothing, module restriction imposed. + elseif (glRestrict == nil) then for k,v in pairs(out) do table.insert(glConstants, v) end end @@ -602,7 +610,9 @@ function const(Prefix, Options, ...) table.insert(out, '') - if (glRestrict == nil) then //. + if nz(Options.module) and (Options.module:lower() != glModule.name:lower()) then + -- Do nothing, module restriction imposed. + elseif (glRestrict == nil) then //. for k,v in pairs(out) do table.insert(glConstants, v) end end @@ -649,13 +659,31 @@ function enum(Prefix, Options, ...) else table.insert(out, '#define ' .. Prefix .. '_' .. name .. ' ' .. inc) end + table.insert(list, { name=name, value=inc, comment=comment, synonym=synonym }) synonym = true end + + inc = inc + 1 + elseif (type(va) == 'table') then -- The client provided a table of fixed values + for name, client_val in pairs(va) do + if (type(client_val) != 'number') then + error('Client-provided enum values must be numeric') + end + + if (Options.type) then + table.insert(out, ' ' .. name .. ' = ' .. client_val .. ',') + elseif (Options.bits == 64) then + table.insert(out, '#define ' .. Prefix .. '_' .. name .. ' ' .. client_val .. 'LL') + else + table.insert(out, '#define ' .. Prefix .. '_' .. name .. ' ' .. client_val) + end + + table.insert(list, { name=name, value=client_val }) + end else - error('Invalid flag type for "' .. Prefix .. '", expected string, got "' .. type(va) .. '"') + error('Invalid enum type for "' .. Prefix .. '", expected string, got "' .. type(va) .. '"') end - inc = inc + 1 end if (Options.type) then @@ -664,7 +692,9 @@ function enum(Prefix, Options, ...) table.insert(out, '') - if (glRestrict == nil) then + if nz(Options.module) and (Options.module:lower() != glModule.name:lower()) then + -- Do nothing, module restriction imposed. + elseif (glRestrict == nil) then for k,v in pairs(out) do table.insert(glConstants, v) end end @@ -803,7 +833,9 @@ function struct(Name, Options, Def, Append) table.insert(out, '') end - if (glRestrict == nil) then + if nz(Options.module) and (Options.module:lower() != glModule.name:lower()) then + -- Do nothing, module restriction imposed. + elseif (glRestrict == nil) then for k,v in pairs(out) do table.insert(glOutput, v) end end @@ -915,12 +947,12 @@ function class(Name, Options, Blueprint, Private, Custom) local content = file.readAll(glFDLFolder .. path) content = content:gsub('\r\n', '\n') - -- Look for C/C++ action declarations, in the format: ERROR CLASS_Action(...). This will create a series + -- Look for C/C++ action declarations, in the format: ERR CLASS_Action(...). This will create a series -- of dummy action entries that can be overwritten with -ACTION- sections. local patterns = { - 'ERROR%s-' .. Name:upper() .. '_(%a-)%(obj.-%)', - 'ERROR%s-' .. Name:upper() .. '_(%a-)%(ext.-%)' + 'ERR%s-' .. Name:upper() .. '_(%a-)%(obj.-%)', + 'ERR%s-' .. Name:upper() .. '_(%a-)%(ext.-%)' } for _, pattern in pairs(patterns) do for actionName in string.gmatch(content, pattern) do @@ -974,7 +1006,7 @@ function class(Name, Options, Blueprint, Private, Custom) -- -- #define MT_[Prefix][Method] [ID] -- struct [Prefix][Method] { [Args] } - -- INLINE ERROR [Prefix][Method]([Args]) { } + -- INLINE ERR [Prefix][Method]([Args]) { } if (class.methods != nil) then local pfx = class.methodPrefix @@ -1043,10 +1075,10 @@ function class(Name, Options, Blueprint, Private, Custom) class.methods[k].struct = 'struct ' .. lpfx .. method.name .. ' { ' .. def .. ' };' if (method.inline != false) then - local inline = 'INLINE ERROR ' .. lpfx .. method.name .. '(' .. call .. ') {\n' + local inline = 'INLINE ERR ' .. lpfx .. method.name .. '(' .. call .. ') noexcept {\n' inline = inline .. ' struct ' .. lpfx .. method.name .. ' args = { ' .. values .. ' };\n' if (results) then - inline = inline .. ' ERROR error = Action(MT_' .. pfx .. method.name .. ', (OBJECTPTR)Ob, &args);\n' + inline = inline .. ' ERR error = Action(MT_' .. pfx .. method.name .. ', (OBJECTPTR)Ob, &args);\n' for _, p in pairs(method.params) do if (p.resultValue) then inline = inline .. ' if (' .. p.name .. ') *' .. p.name .. ' = args.' .. p.name .. ';\n' @@ -1368,12 +1400,12 @@ end ---------------------------------------------------------------------------------------------------------------------- -- Process the formal field definitions in a class blueprint. -function processClassFields(class, Blueprint) +function processClassFields(class, ClientBlueprint) local cdef = '' -- Process fields defined in the FDL - class.fields = extractFields(Blueprint, class.name) + class.fields = extractFields(ClientBlueprint, class.name) -- Add compiled fields into the field definitions. NB: Technically this relies on a circular reference, so such -- information can only be taken advantage of for phase 2 processing (class documentation). @@ -1381,10 +1413,11 @@ function processClassFields(class, Blueprint) if (class.meta != nil) then local newFields = {} + -- NB: Some classes don't output any fields (which is permissable) + local metaFields = class.meta.subFields - if not metaFields then metaFields = class.meta.fields end - if not metaFields then - error('No compiled fields declared for class ' .. class.name) + if (not metaFields) and (class.meta.classID == class.meta.baseClassID) then + metaFields = class.meta.fields end for k, f in ipairs(nz(metaFields, { })) do @@ -1459,7 +1492,6 @@ end -- Output the CPP compatible class definition function outputClassHeader(class, Private, Custom) - if nz(class.fields) then local physicalFields = false for _, f in ipairs(class.fields) do if not f.virtual then physicalFields = true end @@ -1559,7 +1591,7 @@ function outputClassHeader(class, Private, Custom) else field_type = 'const ' .. field_type end - elseif bit.band(f.flags, FD_POINTER) != 0 then + elseif bit.band(f.flags, bit.bor(FD_POINTER, FD_OBJECT)) != 0 then -- Applying const to pointers can cause type conversion issues. else field_type = 'const ' .. field_type @@ -1575,21 +1607,21 @@ function outputClassHeader(class, Private, Custom) if (field_type:sub(-2) == '[]') then field_type = field_type:sub(1,-3) .. '*' - output(string.format(' inline ERROR set%s(%s Value, LONG Elements) {', fid_name, field_type)) + output(string.format(' inline ERR set%s(%s Value, LONG Elements) noexcept {', fid_name, field_type)) elseif (bit.band(f.flags, FD_ARRAY) != 0) then if bit.band(f.flags, FD_CPP) != 0 then - output(string.format(' inline ERROR set%s(%s *Value) {', fid_name, field_type)) + output(string.format(' inline ERR set%s(%s *Value) noexcept {', fid_name, field_type)) else - output(string.format(' inline ERROR set%s(%s Value, LONG Elements) {', fid_name, field_type)) + output(string.format(' inline ERR set%s(%s Value, LONG Elements) noexcept {', fid_name, field_type)) end elseif (field_type == 'T &&') then - output(string.format(' template inline ERROR set%s(%s Value) {', fid_name, field_type)) + output(string.format(' template inline ERR set%s(%s Value) noexcept {', fid_name, field_type)) else - output(string.format(' inline ERROR set%s(%s Value) {', fid_name, field_type)) + output(string.format(' inline ERR set%s(%s Value) noexcept {', fid_name, field_type)) end if (f.write == 'Init') then - output(indent .. 'if (this->initialised()) return ERR_NoFieldAccess;') + output(indent .. 'if (this->initialised()) return ERR::NoFieldAccess;') end local err, fl, target = class.meta.mtFindField(mSys.StrHash(f.name, false)) @@ -1639,15 +1671,15 @@ function outputClassHeader(class, Private, Custom) end else if (field_type == 'T &&') then - output(string.format(' template inline ERROR set%s(%s Value) {', fid_name, field_type)) + output(string.format(' template inline ERR set%s(%s Value) noexcept {', fid_name, field_type)) else - output(string.format(' inline ERROR set%s(%s Value) {', fid_name, field_type)) + output(string.format(' inline ERR set%s(%s Value) noexcept {', fid_name, field_type)) end if (f.write == 'Init') then - output(indent .. 'if (this->initialised()) return ERR_NoFieldAccess;') + output(indent .. 'if (this->initialised()) return ERR::NoFieldAccess;') end output(indent .. string.format('this->%s = Value;', field_name)) - output(indent .. 'return ERR_Okay;') + output(indent .. 'return ERR::Okay;') end output(' }\n') @@ -1657,7 +1689,6 @@ function outputClassHeader(class, Private, Custom) end output('};') output() - end end ---------------------------------------------------------------------------------------------------------------------- @@ -1677,7 +1708,7 @@ function cleanXMLString(str, caller) if (cleanXMLString_xml != nil) then cleanXMLString_xml.statement = str - local err, clean_str = cleanXMLString_xml.mtGetString(0, XMF_INCLUDE_SIBLINGS) + local err, clean_str = cleanXMLString_xml.mtSerialise(0, XMF_INCLUDE_SIBLINGS) if (clean_str) then str = clean_str:match('(.-)'):trim() end else error('Failed to parse XML for ' .. nz(caller, 'undefined') .. '.') @@ -1753,11 +1784,11 @@ function functionNames(Prefix, ...) name = fname, def = ' void (*_' .. fname .. ')(void);', macro = function() -- Default macro, to be overridden by documented function - return 'template inline ERROR ' .. glFunctionPrefix:lower() .. fname .. - '(Args... pArgs) { return ' .. glModule.name .. 'Base->_' .. fname .. '(pArgs...); }' + return 'template inline ERR ' .. glFunctionPrefix:lower() .. fname .. + '(Args... pArgs) noexcept { return ' .. glModule.name .. 'Base->_' .. fname .. '(pArgs...); }' end, staticMacro = function() - return 'template ERROR ' .. glFunctionPrefix:lower() .. fname .. '(Args... pArgs);' + return 'template ERR ' .. glFunctionPrefix:lower() .. fname .. '(Args... pArgs);' end } @@ -2312,7 +2343,7 @@ function buildPrototypes() proto = proto .. ", " .. nz(param.extType, param.type) .. " " .. param.name end end - method.prototype = "ERROR " .. cl.methodPrefix:lower() .. method.name .. "(" .. proto .. ")" + method.prototype = "ERR " .. cl.methodPrefix:lower() .. method.name .. "(" .. proto .. ")" end end end diff --git a/scripts/dev/idl/idl-def.fluid b/scripts/dev/idl/idl-def.fluid index 63ef61023..6504caa19 100644 --- a/scripts/dev/idl/idl-def.fluid +++ b/scripts/dev/idl/idl-def.fluid @@ -74,6 +74,7 @@ function flags(Prefix, Options, ...) Options = checkOptions(Options) if (nz(Options.restrict)) or (glRestrict) then return end -- Restricted definitions are never exported + if nz(Options.module) and (Options.module:lower() != glModuleName:lower()) then return end if (glFeedback == 'verbose') then print('Processing flags ' .. Prefix) end local list = { } @@ -127,6 +128,7 @@ function enum(Prefix, Options, ...) Options = checkOptions(Options) if (nz(Options.restrict)) or (glRestrict) then return end -- Restricted definitions are never exported + if nz(Options.module) and (Options.module:lower() != glModuleName:lower()) then return end if (glFeedback == 'verbose') then print('Processing enum ' .. Prefix) end local list = { } @@ -139,6 +141,10 @@ function enum(Prefix, Options, ...) for _, name in ipairs(val:split('|')) do list[name] = inc end + elseif (type(enum_def) == 'table') then -- The client provided a table of fixed values + for name, client_val in pairs(enum_def) do + list[name] = client_val + end else error("Invalid flag type for '" .. Prefix .. "', expected string, got '" .. type(enum_def) .. "'") end @@ -154,6 +160,7 @@ function const(Prefix, Options, ...) Options = checkOptions(Options) if (nz(Options.restrict)) or (glRestrict) then return end -- Restricted definitions are never exported + if nz(Options.module) and (Options.module:lower() != glModuleName:lower()) then return end if (glFeedback == 'verbose') then print('Processing constants ' .. Prefix) end local list = { } @@ -306,21 +313,28 @@ function cType(Field, Origin) end end - do -- Short flags + do -- Char flags / Strong typing + if (Field.type:match('^char%((%a+)%)') != nil) then + Field.type = 'c' + return Field + end + end + + do -- Short flags / Strong typing if (Field.type:match('^short%((%a+)%)') != nil) then Field.type = 'w' return Field end end - do -- Integer flags + do -- Integer flags / Strong typing if (Field.type:match('^int%((%a+)%)') != nil) then Field.type = 'l' return Field end end - do -- Large flags + do -- Large flags / Strong typing if (Field.type:match('^large%((%a+)%)') != nil) then Field.type = 'x' return Field @@ -447,7 +461,8 @@ end function struct(Name, Options, Def, Append) Options = checkOptions(Options) - if (nz(Options.restrict)) or (glRestrict) then return end -- Restricted structures are never exported + if nz(Options.restrict) or (glRestrict) then return end -- Restricted structures are never exported + if nz(Options.module) and (Options.module:lower() != glModuleName:lower()) then return end if (glFeedback == 'verbose') then print('Processing structure ' .. Name) end local struct = { name = Name, @@ -551,7 +566,7 @@ function saveOutput() end if (glFormat == 'c') then - if (s:len() + c:len() >= 16 * 1024) then -- MSVC doesn't like strings > 16Kb, so we need this alternative + if (s:len() + c:len() >= 16 * 1024) then -- MSVC doesn't like defined strings > 16Kb, so we need this alternative file.acWrite('char glIDL[] = { ') file.acWrite(str_to_bytes(nz(s,'') .. nz(c,''))) file.acWrite(',0 };\n') diff --git a/scripts/dev/idl/idl-doc.fluid b/scripts/dev/idl/idl-doc.fluid index 714660166..d65048636 100644 --- a/scripts/dev/idl/idl-doc.fluid +++ b/scripts/dev/idl/idl-doc.fluid @@ -1,4 +1,4 @@ --- Extended documentation parsing functionality for idl-c +-- Extended documentation parsing functionality; included by idl-c require 'common' @@ -692,7 +692,7 @@ function docFunction(Function) end if nz(errors) then - out = out .. " \n" .. errors .. " \n" + out = out .. " \n" .. errors .. " \n" end elseif nz(Function.result.comment) then local ref = '' diff --git a/scripts/dev/idl/idl-types.fluid b/scripts/dev/idl/idl-types.fluid index bd2c92f1b..269e6cdf4 100644 --- a/scripts/dev/idl/idl-types.fluid +++ b/scripts/dev/idl/idl-types.fluid @@ -13,7 +13,7 @@ glTypes = { cstr = { fd='FD_STR', c_type='CSTRING' }, double = { fd='FD_DOUBLE', c_type='DOUBLE' }, eid = { fd='FD_LONG', c_type='EVENTID' }, - error = { fd='FD_LONG|FD_ERROR', c_type='ERROR' }, + error = { fd='FD_LONG|FD_ERROR', c_type='ERR' }, ext = { fd='FD_OBJECTPTR', c_type='OBJECTPTR' }, fid = { fd='FD_LARGE', c_type='FIELD' }, flags = { fd='FD_LONG', c_type='LONG' }, @@ -21,6 +21,7 @@ glTypes = { func = { fd='FD_FUNCTION', c_type='FUNCTION' }, hhandle = { fd='FD_PTR', c_type='HOSTHANDLE' }, int = { fd='FD_LONG', c_type='LONG' }, + int32 = { fd='FD_LONG', c_type='int32_t' }, large = { fd='FD_LARGE', c_type='LARGE' }, maxint = { fd='FD_LARGE', c_type='MAXINT' }, mem = { fd='FD_LONG', c_type='MEMORYID' }, @@ -323,50 +324,6 @@ function cType(Field, Origin) end end - do -- Char type reference - local prefix = Field.type:match("^char%((%a+)%)") - if (prefix != nil) then - Field.type = "BYTE" - Field.fullType = glTypes.char - Field.ref = glCustomTypes[prefix] - Field.lookup = prefix - - if (glCustomTypes[prefix]) then - glActiveRefs['TYPE:' .. prefix] = 1 - if (glCustomTypes[prefix].type) then -- Strongly typed - Field.type = prefix - end - else - print('Unknown custom type "' .. prefix .. '"') - end - goto finalise - end - end - - do -- Short type reference - local unsigned, prefix = Field.type:match("^(u-)short%((%a+)%)") - if (prefix != nil) then - if nz(unsigned) then - Field.type = "UWORD" - else - Field.type = "WORD" - end - Field.fullType = glTypes.int - Field.ref = glCustomTypes[prefix] - Field.lookup = prefix - - if (glCustomTypes[prefix]) then - glActiveRefs['TYPE:' .. prefix] = 1 - if (glCustomTypes[prefix].type) then -- Strongly typed - Field.type = prefix - end - else - print('Unknown custom type "' .. prefix .. '"') - end - goto finalise - end - end - do -- Integer flags type reference, can be used for strongly typed enum flags local prefix = Field.type:match("^flags%((%a+)%)") if (prefix != nil) then @@ -384,33 +341,30 @@ function cType(Field, Origin) end end - do -- Integer type reference - local prefix = Field.type:match("^int%((%a+)%)") + do -- Integer/Char/Large type reference + local type, prefix = Field.type:match("^([intlargecharuso]+)%((%a+)%)") if (prefix != nil) then - Field.type = "LONG" - Field.fullType = glTypes.int - Field.ref = glCustomTypes[prefix] - Field.lookup = prefix - - if (glCustomTypes[prefix] != nil) then - glActiveRefs['TYPE:' .. prefix] = 1 - if (glCustomTypes[prefix].type) then -- Strongly typed - Field.type = prefix - end + if (type == 'char') then + Field.type = 'char' + Field.fullType = glTypes.char + elseif (type == 'int') then + Field.type = 'LONG' + Field.fullType = glTypes.int + elseif (type == 'large') then + Field.type = 'LARGE' + Field.fullType = glTypes.large + elseif (type == 'short') then + Field.type = 'WORD' + Field.fullType = glTypes.short + elseif (type == 'ushort') then + Field.type = 'UWORD' + Field.fullType = glTypes.ushort else - print('Unknown custom type "' .. prefix .. '"') + error('Invalid type "' .. type .. '"') end - goto finalise - end - end - do -- Large type reference - local prefix = Field.type:match("^large%((%a+)%)") - if (prefix != nil) then - Field.type = "LARGE" - Field.fullType = glTypes.large - Field.ref = glCustomTypes[prefix] - Field.lookup = prefix + Field.ref = glCustomTypes[prefix] + Field.lookup = prefix if (glCustomTypes[prefix] != nil) then glActiveRefs['TYPE:' .. prefix] = 1 diff --git a/scripts/gui.fluid b/scripts/gui.fluid index 132fd11e4..8eee90c8a 100644 --- a/scripts/gui.fluid +++ b/scripts/gui.fluid @@ -128,11 +128,13 @@ end gui.getFontHeight = function(Font) if not Font.height then - local fnt = obj.new('font', { face=Font.face, point=Font.size }) - Font.height = fnt.height - Font.maxHeight = fnt.maxHeight + local err, handle = mVec.getFontHandle(Font.face, 'Regular', 0, Font.size) + local metrics = struct.new('FontMetrics') + mVec.getFontMetrics(handle, metrics) + Font.height = metrics.height + Font.spacing = metrics.lineSpacing end - return Font.maxHeight, Font.height + return Font.spacing, Font.height end ------------------------------------------------------------------------------ diff --git a/scripts/gui/button.fluid b/scripts/gui/button.fluid index de79b5fdc..9a020ca35 100644 --- a/scripts/gui/button.fluid +++ b/scripts/gui/button.fluid @@ -180,16 +180,16 @@ gui.button = function(Options) end end) - self.viewport.mtSubscribeInput(bit.bor(JTYPE_FEEDBACK, JTYPE_BUTTON, JTYPE_REPEATED), function(Viewport, Msg) + self.viewport.mtSubscribeInput(bit.bor(JTYPE_CROSSING, JTYPE_BUTTON, JTYPE_REPEATED), function(Viewport, Msg) repeat - if (Msg.type == JET_ENTERED_SURFACE) then + if (Msg.type == JET_CROSSED_IN) then local highlight = gui.strToRGB(gui.colours.rgb('widgetBkgd')) highlight.a = highlight.a * 0.5 self.bkgd.fill = gui.rgbToSVG(highlight) if self.events.cursorEntry then self.events.cursorEntry(self) end - elseif (Msg.type == JET_LEFT_SURFACE) then + elseif (Msg.type == JET_CROSSED_OUT) then self.bkgd.fill = gui.colours.rgb('widgetBkgd') if self.events.cursorExit then self.events.cursorExit(self) diff --git a/scripts/gui/colourdialog.fluid b/scripts/gui/colourdialog.fluid index 0241dc1f7..03ddbbbc7 100644 --- a/scripts/gui/colourdialog.fluid +++ b/scripts/gui/colourdialog.fluid @@ -564,7 +564,7 @@ gui.dialog.colour = function(Options) end end end - elseif (Msg.type == JET_ABS_X) or (Msg.type == JET_ABS_Y) then + elseif (Msg.type == JET_ABS_XY) then if (self._rainbowClick) then selectPalette(self, Msg.x - self._rainbow.winX, Msg.y - self._rainbow.winY) end end end diff --git a/scripts/gui/combobox.fluid b/scripts/gui/combobox.fluid index c50ed1cfc..4b983aaf4 100644 --- a/scripts/gui/combobox.fluid +++ b/scripts/gui/combobox.fluid @@ -267,6 +267,7 @@ gui.combobox = function(Options) lineLimit = 8, feedback = function(Menu, Item) self.text.string = Item.item + reportFeedback(self) self.viewport.acDraw() end }) diff --git a/scripts/gui/dialog.fluid b/scripts/gui/dialog.fluid index 658c6f46d..fa5af88ba 100644 --- a/scripts/gui/dialog.fluid +++ b/scripts/gui/dialog.fluid @@ -52,7 +52,7 @@ Example usage: gui.dialog.message({ modal = true, - image = 'icons:items/warning', + image = 'items/warning', title = 'Hamlet has a question', message = 'To be or not to be?', userInput = 'That is the question', @@ -67,6 +67,7 @@ Example usage: --]] require 'common' + require 'gui/window' if (gui == nil) then gui = { } end if (gui.dialog == nil) then gui.dialog = { } end @@ -85,10 +86,10 @@ local function defaultIcon(self) info = 'info' } for k,v in pairs(icons) do - if self.type == k then return 'icons:items/' .. v end + if self.type == k then return 'items/' .. v end end end - return 'icons:items/question' + return 'items/question' end gui.dialog.message = function(Options) @@ -99,7 +100,7 @@ gui.dialog.message = function(Options) feedback = Options.feedback, inputRequired = Options.inputRequired, message = Options.message, - fmtMessage = nz(Options.message, Options.fmtMessage) + fmtMessage = Options.fmtMessage } -- Change the message in the dialog @@ -122,22 +123,22 @@ gui.dialog.message = function(Options) processMessages(-1) end - local function matchWindowToDocSize(Window, Document) + local function matchWindowToDocSize(self, Document) local page_width = Document.pageWidth local page_height = Document.pageHeight - Window.surface.maxHeight = page_height - Window.surface.minHeight = page_height - Window.surface.insideHeight = page_height - Window.surface.maxWidth = page_width - Window.surface.minWidth = page_width - Window.surface.insideWidth = page_width + if (page_width < 100) then page_width = 100 end + if (page_height < 100) then page_height = 100 end + + self.window:sizeHints(page_width, page_height, page_width, page_height, false) + self.window.surface.insideWidth = page_width + self.window.surface.insideHeight = page_height end local function docEvent(Document, EventFlag, Parameters) if bit.band(EventFlag, DEF_LINK_ACTIVATED) != 0 then if self.feedback then - local responseIndex = tonumber(mSys.VarGetString(Parameters.parameters, 'response')) + local responseIndex = tonumber(Parameters.response) local response = self.options[responseIndex] local state = { } @@ -167,10 +168,32 @@ gui.dialog.message = function(Options) end local function buildDocument() + local option_icons = '' + + // At minimum, there must be an OK option. + + if not ((type(self.options) == 'table') and (#self.options > 0)) then + self.options = { { id=1, text='Close Dialog', icon='items/cancel' } } + end + + for i, option in ipairs(self.options) do + if option['icon'] then + if nz(option_icons) then option_icons = option_icons .. '\n' end + option_icons = option_icons .. ' \n' + end + end + local doc = [[ - + + + + ]] + .. option_icons .. [[ + + + + ]] if Options.envTemplate then @@ -184,22 +207,21 @@ gui.dialog.message = function(Options) doc = doc .. '\n' end - image = nz(Options.image, defaultIcon(self)) - if image:startsWith('icons:') then - image = image:gsub('^icons:(%w+)/(%w+)', 'icons:%1/%2(48)') - else - image = image:gsub('^(%w+)/(%w+)', 'icons:%1/%2(48)') + icon = nz(Options.image, defaultIcon(self)) + icon = icon:gsub('^(%w+)/(%w+)', '%1/%2') + local msg = self.fmtMessage + if not nz(msg) then + msg = string.escXML(nz(self.message, '')) + msg = string.gsub(msg, '\n', '
    ') end doc = doc .. [[ + - - - -

    ]] .. nz(self.fmtMessage, string.escXML(nz(self.message,''))) .. [[

    +

    ]] .. msg .. [[

    ]] if Options.userInput then @@ -215,7 +237,7 @@ gui.dialog.message = function(Options) msg = '' end - doc = doc .. '

    \n' + doc = doc .. '

    \n' end if Options.checkboxLabel then @@ -228,17 +250,10 @@ gui.dialog.message = function(Options) doc = doc .. Options.inject end - // Build the clickable options/buttons. At minimum, there must be an OK option. - - if not ((type(self.options) == 'table') and (#self.options > 0)) then - self.options = { { id=1, text='Close Dialog', icon='items/cancel' } } - end - - doc = doc .. '

    \n

    ' - + doc = doc .. '

    ' for i, option in ipairs(self.options) do if option['icon'] then - doc = doc .. '\n' + doc = doc .. '\n' end doc = doc .. '' .. option.text .. '\n' @@ -247,7 +262,6 @@ gui.dialog.message = function(Options) doc = doc .. '' end end - doc = doc .. '

    ' doc = doc .. [[ @@ -310,7 +324,7 @@ gui.dialog.message = function(Options) eventCallback = docEvent, path = '#Index', flags = 'Unrestricted|NoScrollbars', - defaultScript = obj.find('self') + clientScript = obj.find('self') }) lDoc.acDataFeed(0, DATA_XML, buildDocument()) @@ -322,13 +336,10 @@ gui.dialog.message = function(Options) self.input.textinput.mtSelectArea(0, 0, 20000, 20000) end - matchWindowToDocSize(self.window, lDoc) - - self.window.userFocus = lDocSurface.id + matchWindowToDocSize(self, lDoc) self.window:moveToFront() self.window:show() - lDocSurface.acFocus() self.document = lDoc diff --git a/scripts/gui/divider.fluid b/scripts/gui/divider.fluid index 050b7ed41..12186f828 100644 --- a/scripts/gui/divider.fluid +++ b/scripts/gui/divider.fluid @@ -187,7 +187,7 @@ gui.divider = function(Options) check(self._dividerVP.mtSubscribeInput(bit.bor(JTYPE_MOVEMENT, JTYPE_BUTTON), function(Viewport, Events) local ev = Events while ev do - if (ev.type == JET_ABS_X) or (ev.type == JET_ABS_Y) then + if (ev.type == JET_ABS_XY) then if self._buttonHeld then if (self._orientation == 'h') then arrangeAll(self, ev.absX - self._vp.absX) diff --git a/scripts/gui/fontdialog.fluid b/scripts/gui/fontdialog.fluid index 7075f429d..059d73802 100644 --- a/scripts/gui/fontdialog.fluid +++ b/scripts/gui/fontdialog.fluid @@ -26,8 +26,8 @@ Valid options to use when creating the dialog are as follows: path: The initial selection path. feedback: Refers to a Fluid function that will receive the user's response to the dialog. style: Preset the font's style, e.g. 'Bold Italic'. The default is 'Regular'. - size: Preset the font's point size, must be between 4 and 256. The default is 12. - face: Preset the font's face. Defaults to 'Open Sans'. + face: Preset the font's face and additional details. Defaults to 'Noto Sans'. + The full format is "Face:Size:Style:Colour" example: Overrides the example text normally printed in the dialog. colour: Change the default font colour to something other than black. @@ -45,23 +45,23 @@ gui.dialog.font = function(Options) local self = { -- Public variables windowID = nil, - face = 'Open Sans', - size = 12, + face = 'Noto Sans', + pointSize = 12, style = 'Regular', compactFace = nil, colour = { r=0, g=0, b=0, a=255 } } local lLongText = [[ -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Maecenas varius dignissim sapien eu pellentesque. Etiam libero velit, vehicula nec ante non, sodales ultricies metus. Phasellus commodo dolor turpis. Aliquam sed pellentesque magna, non luctus sapien. Etiam molestie dui nibh, nec finibus velit molestie non. Ut feugiat maximus elit nec mattis. Suspendisse porta vestibulum faucibus. Sed iaculis placerat justo id lobortis. Interdum et malesuada fames ac ante ipsum primis in faucibus. +Lorem ipsum dolor sit amet, consectetur adipiscing elit. Maecenas varius dignissim sapien eu pellentesque. Ètiam libero velit, vehicula nec ante non, sodales ultricies metus. Phasellus commodo dolor turpis. Âliquam sed pellentesque magna, non luctus sapien. Ètiam molestie dui nibh, nec finibus velit molestie non. Ut feugiat maximus elit nec mattis. Suspendisse porta vestibulum faucibus. Sed iaculis placerat justo id lobortis. Interdum et malesuada fames ac ante ipsum primis in faucibus. Morbi tincidunt varius ante sit amet pulvinar. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Nulla ante orci, faucibus non odio viverra, tempus rutrum ex. Mauris sit amet hendrerit quam. Vestibulum tincidunt magna suscipit ultrices congue. Aliquam et blandit tellus, ut porta libero. Cum sociis natoque penatibus et magnis dis parturient montes, nascetur ridiculus mus. Cras vulputate congue eros sed placerat. Nunc eleifend nec felis sit amet fermentum. Cras suscipit ullamcorper eros, id consectetur quam blandit ac. Suspendisse sed diam ut sem euismod accumsan commodo vehicula sapien. Nullam nisl augue, suscipit vitae posuere sit amet, porttitor et ex. Duis at elit pellentesque, placerat risus in, placerat mauris. Nam in metus sed dui iaculis aliquam sed ut sem. In varius euismod quam, sed lobortis sem. Aliquam nec dui magna. Suspendisse lobortis enim vitae vestibulum accumsan. Pellentesque ac tincidunt est. Ut porta, arcu eu ornare placerat, urna urna venenatis est, at imperdiet lectus justo vel neque. Sed congue dolor eget erat dignissim sollicitudin. Aliquam mollis massa in est gravida faucibus. -Fusce auctor metus egestas commodo laoreet. Morbi sed venenatis augue. Maecenas non nisi vehicula, aliquam turpis in, mattis lectus. Donec magna metus, tempor fringilla metus ac, ultricies efficitur ante. Quisque at semper elit. Ut in purus in est venenatis interdum. Curabitur a dui mauris. Suspendisse potenti. Suspendisse tempus dictum ipsum, id condimentum nulla fermentum sed. Etiam mattis ligula lacus, a tempor felis sodales fermentum. Donec in risus vulputate, tempor neque vel, volutpat mauris. Integer placerat a nunc a aliquet. Phasellus quis porta leo. Etiam et arcu ex. Nunc dictum at ipsum eu dapibus. +Fusce auctor metus egestas commodo laoreet. Morbi sed venenatis augue. Maecenas non nisi vehicula, aliquam turpis in, mattis lectus. Dõnec magna metus, tempor fringilla metus ac, ultricies efficitur ante. Quisque at semper elit. Ut in purus in est venenatis interdum. Curabitur a dui mauris. Suspendisse potenti. Suspendisse tempus dictum ipsum, id condimentum nulla fermentum sed. Etiam mattis ligula lacus, a tempor felis sodales fermentum. Donec in risus vulputate, tempor neque vel, volutpat mauris. Integer placerat a nunc a aliquet. Phasellus quis porta leo. Etiam et arcu ex. Nunc dictum at ipsum eu dapibus. -Cras metus mi, ultricies nec blandit condimentum, congue dapibus libero. Nulla eget ornare ante, ac efficitur turpis. Proin venenatis eget sapien vitae volutpat. In interdum id ante in aliquet. Quisque convallis lacus in gravida fringilla. Nam porta pellentesque turpis, ut efficitur neque suscipit vel. Morbi vitae consequat nisl. Donec turpis lorem, dapibus eget scelerisque quis, porttitor bibendum leo. +Ĉras metus mi, ultricies nec blandit condimentum, congue dapibus libero. Nulla eget ornare ante, ac efficitur turpis. Proin venenatis eget sapien vitae volutpat. In interdum id ante in aliquet. Quisque convallis lacus in gravida fringilla. Nam porta pellentesque turpis, ut efficitur neque suscipit vel. Morbi vitae consequat nisl. Donec turpis lorem, dapibus eget scelerisque quis, porttitor bibendum leo. ]] local lWindow, lFonts, vwSize, vwStyle, vwFace @@ -76,7 +76,7 @@ Cras metus mi, ultricies nec blandit condimentum, congue dapibus libero. Nulla e local function sendFeedback(Accepted) local colour = self.colour.r .. ',' .. self.colour.g .. ',' .. self.colour.b .. ',' .. self.colour.a - self.compactFace = self.face .. ':' .. self.size .. ':' .. self.style .. ':' .. colour + self.compactFace = self.face .. ':' .. self.pointSize .. ':' .. self.style .. ':' .. colour if (lOptions.feedback != nil) then lOptions.feedback(self, Accepted) @@ -87,22 +87,24 @@ Cras metus mi, ultricies nec blandit condimentum, congue dapibus libero. Nulla e end local function refreshGuidelines() - local seq = '' - local gap = exampleMargin() - local spacing = self.font.lineSpacing - local pageWidth = self.examplePage.width - - local x1 = gap - local x2 = pageWidth - gap - for y = gap + self.font.height, self.examplePage.height, spacing do - seq = seq .. string.format('M%f,%f L%f,%f ', x1, y, x2, y) - end - self.guidelines.sequence = seq - if self.exampleText then + local seq = '' + local gap = exampleMargin() + local spacing = self.exampleText.lineSpacing + local pageWidth = self.examplePage.width + local baseline = self.exampleText.y + + local x1 = gap + local x2 = pageWidth - gap + for y = baseline, self.examplePage.height, spacing do + seq = seq .. string.format('M%f,%f L%f,%f ', x1, y, x2, y) + end + self.guidelines.sequence = seq + self.exampleText.inlineSize = x2 - x1 self.exampleText.x = gap - self.exampleText.y = gap + self.font.height + else + self.guidelines.sequence = 'M-1,-1 Z' end end @@ -112,36 +114,34 @@ Cras metus mi, ultricies nec blandit condimentum, congue dapibus libero. Nulla e end local pageWidth = self.examplePage.width - local newStyle = self.face .. '+' .. self.size .. '+' .. self.style - if newStyle == self.currentStyle then return end - self.currentStyle = newStyle - - self.font = obj.new('font', { - face = self.face, - point = self.size, - style = self.style, - string = nz(lOptions.example, lLongText) - }) - local gap = exampleMargin() - refreshGuidelines() - if self.exampleText then self.exampleText.free() + self.exampleText = nil end - self.exampleText = self.examplePage.new('VectorText', { - x = gap, - y = gap + self.font.height, - fill = 'rgb(0,0,0)', - inlineSize = pageWidth - (gap * 2), - face = self.face, - fontSize = self.size .. 'pt', - fontStyle = self.font.style, - string = lLongText, - textFlags = VTXF_RASTER - }) + catch(function() + self.exampleText = self.examplePage.new('VectorText', { + x = gap, + fill = 'rgb(0,0,0)', + inlineSize = pageWidth - (gap * 2), + face = self.face, + fontSize = self.pointSize .. 'pt', + fontStyle = self.style, + string = lLongText, + textFlags = VTXF_RASTER + }) + end, + function() + msg('Failed to create example text for ' .. self.face .. ' ' .. nz(self.style,'NIL')) + end) + + if self.exampleText then + self.exampleText.y = math.floor(gap + self.exampleText.displaySize) + end + + refreshGuidelines() collectgarbage() self.viewport.acDraw() @@ -161,12 +161,16 @@ Cras metus mi, ultricies nec blandit condimentum, congue dapibus libero. Nulla e lFonts[font.name] = { } lFonts[font.name].order = index lFonts[font.name].name = font.name + lFonts[font.name].alias = font.alias lFonts[font.name].styles = string.split(font.styles, ',') lFonts[font.name].sizes = font.points + lFonts[font.name].hidden = font.hidden if nz(font.scalable) then lFonts[font.name].scalable = true end - table.insert(lFontsSorted, lFonts[font.name]) + if not nz(font.hidden) then + table.insert(lFontsSorted, lFonts[font.name]) + end index = index + 1 font = font.next end @@ -184,6 +188,7 @@ Cras metus mi, ultricies nec blandit condimentum, congue dapibus libero. Nulla e local function showStyles(Face) local styles = { } + if nz(lFonts[Face].alias) then Face = lFonts[Face].alias end local font_styles = nz(lFonts[Face].styles, { 'Regular' }) for _, v in ipairs(font_styles) do table.insert(styles, { id=v, name=v }) @@ -214,7 +219,7 @@ Cras metus mi, ultricies nec blandit condimentum, congue dapibus libero. Nulla e if (lOptions.face) then local s = string.split(face, ':') -- FaceName, Size, Style, Colour if (s[1]) then lOptions.face = s[1] end - if (s[2]) then lOptions.size = s[2] end + if (s[2]) then lOptions.pointSize = s[2] end if (s[3]) then lOptions.style = s[3] end if (s[4]) then lOptions.colour = s[4] end end @@ -324,11 +329,11 @@ Cras metus mi, ultricies nec blandit condimentum, congue dapibus libero. Nulla e textAttrib = 'name', itemSelected = function(View, Reason, Item) local selection = Item.name - self.size = tonumber(selection) - if (self.size < 4) then - self.size = 4 - elseif (self.size > 400) then - self.size = 400 + self.pointSize = tonumber(selection) + if (self.pointSize < 4) then + self.pointSize = 4 + elseif (self.pointSize > 400) then + self.pointSize = 400 end collectgarbage() refreshExample() @@ -378,7 +383,17 @@ Cras metus mi, ultricies nec blandit condimentum, congue dapibus libero. Nulla e -- Highlight the correct style, trying to keep the current setting if possible. - if not self.style then + if self.style and lFonts[self.face] then + local supported = false + for _, v in ipairs(lFonts[self.face].styles) do + if (v == self.style) then + supported = true + break + end + end + + if not supported then self.style = 'Regular' end + else self.style = 'Regular' end @@ -386,6 +401,8 @@ Cras metus mi, ultricies nec blandit condimentum, congue dapibus libero. Nulla e if (Item.id == self.style) then return true end end) + refreshExample() + local sizes = lFonts[Item.name].sizes if (lFonts[Item.name].scalable) or (sizes == nil) or (#sizes == 0) then sizes = lSizes @@ -393,16 +410,17 @@ Cras metus mi, ultricies nec blandit condimentum, congue dapibus libero. Nulla e showFontSizes(sizes) - if (sizes[1] > self.size) then self.size = sizes[1] end - highlightSize(self.size) - - refreshExample() + if (sizes[1] > self.pointSize) then self.pointSize = sizes[1] end + highlightSize(self.pointSize) end }) local faces = { } for _, font in ipairs(lFontsSorted) do local new_font = { id=font.name, name=font.name } + + if nz(font.alias) then font = lFonts[font.alias] end + if (font.scalable) then new_font.icon = 'items/font' else @@ -415,14 +433,14 @@ Cras metus mi, ultricies nec blandit condimentum, congue dapibus libero. Nulla e -- Preselect list items based on the preferences supplied by the client. vwFace.selectItems(function(Item) - if Item.id == nz(lOptions.face, 'Open Sans') then return true end + if Item.id == nz(lOptions.face, 'Noto Sans') then return true end end) vwStyle.selectItems(function(Item) if Item.id == nz(lOptions.style, 'Regular') then return true end end) - highlightSize(self.size) + highlightSize(self.pointSize) lWindow:moveToFront() lWindow:show() diff --git a/scripts/gui/icon.fluid b/scripts/gui/icon.fluid index c8e40a4fb..395a100a9 100644 --- a/scripts/gui/icon.fluid +++ b/scripts/gui/icon.fluid @@ -51,8 +51,6 @@ local function imageLocation(Path) end gui.icon = function(Options) - local mFont = mod.load('font') - local self = { -- Public variables parentViewport = Options.target, events = nz(Options.events, { }), @@ -111,15 +109,16 @@ gui.icon = function(Options) lFontSize = 10 end - local font = obj.new('font', { face = gui.fonts.icon.face, point = lFontSize }) - - lLineHeight = font.maxHeight + local err, font = mVec.getFontHandle(gui.fonts.icon.face, "Regular", 0, lFontSize) + local metrics = struct.new('FontMetrics') + local err = mVec.getFontMetrics(font, metrics) + lLineHeight = metrics.lineSpacing -- Extract each word's pixel width local widest_word = 0 for _, word in ipairs(lText) do - local width = mFont.stringWidth(font, word, -1) + local width = mVec.stringWidth(font, word, -1) if (width > widest_word) then widest_word = width end table.insert(lWords, { word=word, width=width }) end @@ -137,7 +136,7 @@ gui.icon = function(Options) current_line = word.word else local new_line = current_line .. ' ' .. word.word - local width = mFont.stringWidth(font, new_line, -1) + local width = mVec.stringWidth(font, new_line, -1) if (width + (MARGIN * 2) < lIconWidth) then current_line = new_line else diff --git a/scripts/gui/input.fluid b/scripts/gui/input.fluid index 3b7b68ebf..218d763eb 100644 --- a/scripts/gui/input.fluid +++ b/scripts/gui/input.fluid @@ -226,11 +226,11 @@ gui.input = function(Options) end) if self.events.cursorEntry or self.events.cursorExit then - self.inputViewport.mtSubscribeInput(JTYPE_FEEDBACK, function(Viewport, Msg) + self.inputViewport.mtSubscribeInput(JTYPE_CROSSING, function(Viewport, Msg) repeat - if (Msg.type == JET_ENTERED_SURFACE) then + if (Msg.type == JET_CROSSED_IN) then if self.events.cursorEntry then self.events.cursorEntry(self) end - elseif (Msg.type == JET_LEFT_SURFACE) then + elseif (Msg.type == JET_CROSSED_OUT) then if self.events.cursorExit then self.events.cursorExit(self) end end Msg = Msg.next diff --git a/scripts/gui/libview.fluid b/scripts/gui/libview.fluid index 935677eb2..45f000010 100644 --- a/scripts/gui/libview.fluid +++ b/scripts/gui/libview.fluid @@ -4,7 +4,6 @@ require 'gui' require 'gui/scrollbar' - if (not mFont) then mFont = mod.load('font') end if (not mGfx) then mGfx = mod.load('display') end if (not mVec) then mVec = mod.load('vector') end @@ -562,26 +561,20 @@ gui.initView = function(Options, BuildUI, NewItems) end end) - vw.page.mtSubscribeInput(bit.bor(JTYPE_MOVEMENT, JTYPE_BUTTON, JTYPE_FEEDBACK, JTYPE_EXT_MOVEMENT), function(Viewport, Events) + vw.page.mtSubscribeInput(bit.bor(JTYPE_MOVEMENT, JTYPE_BUTTON, JTYPE_CROSSING, JTYPE_EXT_MOVEMENT), function(Viewport, Events) local ev = Events while (ev) do - if (ev.type == JET_ENTERED_SURFACE) then + if (ev.type == JET_CROSSED_IN) then vw.cursorX = ev.x vw.cursorY = ev.y checkCursorImage(vw) - elseif (ev.type == JET_LEFT_SURFACE) then + elseif (ev.type == JET_CROSSED_OUT) then vw.cursorX = nil vw.cursorY = nil checkCursorImage(vw) if vw.hItem then highlightItem(vw, nil) end - elseif (ev.type == JET_WHEEL) then - local length = vw.page.height - vw.window.height - if (length > 0) then - if (length > vw.window.height) then length = vw.window.height end - vw.scrollbar.scrollPage(0, -ev.value * length * 0.06) - end elseif (ev.type == JET_BUTTON_1) then if (bit.band(ev.flags, JTYPE_REPEATED) != 0) then return @@ -624,7 +617,7 @@ gui.initView = function(Options, BuildUI, NewItems) vw.scene.surface.mtScheduleRedraw() end - elseif (ev.type == JET_ABS_X) or (ev.type == JET_ABS_Y) then + elseif (ev.type == JET_ABS_XY) then if vw.activeZone and vw.activeZone.clickMove then vw.activeZone.clickMove(ev) end diff --git a/scripts/gui/listview.fluid b/scripts/gui/listview.fluid index 0acd6293c..44f1cc9d9 100644 --- a/scripts/gui/listview.fluid +++ b/scripts/gui/listview.fluid @@ -73,6 +73,8 @@ gui.listView = function(Options) -- When an item is hovered, create a highlight for it. local function highlightItem(View, Item, Highlighted) + if (Item._vectors.viewport == nil) then return end + if (not Item._vectors.highlight) then Item._vectors.highlight = Item._vectors.viewport.new('VectorRectangle', { roundX = 4, roundY = 4, width = '100%', height = '100%', visibility = VIS_HIDDEN @@ -101,13 +103,6 @@ gui.listView = function(Options) end local function constructListView(View, Scene, Viewport, Page) - if not View.itemFont then - View.itemFont = obj.new('font', { - face = gui.fonts.widget.face, - point = string.format('%.2fpt', gui.fonts.widget.size) - }) - end - local width = Viewport.width - EDGE - EDGE local height = Viewport.height local x = EDGE @@ -196,7 +191,9 @@ gui.listView = function(Options) item._vectors.text.string = item[lTextAttrib] --font.wrapEdge = x + item.Width - width = internalMargin + iconMargin + mFont.stringWidth(View.itemFont, item[lTextAttrib], -1) + internalMargin + local err, bx, by, bw, bh = item._vectors.text.mtGetBoundary(0) + + width = internalMargin + iconMargin + bw + internalMargin if item._selected then item._vectors.text.fill = lColours.fillSelectFont diff --git a/scripts/gui/menu.fluid b/scripts/gui/menu.fluid index 08d14ee68..9cd195c8d 100644 --- a/scripts/gui/menu.fluid +++ b/scripts/gui/menu.fluid @@ -30,13 +30,13 @@ Valid options to use when creating the menu are as follows: require 'gui' include 'display' - if (not mFont) then mFont = mod.load('font') end if (not mGfx) then mGfx = mod.load('display') end -local FONT_FACE = 'Open Sans' +local FONT_FACE = 'Noto Sans' local FONT_SIZE = 11 local MARGIN = 6 local RIGHT_MARGIN = MARGIN +local ITEM_SPACING = 1.2 local function applyFill(Vector, Fill) while (Vector != nil) do @@ -88,7 +88,7 @@ gui.menu = function(Options) -- To use the clip, set the 'mask' field of any drawable vector. self.clip = self.scene.new('VectorClip', { units='BoundingBox' }) - local clipRect = self.clip.new('VectorRectangle', { + local clipRect = self.clip.viewport.new('VectorRectangle', { x = 1.5, y = 1.5, roundX = 3, @@ -158,13 +158,14 @@ gui.menu = function(Options) string = item['item'] }) + local err, bx, by, bw, bh = vText.mtGetBoundary(0) + mi.text = vText - mi.textY = y + vText.font.height + ((vText.font.maxHeight - vText.font.height)/2) + mi.textY = y + ((vText.lineSpacing + vText.displaySize) * 0.5) - itemWidth = mFont.StringWidth(vText.font, item['item'], -1) - if (itemWidth > widestItem) then widestItem = itemWidth end + if (bw > widestItem) then widestItem = bw end - local icon_size = vText.font.maxHeight + local icon_size = vText.displayHeight + vText.descent if showIcons and item['icon'] then catch(function() @@ -191,15 +192,18 @@ gui.menu = function(Options) align = 'right', string = key }) - vKey.y = y + vKey.font.height + ((vKey.font.maxHeight - vKey.font.height)/2) - keyWidth = mFont.StringWidth(vKey.font, key, -1) + local err, bx, by, bw, bh = vKey.mtGetBoundary(0) + + vKey.y = y + ((vKey.lineSpacing + vKey.displaySize) * 0.5) + + keyWidth = bw if (keyWidth > widestKey) then widestKey = keyWidth end mi.keyText = vKey end vText.y = mi.textY - mi.height = vText.font.maxHeight * 1.4 + mi.height = vText.lineSpacing * ITEM_SPACING y = y + mi.height table.insert(self.items, mi) @@ -497,7 +501,7 @@ gui.menu = function(Options) end end) - self.viewport.mtSubscribeInput(bit.bor(JTYPE_MOVEMENT, JTYPE_BUTTON), function(Viewport, Events) + self.viewport.mtSubscribeInput(bit.bor(JTYPE_MOVEMENT, JTYPE_BUTTON, JTYPE_CROSSING), function(Viewport, Events) local ev = Events while ev do if (ev.type == JET_BUTTON_1) then @@ -512,18 +516,16 @@ gui.menu = function(Options) self.surface.acHide() end end - elseif (ev.type == JET_ABS_X) or (ev.type == JET_ABS_Y) then + elseif (ev.type == JET_ABS_XY) then local highlightFound = false - if (ev.overID == self.surface.id) then - for _, item in pairs(self.items) do - if not item.lineBreak then - if (ev.y >= item.y) and (ev.y < item.y + item.height) then - if (self.hItem != item) then - highlightItem(item) - end - highlightFound = true - break + for _, item in pairs(self.items) do + if not item.lineBreak then + if (ev.y >= item.y) and (ev.y < item.y + item.height) then + if (self.hItem != item) then + highlightItem(item) end + highlightFound = true + break end end end diff --git a/scripts/gui/menubar.fluid b/scripts/gui/menubar.fluid index 4055f3a9b..eb7a41dc6 100644 --- a/scripts/gui/menubar.fluid +++ b/scripts/gui/menubar.fluid @@ -31,8 +31,6 @@ as follows: require 'translate' include 'vector' - if (not mFont) then mFont = mod.load('font') end - local lColours = { textFill = 'rgb(255,255,255)', textHighlight = 'rgb(160,160,220)', @@ -159,15 +157,16 @@ local function arrangeItems(self) if nz(item.displayName) then item.vectorText = self._vg.new('VectorText', { x = x + iconWidth + VMARGIN, - face = 'Source Sans Pro', + face = 'Source Sans Pro,*', fontSize = FONT_SIZE, fill = lColours.textFill, string = item.displayName }) - item.gfxWidth = iconWidth + mFont.StringWidth(item.vectorText.font, item.displayName, -1) + (VMARGIN * 2) + local err, bx, by, bw, bh = item.vectorText.mtGetBoundary(0) + item.gfxWidth = iconWidth + bw + (VMARGIN * 2) item.width = item.gfxWidth + GAP - item.vectorText.y = (self.viewport.height * 0.5) + (item.vectorText.font.height * 0.5) + item.vectorText.y = math.floor((self.viewport.height + item.vectorText.displaySize) * 0.5) if self._disabled or item.disabled then item.vectorText.opacity = 0.5 @@ -337,12 +336,12 @@ gui.menubar = function(HostVP, Options) self.viewport.acDraw() end - self.viewport.mtSubscribeInput(bit.bor(JTYPE_BUTTON, JTYPE_MOVEMENT, JTYPE_FEEDBACK), function(Viewport, Events) + self.viewport.mtSubscribeInput(bit.bor(JTYPE_BUTTON, JTYPE_MOVEMENT, JTYPE_CROSSING), function(Viewport, Events) local ev = Events while ev do - if (ev.type == JET_ENTERED_SURFACE) then + if (ev.type == JET_CROSSED_IN) then - elseif (ev.type == JET_LEFT_SURFACE) then + elseif (ev.type == JET_CROSSED_OUT) then if self._currentItem then hoverUpdate(nil) end diff --git a/scripts/gui/scrollbar.fluid b/scripts/gui/scrollbar.fluid index 66a0d3b90..a2c9635dc 100644 --- a/scripts/gui/scrollbar.fluid +++ b/scripts/gui/scrollbar.fluid @@ -12,8 +12,11 @@ The following example illustrates typical usage: Valid options to use when creating the scrollbar are as follows: target: Required. Refers to a viewport that will contain the scrollbar. - view: Required. A viewport that is within the target and contains the page content. Note that the dimensions of the view will be controlled by the scrollbar. - page: Required. A viewport within the view. The page will contain the content for display and must use fixed width and height values. + view: Required. A viewport that is within the target and contains the page content. Note that the dimensions + of the view will be controlled by the scrollbar, notably the XOffset and YOffset which the client should + set to zero. + page: Required. A viewport within the view. The page will contain the content for display and must use fixed + width and height values. breadth: Overrides the breadth of the scrollbar in pixel units. direction: Limits scrolling to 'vertical' or 'horizontal' if desired. Both axis are enabled by default. @@ -33,6 +36,11 @@ Functionality: setFixedPageSize(Width, Height) Defines a fixed page size. + +Internally the scrollbar code works by monitoring the FM_PATH_CHANGED event of the provided view and page. The +recalcSlidersFromView() function is responsible for making adjustments to the scrollbars, and alters their visibility +as required. + --]] require 'common' @@ -172,7 +180,7 @@ gui.scrollbar = function(Options) if (Y != lVBar.slider.offset) or (slider_height != lVBar.slider.size) then local pct_pos = Y / (host_height - slider_height) - lPage.y = -((lPage.height - lView.height) * pct_pos) + lPage.y = -math.floor((lPage.height - lView.height) * pct_pos) lTarget.acDraw() end end @@ -200,7 +208,7 @@ gui.scrollbar = function(Options) if (X != lHBar.slider.offset) or (slider_width != lHBar.slider.size) then local pct_pos = X / (host_width - slider_width) - lPage.x = -((lPage.width - lView.width) * pct_pos) + lPage.x = -math.floor((lPage.width - lView.width) * pct_pos) lTarget.acDraw() end end @@ -292,8 +300,8 @@ gui.scrollbar = function(Options) end if (x != current_x) or (y != current_y) then - lPage.x = x - lPage.y = y + lPage.x = math.floor(x) + lPage.y = math.floor(y) lTarget.acDraw() end end @@ -331,6 +339,8 @@ gui.scrollbar = function(Options) if (lView.id == lTarget.id) then error('The view and target cannot be the same.') end if (lPage.parent.id != lView.id) then error('The page is not a child of the view.') end if (lView.overflow != VOF_HIDDEN) then error('The overflow setting for the view must be HIDDEN.') end + if (lView.xOffset != 0) then error('The XOffset of the view must be set to zero.') end + if (lView.yOffset != 0) then error('The YOffset of the view must be set to zero.') end if (Options.direction == 'all') then Options.direction = nil end @@ -367,13 +377,13 @@ gui.scrollbar = function(Options) if (px + pw < lView.width) then local x = lView.width - pw if (x > 0) then x = 0 end - if (px != x) then lPage.x = x end + if (px != x) then lPage.x = math.floor(x) end end if (py + lPage.height < lView.height) then local y = lView.height - lPage.height if (y > 0) then y = 0 end - if (py != y) then lPage.y = y end + if (py != y) then lPage.y = math.floor(y) end end recalcSlidersFromView() @@ -383,5 +393,19 @@ gui.scrollbar = function(Options) recalcSlidersFromView() end) + lPage.mtSubscribeInput(JTYPE_EXT_MOVEMENT, function(Viewport, Events) + local ev = Events + while (ev) do + if (ev.type == JET_WHEEL) then + local length = lPage.height - lView.height + if (length > 0) then + if (length > lView.height) then length = lView.height end + self.scrollPage(0, -ev.value * length * 0.06) + end + end + ev = ev.next + end + end) + return self end diff --git a/scripts/gui/toolbar.fluid b/scripts/gui/toolbar.fluid index fc89bd94e..3e28d49fe 100644 --- a/scripts/gui/toolbar.fluid +++ b/scripts/gui/toolbar.fluid @@ -39,8 +39,6 @@ The resulting object consists of the following accessible fields: require 'translate' include 'vector' - if (not mFont) then mFont = mod.load('font') end - local lColours = { hover = 'rgb(0,0,0,32)', selected = 'rgb(255,255,255,128)', @@ -172,7 +170,7 @@ gui.toolbar = function(HostVP, Options) if self.vg then self.vg.free() end if (self._groupCount > 0) then - self._groupClip = self.viewport.scene.new('VectorClip', { name='GroupMask', units='BoundingBox' }) + self._groupClip = self.viewport.scene.new('VectorClip', { name='GroupMask', units='UserSpace' }) end self.vg = self.viewport.new('VectorGroup', { name='ItemGroup' }) @@ -239,8 +237,8 @@ gui.toolbar = function(HostVP, Options) }) if self._groupClip then - item.clip = self._groupClip.new('VectorRectangle', { - name = 'groupclip', x = self.viewport.x + x, y = self.viewport.y + y, roundX = 4, roundY = 4, width = 1, height = 1 + item.clip = self._groupClip.viewport.new('VectorRectangle', { + name = 'groupclip', x = x, y = y, roundX = 4, roundY = 4, width = 1, height = 1 }) end elseif (item.type == TI_ICON) then @@ -261,15 +259,16 @@ gui.toolbar = function(HostVP, Options) item.vectorText = self.vg.new('VectorText', { x = x + self._cellMargin, - face = 'Open Sans', + face = 'Noto Sans', fontSize = self._iconSize * 0.75, weight = 500, fill = 'url(#' .. gname .. ')', - string = item.displayName + string = item.displayName }) - item.width = mFont.StringWidth(item.vectorText.font, item.displayName, -1) + (self._cellMargin * 2) - item.vectorText.y = (self.viewport.height * 0.5) + (item.vectorText.font.height * 0.5) + local err, bx, by, bw, bh = item.vectorText.mtGetBoundary(0) + item.width = bw + (self._cellMargin * 2) + item.vectorText.y = (self.viewport.height * 0.5) + (item.vectorText.displaySize * 0.5) if self._disabled or item.disabled then item.vectorText.opacity = 0.5 @@ -478,9 +477,9 @@ gui.toolbar = function(HostVP, Options) local function inputFeedback(Viewport, Events) -- Internal input handler local ev = Events while ev do - if (ev.type == JET_ENTERED_SURFACE) then + if (ev.type == JET_CROSSED_IN) then - elseif (ev.type == JET_LEFT_SURFACE) then + elseif (ev.type == JET_CROSSED_OUT) then resetTipTimer() if self._current then hoverUpdate(nil) @@ -622,7 +621,7 @@ gui.toolbar = function(HostVP, Options) end end) - self.viewport.mtSubscribeInput(bit.bor(JTYPE_BUTTON, JTYPE_MOVEMENT, JTYPE_FEEDBACK), inputFeedback) + self.viewport.mtSubscribeInput(bit.bor(JTYPE_BUTTON, JTYPE_MOVEMENT, JTYPE_CROSSING), inputFeedback) local fill = 'rgb(0,0,0,128)' if (Options.theme != 'light') then diff --git a/scripts/gui/tooltip.fluid b/scripts/gui/tooltip.fluid index ac48507bc..591ce46f6 100644 --- a/scripts/gui/tooltip.fluid +++ b/scripts/gui/tooltip.fluid @@ -16,7 +16,7 @@ is possible by calling the free method. if (gui == nil) then gui = { } end -local FONT_FACE = 'Open Sans' +local FONT_FACE = 'Noto Sans' local FONT_SIZE = 11 gui.tooltip = function(Options) @@ -63,7 +63,7 @@ gui.tooltip = function(Options) self.surface.height = (FONT_SIZE*1.5) + self.text.fontSize self.surface.y = ptr.y - self.surface.height - self.text.y = math.floor((self.viewport.height * 0.5) + (self.text.font.height * 0.5)) + self.text.y = math.floor((self.viewport.height * 0.5) + (self.text.displaySize * 0.5)) -- This code segment attaches to the surface and terminates it when the pointer is moved by the user. diff --git a/scripts/gui/window.fluid b/scripts/gui/window.fluid index 1b5863a4c..82e76a3a2 100644 --- a/scripts/gui/window.fluid +++ b/scripts/gui/window.fluid @@ -44,8 +44,10 @@ Valid options to use when creating the window are as follows: Returns the size of the window as { x, y, width, height } :hide() Hide the window and move the user focus to the next active window - :reposition(X, Y, Width, Height) + :resize(X, Y, Width, Height) Alter the window dimensions. Values can be set to nil to leave them unchanged. + :resizeClientArea(Width, Height) + Alter the internal size of the window and adjust the border automatically. Values can be set to nil to leave them unchanged. :minimise() Manually minimise the window. :maximise() @@ -186,18 +188,23 @@ gui.window = function(Options) end end - -- Changes the size of the position of the window in relation to its parent. + -- Changes the size of the position of the window in relation to its parent. All dimensions refer to the + -- border of the window. self.resize = function(self, X, Y, Width, Height) - if not X then X = self.surface.x end - if not Y then Y = self.surface.y end if not Width then Width = self.surface.width end if not Height then Height = self.surface.height end if hosted(self) then - self.surface.acRedimension(X + self.client.left, Y + self.client.top, 0, Width - self.client.left - self.client.right, Height - self.client.top - self.client.bottom, 0) + if not X then X = self.surface.x end + if not Y then Y = self.surface.y end + self.surface.acRedimension(X + self.client.left, Y + self.client.top, 0, + Width - self.client.left - self.client.right, + Height - self.client.top - self.client.bottom, 0) else if (X) or (Y) then + if not X then X = self.surface.x end + if not Y then Y = self.surface.y end self.surface.acRedimension(X, Y, 0, Width, Height, 0) else self.surface.acResize(Width, Height, 0) @@ -205,6 +212,17 @@ gui.window = function(Options) end end + -- Define window sizing limits. + + self.sizeHints = function(self, MinWidth, MinHeight, MaxWidth, MaxHeight, EnforceAspect) + if self.surface.display.mtSizeHints(MinWidth, MinHeight, MaxWidth, MaxHeight, EnforceAspect) != ERR_Okay then + self.surface.maxWidth = MaxWidth + self.surface.minWidth = MinWidth + self.surface.maxHeight = MaxHeight + self.surface.minHeight = MinHeight + end + end + -- Smart limits are used to prevent the window from moving completely outside of the visible display area. self.applySmartLimits = function(self) @@ -224,7 +242,7 @@ gui.window = function(Options) self.minimise = function(self) if (self.MinimiseEnabled) then - if (self.events.minimise) then + if self.events and self.events.minimise then self.events.minimise(self) end end @@ -242,7 +260,7 @@ gui.window = function(Options) return end - if (self.events.maximise) then + if self.events.maximise then self.events.maximise(self) end @@ -325,7 +343,7 @@ gui.window = function(Options) self.surface.acFocus() end - if self.events.show then self.events.show(self) end + if self.events and self.events.show then self.events.show(self) end end self.hide = function(self) @@ -360,7 +378,7 @@ gui.window = function(Options) -- If there are no other windows in our container - it's highly likely that we're in a hosted environment. --]] - if self.events.hide then self.events.hide(self) end + if self.events and self.events.hide then self.events.hide(self) end end self.setTitle = function(self, Title) @@ -534,11 +552,11 @@ gui.window = function(Options) self.viewport.mtSubscribeFeedback(bit.bor(FM_HAS_FOCUS, FM_CHILD_HAS_FOCUS, FM_LOST_FOCUS), function(Viewport, Event) if (Event == FM_LOST_FOCUS) then - if self.events.lostFocus then self.events.lostFocus(self) end + if self.events and self.events.lostFocus then self.events.lostFocus(self) end else if self.disabled then else - if self.events.focus then self.events.focus(self) end + if self.events and self.events.focus then self.events.focus(self) end end end @@ -548,7 +566,7 @@ gui.window = function(Options) mGfx.windowHook(self.surface.id, WH_CLOSE, function() if not self.closeEnabled then return end - if self.events.close then + if self.events and self.events.close then local result = self.events.close(self) if result != nil then -- If client returns something, the window stays open msg('Client requested that the window stay open.') @@ -563,7 +581,7 @@ gui.window = function(Options) Surface.acShow() end - if self.events.focus then self.events.focus(self) end + if self.events and self.events.focus then self.events.focus(self) end end, self) self.surface.subscribe('lostfocus', function(Surface, Args, self) diff --git a/scripts/vfx.fluid b/scripts/vfx.fluid index dde05ea4b..c70f5c117 100644 --- a/scripts/vfx.fluid +++ b/scripts/vfx.fluid @@ -8,11 +8,111 @@ if (vfx == nil) then } end +vfx.wipes = { shutter = { }, simple = { }, radial = { }, shape = { }, clock = { }, spiral = { }, pixelate = { } } + +---------------------------------------------------------------------------------------------------------------------- + +vfx.dist = function(X1, Y1, X2, Y2) + local a = math.abs(X2 - X1) + local b = math.abs(Y2 - Y1) + if (a > b) then + local t = a + a = b + b = t + end + return b + 0.428 * a * a / b +end + +vfx.config_circle = function(State, Options) + State.cx = 0.5 * State.v_width + if (type(Options.cx) == 'number') then State.cx = Options.cx * State.v_width end + + State.cy = 0.5 * State.v_height + if (type(Options.cy) == 'number') then State.cy = Options.cy * State.v_height end + + local ex, ey + if (State.cx <= 0.5) then ex = State.v_width else ex = 0 end + if (State.cy <= 0.5) then ey = State.v_height else ey = 0 end + + State.max_radius = vfx.dist(State.cx, State.cy, ex, ey) +end + +---------------------------------------------------------------------------------------------------------------------- +-- Use chain() to receive a single callback once all effects in the chain have finished processing. +-- +-- Example: vfx.chain({ vfx.zoomIn(Viewport, 0.5), vfx.fadeIn(Viewport, 0.25) }, Callback) + +vfx.chain = function(Effects, CallbackOnCompletion) + local state = { effects = Effects } + + state.counter = #Effects + for _, effect in ipairs(Effects) do + effect.callback = function() + state.counter = state.counter - 1 + if (state.counter == 0) and CallbackOnCompletion then + CallbackOnCompletion(state) + end + end + end + + return state +end + +---------------------------------------------------------------------------------------------------------------------- +-- Use 'screen wipe' effects to display or hide a viewport. The Viewport's Mask is utilised to achieve this. A +-- wipe-out can be achieved by setting inverse=true in the Options. +-- +-- Seconds: Specifies the maximum number of seconds for the effect to complete. +-- Delay: Delays the initial start of the effect, measured in seconds. +-- Style: 'shutter', 'simple', 'radial', 'spiral', 'clock', 'shape', 'pixelate' + +vfx.wipe = function(Viewport, Seconds, Delay, Style, Options) + if not Options then Options = { } end + if not Style then Style = 'shutter' end + + local state = { + name = 'wipe', viewport = Viewport, seconds = nz(Seconds, 1.0), delay = nz(Delay, 0), + v_width = Viewport.width, v_height = Viewport.height, + animate = vfx.wipes[Style].animate, callback = CallbackOnCompletion, + path_cmd = struct.new('PathCommand') + } + + state.clip = Viewport.scene.new('VectorClip', { units='BoundingBox' }) + state.clip.viewport.viewWidth = Viewport.width -- Change from the default bounding-box of (0 0 1 1) + state.clip.viewport.viewHeight = Viewport.height + Viewport.mask = state.clip + + state.free = function(State) + State.viewport.mask = nil + State.clip.free() + State.clip = nil + collectgarbage() + State.viewport.acDraw() + end + + if vfx.wipes[Style].init then vfx.wipes[Style].init(state, Options) end + + vfx.initTimer(state, Options) + return state +end + +---------------------------------------------------------------------------------------------------------------------- +-- Move the viewport to its indicated (x,y) position within the allotted time. By default the move will commence from +-- an out-of-bounds position on the left. The client can override this with a custom FromX, FromY position. + +vfx.moveIn = function(Viewport, Seconds, Delay, FromX, FromY) + +end + +vfx.moveOut = function(Viewport, Seconds, Delay, FromX, FromY) + +end + ---------------------------------------------------------------------------------------------------------------------- --- Enables fading-in of a viewport. +-- Fades a viewport into the display by adjusting the opacity level. -- --- Seconds: Specifies the maximum number of seconds for the fade effect to complete. --- Delay: Delays the initial start of the icon fade effect, measured in seconds. +-- Seconds: Specifies the maximum number of seconds for the effect to complete. +-- Delay: Delays the initial start of the effect, measured in seconds. vfx.fadeIn = function(Viewport, Seconds, Delay) local state = { name = 'fadeIn', seconds = nz(Seconds, 1.0), delay = nz(Delay, 0), callback = CallbackOnCompletion } @@ -132,18 +232,6 @@ vfx.zoomOut = function(Viewport, Seconds, Delay, CallbackOnCompletion) return state end ----------------------------------------------------------------------------------------------------------------------- --- Move the viewport to its indicated (x,y) position within the allotted time. By default the move will commence from --- an out-of-bounds position on the left. The client can override this with a custom FromX, FromY position. - -vfx.moveIn = function(Viewport, Seconds, Delay, FromX, FromY) - -end - -vfx.moveOut = function(Viewport, Seconds, Delay, FromX, FromY) - -end - ---------------------------------------------------------------------------------------------------------------------- -- 'Shake' a vector by applying an alternating rotation around its center. Intensity is between 0.1 and 2.0 and -- affects the number of shakes and maximum angle of rotation. @@ -241,22 +329,267 @@ vfx.rotate = function(Viewport, Seconds, Delay, CallbackOnCompletion) end ---------------------------------------------------------------------------------------------------------------------- --- Use chain() to receive a single callback once all effects in the chain have finished processing. --- --- Example: vfx.chain({ vfx.zoomIn(Viewport, 0.5), vfx.fadeIn(Viewport, 0.25) }, Callback) -vfx.chain = function(Effects, CallbackOnCompletion) - local state = { effects = Effects } +vfx.wipes.simple.init = function(State, Options) + if (Options.rotate) then + local err + err, State.matrix = State.clip_path.mtNewMatrix() + mVector.Rotate(State.matrix, Options.rotate, State.v_width * 0.5, State.v_height * 0.5) + end +end - state.counter = #Effects - for _, effect in ipairs(Effects) do - effect.callback = function() - state.counter = state.counter - 1 - if (state.counter == 0) and CallbackOnCompletion then - CallbackOnCompletion(state) - end +vfx.wipes.simple.animate = function(State, Options, Progress) + -- Use the diagonal to determine the bar width because the client might use rotation. + local max_width = vfx.dist(0, 0, State.v_width, State.v_height) + + if not State.clip_path then State.clip_path = State.clip.viewport.new('VectorPath', { }) end + + State.clip_path.acClear() + + local pc = State.path_cmd + pc.type = PE_Move + pc.x = -((max_width - State.v_width) * 0.5) + pc.y = 0 + State.clip_path.mtAddCommand(pc) + + pc.type = PE_Line + pc.x = max_width + State.clip_path.mtAddCommand(pc) + + pc.y = Progress * State.v_height + State.clip_path.mtAddCommand(pc) + + pc.x = -((max_width - State.v_width) * 0.5) + State.clip_path.mtAddCommand(pc) + + pc.type = PE_Close + State.clip_path.mtAddCommand(pc) +end + +---------------------------------------------------------------------------------------------------------------------- + +vfx.wipes.clock.animate = function(State, Options, Progress) + local radius = vfx.dist(0, 0, State.v_width+2, State.v_height+2) * 0.5 + + if not State.clip_path then State.clip_path = State.clip.viewport.new('VectorPath', { }) end + + State.clip_path.acClear() + local bar_pos = 0 + local height = Progress * State.v_height + + local angle = Progress * 360 + local rad = math.rad(angle) + local cx = State.v_width * 0.5 + local cy = State.v_height * 0.5 + + local x = (radius * math.sin(rad)) + cx + local y = (-radius * math.cos(rad)) + cy + + local top_right_pt = 90 - math.deg(math.atan2((State.v_height*0.5), cx)) + local bottom_right_pt = 180 - top_right_pt + local bottom_left_pt = 180 + top_right_pt + local top_left_pt = 360 - top_right_pt + + local pc = State.path_cmd + + pc.type = PE_Move -- Center + pc.x = State.v_width * 0.5 + pc.y = State.v_height * 0.5 + State.clip_path.mtAddCommand(pc) + + pc.type = PE_Line -- Clock hand + pc.x = State.v_width * 0.5 + pc.y = -1 + State.clip_path.mtAddCommand(pc) + + if (angle > top_right_pt) then -- Fill corners + pc.x = State.v_width + 1 + pc.y = -1 + State.clip_path.mtAddCommand(pc) + end + + if (angle > bottom_right_pt) then + pc.x = State.v_width + 1 + pc.y = State.v_height + 1 + State.clip_path.mtAddCommand(pc) + end + + if (angle > bottom_left_pt) then + pc.x = -1 + pc.y = State.v_height + 1 + State.clip_path.mtAddCommand(pc) + end + + if (angle > top_left_pt) then + pc.x = -1 + pc.y = -1 + State.clip_path.mtAddCommand(pc) + end + + pc.x = x -- The angled point + pc.y = y + State.clip_path.mtAddCommand(pc) + + pc.type = PE_Close + State.clip_path.mtAddCommand(pc) +end + +---------------------------------------------------------------------------------------------------------------------- +-- segments: Total number of radial segments +-- cx: Horizontal position of the effect (scaled) +-- cy: Vertical position of the effect (scaled) + +vfx.wipes.radial.init = function(State, Options) + vfx.config_circle(State, Options) + + State.segments = nz(Options.segments, 10) + if (State.segments < 1) then State.segments = 1 end + if (State.segments > State.max_radius * 0.33) then State.segments = math.floor(State.max_radius * 0.33) end + + State.interval = 1.0 / State.segments + State.stroke_size = State.max_radius / State.segments + + State.ellipses = { } + State.clip.flags = 'ApplyStrokes|ApplyFills' + + State.center = State.clip.viewport.new('VectorEllipse', { + cx = State.cx, cy = State.cy, rx = 0.01, ry = 0.01, visibility = VIS_HIDDEN, fill='rgb(255,255,255)' + }) + + for i=1,State.segments-1 do + local radius = State.stroke_size + ((State.max_radius - State.stroke_size)) * (i / (State.segments-1)) - (State.stroke_size * 0.5) + table.insert(State.ellipses, State.clip.viewport.new('VectorEllipse', { + cx = State.cx, cy = State.cy, rx = radius, ry = radius, fill='none', + stroke = 'rgb(255,255,255)', visibility = VIS_HIDDEN + })) + end +end + +vfx.wipes.radial.animate = function(State, Options, Progress) + local size = (Progress / State.interval) * State.stroke_size + if (size > State.stroke_size + 0.25) then size = State.stroke_size + 0.25 end + State.center.radius = size + State.center.visibility = VIS_VISIBLE + + for i=1,State.segments-1 do + local size = (Progress / (i * State.interval)) * State.stroke_size + if (size > State.stroke_size + 0.25) then size = State.stroke_size + 0.25 end + State.ellipses[i].strokeWidth = size + + if (size < 0.5) then + State.ellipses[i].visibility = VIS_HIDDEN + else + State.ellipses[i].visibility = VIS_VISIBLE end end +end - return state +---------------------------------------------------------------------------------------------------------------------- +-- Spiral effect. Looks its best when the segment count is kept low (1 - 3). +-- cx: Horizontal position of the effect (scaled) +-- cy: Vertical position of the effect (scaled) + +vfx.wipes.spiral.init = function(State, Options) + vfx.config_circle(State, Options) + + State.segments = nz(Options.segments, 2) + if (State.segments < 1) then State.segments = 1 end + if (State.segments > State.max_radius * 0.33) then State.segments = math.floor(State.max_radius * 0.33) end + + State.spiral = State.clip.viewport.new('VectorSpiral', { + cx = State.cx, cy = State.cy, + radius = State.max_radius + (State.max_radius / State.segments), + spacing = State.max_radius / State.segments, + fill = 'rgb(255,255,255)', visibility = VIS_HIDDEN + }) +end + +vfx.wipes.spiral.animate = function(State, Options, Progress) + local radius = (State.max_radius + (State.max_radius / State.segments)) * Progress + if (radius < 0.001) then radius = 0.001 end + State.spiral.radius = radius + State.spiral.visibility = VIS_VISIBLE +end + +---------------------------------------------------------------------------------------------------------------------- + +vfx.wipes.shutter.init = function(State, Options) + if (Options.rotate) then + local err + err, State.matrix = State.clip_path.mtNewMatrix() + mVector.Rotate(State.matrix, Options.rotate, State.v_width * 0.5, State.v_height * 0.5) + end +end + +vfx.wipes.shutter.animate = function(State, Options, Progress) + -- Use the diagonal to determine the bar width because the client might use rotation. + local max_width = vfx.dist(0, 0, State.v_width, State.v_height) + + local segments = nz(Options.segments, 10) + if (segments > max_width * 0.33) then segments = max_width * 0.33 end + + local pc = State.path_cmd + local interval = 1.0 / segments + local bar_height = State.v_height / segments + + if not State.clip_path then State.clip_path = State.clip.viewport.new('VectorPath', { }) end + + State.clip_path.acClear() + for i=0,segments-1 do + local bar_pos = i * bar_height + local height = (Progress / ((i * interval) + interval)) * bar_height + + if (height > bar_height) then height = bar_height end + + pc.type = PE_Move + pc.x = -((max_width - State.v_width) * 0.5) + pc.y = bar_pos + State.clip_path.mtAddCommand(pc) + + pc.type = PE_Line + pc.x = max_width + State.clip_path.mtAddCommand(pc) + + pc.y = bar_pos + height + State.clip_path.mtAddCommand(pc) + + pc.x = -((max_width - State.v_width) * 0.5) + State.clip_path.mtAddCommand(pc) + + pc.type = PE_Close + State.clip_path.mtAddCommand(pc) + end +end + +---------------------------------------------------------------------------------------------------------------------- +-- Generic routine for initialising and processing the effect timer + +vfx.initTimer = function(State, Options) + local err + err, State.timerID = mSys.SubscribeTimer(1 * vfx.fps, function(Subscriber, Elapsed, CurrentTime) + if not State.viewport.exists() then check(ERR_Terminate) end + + if (State.time == nil) then State.time = CurrentTime end + if (State.delay > 0) then + if ((CurrentTime - State.time) >= State.delay * 1000000) then + State.delay = 0 + mSys.UpdateTimer(State.timerID, 1 * vfx.fps) -- Resubscribe to the timer to clear the TotalElapsed counter + State.time = nil + end + else + local value = (CurrentTime - State.time) / (State.seconds * 1000000) + if (value >= 1.0) then + if (State.free != nil) then State:free() end + if State.callback then State.callback(State) end + check(ERR_Terminate) + else + if Options.inverse then + State.animate(State, Options, 1.0 - value) + else + State.animate(State, Options, value) + end + State.viewport.acDraw() + end + end + end) end diff --git a/src/audio/alsa.cpp b/src/audio/alsa.cpp index 06554b61c..b343235e9 100644 --- a/src/audio/alsa.cpp +++ b/src/audio/alsa.cpp @@ -12,7 +12,7 @@ static void free_alsa(extAudio *Self) //******************************************************************************************************************** -static ERROR init_audio(extAudio *Self) +static ERR init_audio(extAudio *Self) { pf::Log log(__FUNCTION__); struct sndSetVolume setvol; @@ -33,7 +33,7 @@ static ERROR init_audio(extAudio *Self) if (Self->Handle) { log.msg("Audio system is already active."); - return ERR_Okay; + return ERR::Okay; } snd_ctl_card_info_alloca(&info); @@ -48,13 +48,13 @@ static ERROR init_audio(extAudio *Self) // Convert english pcm_name to the device number - if (StrMatch("default", pcm_name.c_str()) != ERR_Okay) { + if (StrMatch("default", pcm_name.c_str()) != ERR::Okay) { STRING cardid, cardname; LONG card = -1; if ((snd_card_next(&card) < 0) or (card < 0)) { log.warning("There are no sound cards supported by audio drivers."); - return ERR_NoSupport; + return ERR::NoSupport; } while (card >= 0) { @@ -87,7 +87,7 @@ static ERROR init_audio(extAudio *Self) LONG card = -1; if ((snd_card_next(&card) < 0) or (card < 0)) { log.warning("There are no sound cards supported by audio drivers."); - return ERR_NoSupport; + return ERR::NoSupport; } // Check the number of mixer controls for all cards that support output. We'll choose the card that has the most @@ -156,22 +156,22 @@ static ERROR init_audio(extAudio *Self) if ((err = snd_mixer_open(&Self->MixHandle, 0)) < 0) { log.warning("snd_mixer_open() %s", snd_strerror(err)); - return ERR_Failed; + return ERR::Failed; } if ((err = snd_mixer_attach(Self->MixHandle, pcm_name.c_str())) < 0) { log.warning("snd_mixer_attach() %s", snd_strerror(err)); - return ERR_Failed; + return ERR::Failed; } if ((err = snd_mixer_selem_register(Self->MixHandle, NULL, NULL)) < 0) { log.warning("snd_mixer_selem_register() %s", snd_strerror(err)); - return ERR_Failed; + return ERR::Failed; } if ((err = snd_mixer_load(Self->MixHandle)) < 0) { log.warning("snd_mixer_load() %s", snd_strerror(err)); - return ERR_Failed; + return ERR::Failed; } // Build a list of all available volume controls @@ -184,7 +184,7 @@ static ERROR init_audio(extAudio *Self) if (voltotal < 1) { log.warning("Aborting due to lack of mixers for the sound device."); - return ERR_NoSupport; + return ERR::NoSupport; } std::vector volctl; @@ -259,19 +259,19 @@ static ERROR init_audio(extAudio *Self) stream = SND_PCM_STREAM_PLAYBACK; if ((err = snd_pcm_open(&pcmhandle, pcm_name.c_str(), stream, 0)) < 0) { log.warning("snd_pcm_open(%s) %s", pcm_name.c_str(), snd_strerror(err)); - return ERR_Failed; + return ERR::Failed; } // Set access type, either SND_PCM_ACCESS_RW_INTERLEAVED or SND_PCM_ACCESS_RW_NONINTERLEAVED. if ((err = snd_pcm_hw_params_any(pcmhandle, hwparams)) < 0) { log.warning("Broken configuration for this PCM: no configurations available"); - return ERR_Failed; + return ERR::Failed; } if ((err = snd_pcm_hw_params_set_access(pcmhandle, hwparams, SND_PCM_ACCESS_RW_INTERLEAVED)) < 0) { log.warning("set_access() %d %s", err, snd_strerror(err)); - return ERR_Failed; + return ERR::Failed; } // Set the preferred audio bit format @@ -279,18 +279,18 @@ static ERROR init_audio(extAudio *Self) if (Self->BitDepth IS 32) { if ((err = snd_pcm_hw_params_set_format(pcmhandle, hwparams, SND_PCM_FORMAT_FLOAT_LE)) < 0) { log.warning("set_format(32) %s", snd_strerror(err)); - return ERR_Failed; + return ERR::Failed; } } else if (Self->BitDepth IS 16) { if ((err = snd_pcm_hw_params_set_format(pcmhandle, hwparams, SND_PCM_FORMAT_S16_LE)) < 0) { log.warning("set_format(16) %s", snd_strerror(err)); - return ERR_Failed; + return ERR::Failed; } } else if ((err = snd_pcm_hw_params_set_format(pcmhandle, hwparams, SND_PCM_FORMAT_U8)) < 0) { log.warning("set_format(8) %s", snd_strerror(err)); - return ERR_Failed; + return ERR::Failed; } // Retrieve the bit rate from alsa @@ -313,7 +313,7 @@ static ERROR init_audio(extAudio *Self) default: log.warning("Hardware uses an unsupported audio format."); - return ERR_Failed; + return ERR::Failed; } log.msg("ALSA bit rate: %d", Self->BitDepth); @@ -324,7 +324,7 @@ static ERROR init_audio(extAudio *Self) dir = 0; if ((err = snd_pcm_hw_params_set_rate_near(pcmhandle, hwparams, (ULONG *)&Self->OutputRate, &dir)) < 0) { log.warning("set_rate_near() %s", snd_strerror(err)); - return ERR_Failed; + return ERR::Failed; } // Set number of channels @@ -332,7 +332,7 @@ static ERROR init_audio(extAudio *Self) ULONG channels = ((Self->Flags & ADF::STEREO) != ADF::NIL) ? 2 : 1; if ((err = snd_pcm_hw_params_set_channels_near(pcmhandle, hwparams, &channels)) < 0) { log.warning("set_channels_near(%d) %s", channels, snd_strerror(err)); - return ERR_Failed; + return ERR::Failed; } if (channels IS 2) Self->Stereo = true; @@ -369,24 +369,24 @@ static ERROR init_audio(extAudio *Self) if ((err = snd_pcm_hw_params_set_period_size_near(pcmhandle, hwparams, &periodsize, 0)) < 0) { log.warning("Period size failure: %s", snd_strerror(err)); - return ERR_Failed; + return ERR::Failed; } if ((err = snd_pcm_hw_params_set_buffer_size_near(pcmhandle, hwparams, &buffersize)) < 0) { log.warning("Buffer size failure: %s", snd_strerror(err)); - return ERR_Failed; + return ERR::Failed; } // ALSA device initialisation if ((err = snd_pcm_hw_params(pcmhandle, hwparams)) < 0) { log.warning("snd_pcm_hw_params() %s", snd_strerror(err)); - return ERR_Failed; + return ERR::Failed; } if ((err = snd_pcm_prepare(pcmhandle)) < 0) { log.warning("snd_pcm_prepare() %s", snd_strerror(err)); - return ERR_Failed; + return ERR::Failed; } // Retrieve ALSA buffer sizes @@ -459,10 +459,10 @@ static ERROR init_audio(extAudio *Self) Self->Handle = pcmhandle; } else { - return log.warning(ERR_AllocMemory); + return log.warning(ERR::AllocMemory); } - return ERR_Okay; + return ERR::Okay; } #endif diff --git a/src/audio/audio.cpp b/src/audio/audio.cpp index 184ef8fa0..268f2a141 100644 --- a/src/audio/audio.cpp +++ b/src/audio/audio.cpp @@ -47,9 +47,9 @@ its low-level mixer capabilities only if your needs are not met by the @Sound cl #include #include -static ERROR CMDInit(OBJECTPTR, struct CoreBase *); -static ERROR CMDExpunge(void); -static ERROR CMDOpen(OBJECTPTR); +static ERR CMDInit(OBJECTPTR, struct CoreBase *); +static ERR CMDExpunge(void); +static ERR CMDOpen(OBJECTPTR); #include "module_def.c" @@ -59,18 +59,18 @@ static OBJECTPTR clAudio = 0; static std::unordered_map glSoundChannels; class extAudio; -ERROR add_audio_class(void); -ERROR add_sound_class(void); +ERR add_audio_class(void); +ERR add_sound_class(void); void free_audio_class(void); void free_sound_class(void); extern "C" void end_of_stream(OBJECTPTR, LONG); static void audio_stopped_event(extAudio &, LONG); -static ERROR set_channel_volume(extAudio *, struct AudioChannel *); +static ERR set_channel_volume(extAudio *, struct AudioChannel *); static void load_config(extAudio *); -static ERROR init_audio(extAudio *); -static ERROR audio_timer(extAudio *, LARGE, LARGE); +static ERR init_audio(extAudio *); +static ERR audio_timer(extAudio *, LARGE, LARGE); #include "audio.h" @@ -99,7 +99,7 @@ static const WORD glAlsaConvert[6] = { //******************************************************************************************************************** -static ERROR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) +static ERR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) { pf::Log log; @@ -111,28 +111,28 @@ static ERROR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) CSTRING errstr; if ((errstr = dsInitDevice(44100))) { log.warning("DirectSound Failed: %s", errstr); - return ERR_NoSupport; + return ERR::NoSupport; } } #elif ALSA_ENABLED // Nothing required for ALSA #else log.warning("No audio support available."); - return ERR_Failed; + return ERR::Failed; #endif - if (add_audio_class() != ERR_Okay) return ERR_AddClass; - if (add_sound_class() != ERR_Okay) return ERR_AddClass; - return ERR_Okay; + if (add_audio_class() != ERR::Okay) return ERR::AddClass; + if (add_sound_class() != ERR::Okay) return ERR::AddClass; + return ERR::Okay; } -static ERROR CMDOpen(OBJECTPTR Module) +static ERR CMDOpen(OBJECTPTR Module) { Module->set(FID_FunctionList, glFunctions); - return ERR_Okay; + return ERR::Okay; } -static ERROR CMDExpunge(void) +static ERR CMDExpunge(void) { for (auto& [id, handle] : glSoundChannels) { // NB: Most Audio objects will be disposed of prior to this module being expunged. @@ -145,7 +145,7 @@ static ERROR CMDExpunge(void) free_audio_class(); free_sound_class(); - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** diff --git a/src/audio/audio.fdl b/src/audio/audio.fdl index 2f90c8740..488bfa512 100644 --- a/src/audio/audio.fdl +++ b/src/audio/audio.fdl @@ -1,6 +1,6 @@ --$FLUID:Include -module({ name="Audio", copyright="Paul Manias © 2002-2023", version=1.0 }, function() +module({ name="Audio", copyright="Paul Manias © 2002-2024", version=1.0 }, function() flags("ADF", { comment="Optional flags for the Audio object." }, "OVER_SAMPLING: Enables oversampling for higher quality audio at the cost of slower mixing.", "FILTER_LOW: Enable a low level of output filtering to minimise distortion.", diff --git a/src/audio/audio.h b/src/audio/audio.h index d004449b0..39a2ab41c 100644 --- a/src/audio/audio.h +++ b/src/audio/audio.h @@ -314,5 +314,5 @@ class extSound : public objSound { struct BufferCommand { CMD CommandID; - ERROR (*Routine)(extAudio *Self, APTR); + ERR (*Routine)(extAudio *Self, APTR); }; diff --git a/src/audio/class_audio.cpp b/src/audio/class_audio.cpp index 6edfbfae0..cf92e7dd3 100644 --- a/src/audio/class_audio.cpp +++ b/src/audio/class_audio.cpp @@ -17,17 +17,17 @@ Support for audio recording is not currently available. *********************************************************************************************************************/ #ifndef ALSA_ENABLED -static ERROR init_audio(extAudio *Self) +static ERR init_audio(extAudio *Self) { Self->BitDepth = 16; Self->Stereo = true; Self->MasterVolume = Self->Volumes[0].Channels[0]; Self->Volumes[0].Flags |= VCF::MONO; - for (LONG i=1; i < (LONG)Self->Volumes[0].Channels.size(); i++) Self->Volumes[0].Channels[i] = -1; + for (LONG i=1; i < std::ssize(Self->Volumes[0].Channels); i++) Self->Volumes[0].Channels[i] = -1; if ((Self->Volumes[0].Flags & VCF::MUTE) != VCF::NIL) Self->Mute = true; else Self->Mute = false; - return ERR_Okay; + return ERR::Okay; } #endif @@ -44,18 +44,18 @@ An inactive audio object can operate in a limited fashion but is without access *********************************************************************************************************************/ -static ERROR AUDIO_Activate(extAudio *Self, APTR Void) +static ERR AUDIO_Activate(extAudio *Self, APTR Void) { pf::Log log; - if (Self->Initialising) return ERR_Okay; + if (Self->Initialising) return ERR::Okay; log.branch(); Self->Initialising = true; - ERROR error; - if ((error = init_audio(Self)) != ERR_Okay) { + ERR error; + if ((error = init_audio(Self)) != ERR::Okay) { Self->Initialising = false; return error; } @@ -80,7 +80,7 @@ static ERROR AUDIO_Activate(extAudio *Self, APTR Void) Self->MixBufferSize = BYTELEN((F2T((mixbitsize * Self->OutputRate) * (MIX_INTERVAL * 1.5)) + 15) & (~15)); Self->MixElements = SAMPLE(Self->MixBufferSize / mixbitsize); - if (!AllocMemory(Self->MixBufferSize, MEM::DATA, &Self->MixBuffer)) { + if (AllocMemory(Self->MixBufferSize, MEM::DATA, &Self->MixBuffer) IS ERR::Okay) { // Pick the correct mixing routines if ((Self->Flags & ADF::OVER_SAMPLING) != ADF::NIL) { @@ -104,12 +104,12 @@ static ERROR AUDIO_Activate(extAudio *Self, APTR Void) if (auto strerr = sndCreateBuffer(Self, &wave, Self->MixBufferSize, 0x7fffffff, (PlatformData *)Self->PlatformData, TRUE)) { log.warning(strerr); Self->Initialising = false; - return ERR_Failed; + return ERR::Failed; } if (sndPlay((PlatformData *)Self->PlatformData, TRUE, 0)) { Self->Initialising = false; - return log.warning(ERR_Failed); + return log.warning(ERR::Failed); } #endif @@ -117,11 +117,11 @@ static ERROR AUDIO_Activate(extAudio *Self, APTR Void) // is executed by the client. Self->Initialising = false; - return ERR_Okay; + return ERR::Okay; } else { Self->Initialising = false; - return log.warning(ERR_AllocMemory); + return log.warning(ERR::AllocMemory); } } @@ -174,22 +174,22 @@ AllocMemory: Failed to allocate enough memory to hold the sample data. *********************************************************************************************************************/ -ERROR AUDIO_AddSample(extAudio *Self, struct sndAddSample *Args) +ERR AUDIO_AddSample(extAudio *Self, struct sndAddSample *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); log.branch("Data: %p, Length: %d", Args->Data, Args->DataSize); // Find an unused sample block. If there is none, increase the size of the sample management area. LONG idx; - for (idx=1; idx < (LONG)Self->Samples.size(); idx++) { + for (idx=1; idx < std::ssize(Self->Samples); idx++) { if (!Self->Samples[idx].Data) break; } - if (idx >= (LONG)Self->Samples.size()) Self->Samples.resize(Self->Samples.size()+10); + if (idx >= std::ssize(Self->Samples)) Self->Samples.resize(std::ssize(Self->Samples)+10); auto shift = sample_shift(Args->SampleFormat); @@ -219,13 +219,13 @@ ERROR AUDIO_AddSample(extAudio *Self, struct sndAddSample *Args) if ((sample.SampleType IS SFM::NIL) or (Args->DataSize <= 0) or (!Args->Data)) { sample.Data = NULL; } - else if (!AllocMemory(Args->DataSize, MEM::DATA|MEM::NO_CLEAR, &sample.Data)) { + else if (AllocMemory(Args->DataSize, MEM::DATA|MEM::NO_CLEAR, &sample.Data) IS ERR::Okay) { CopyMemory(Args->Data, sample.Data, Args->DataSize); } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); Args->Result = idx; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -287,23 +287,23 @@ AllocMemory: Failed to allocate the stream buffer. static const LONG MAX_STREAM_BUFFER = 16 * 1024; // Max stream buffer length in bytes -static ERROR AUDIO_AddStream(extAudio *Self, struct sndAddStream *Args) +static ERR AUDIO_AddStream(extAudio *Self, struct sndAddStream *Args) { pf::Log log; - if ((!Args) or (Args->SampleFormat IS SFM::NIL)) return log.warning(ERR_NullArgs); - if (!Args->Callback.Type) return log.warning(ERR_NullArgs); + if ((!Args) or (Args->SampleFormat IS SFM::NIL)) return log.warning(ERR::NullArgs); + if (!Args->Callback.Type) return log.warning(ERR::NullArgs); log.branch("Length: %d", Args->SampleLength); // Find an unused sample block. If there is none, increase the size of the sample management area. LONG idx; - for (idx=1; idx < (LONG)Self->Samples.size(); idx++) { + for (idx=1; idx < std::ssize(Self->Samples); idx++) { if (!Self->Samples[idx].Data) break; } - if (idx >= (LONG)Self->Samples.size()) Self->Samples.resize(Self->Samples.size()+10); + if (idx >= std::ssize(Self->Samples)) Self->Samples.resize(std::ssize(Self->Samples)+10); auto shift = sample_shift(Args->SampleFormat); @@ -343,12 +343,12 @@ static ERROR AUDIO_AddStream(extAudio *Self, struct sndAddStream *Args) if (sample.Loop2Start IS sample.Loop2End) sample.Loop2Type = LTYPE::NIL; } - if (AllocMemory(buffer_len, MEM::DATA|MEM::NO_CLEAR, &sample.Data) != ERR_Okay) { - return ERR_AllocMemory; + if (AllocMemory(buffer_len, MEM::DATA|MEM::NO_CLEAR, &sample.Data) != ERR::Okay) { + return ERR::AllocMemory; } Args->Result = idx; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -372,18 +372,18 @@ NoSupport: PC speaker support is not available. *********************************************************************************************************************/ -static ERROR AUDIO_Beep(extAudio *Self, struct sndBeep *Args) +static ERR AUDIO_Beep(extAudio *Self, struct sndBeep *Args) { - if (!Args) return ERR_NullArgs; + if (!Args) return ERR::NullArgs; #ifdef __linux__ LONG console; if ((console = GetResource(RES::CONSOLE_FD)) != -1) { ioctl(console, KDMKTONE, ((1193190 / Args->Pitch) & 0xffff) | ((ULONG)Args->Duration << 16)); - return ERR_Okay; + return ERR::Okay; } #endif - return ERR_NoSupport; + return ERR::NoSupport; } /********************************************************************************************************************* @@ -406,19 +406,19 @@ Args *********************************************************************************************************************/ -static ERROR AUDIO_CloseChannels(extAudio *Self, struct sndCloseChannels *Args) +static ERR AUDIO_CloseChannels(extAudio *Self, struct sndCloseChannels *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); log.branch("Handle: $%.8x", Args->Handle); LONG index = Args->Handle>>16; - if ((index < 0) or (index >= (LONG)Self->Sets.size())) log.warning(ERR_Args); + if ((index < 0) or (index >= std::ssize(Self->Sets))) log.warning(ERR::Args); Self->Sets[index].clear(); // We can't erase because that would mess up other channel handles. - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -430,7 +430,7 @@ resources back to the host system. The audio object will remain in a suspended -END- *********************************************************************************************************************/ -static ERROR AUDIO_Deactivate(extAudio *Self, APTR Void) +static ERR AUDIO_Deactivate(extAudio *Self, APTR Void) { pf::Log log; @@ -438,7 +438,7 @@ static ERROR AUDIO_Deactivate(extAudio *Self, APTR Void) if (Self->Initialising) { log.msg("Audio is still in the process of initialisation."); - return ERR_Okay; + return ERR::Okay; } acClear(Self); @@ -449,12 +449,12 @@ static ERROR AUDIO_Deactivate(extAudio *Self, APTR Void) //if (Self->Handle) { snd_pcm_close(Self->Handle); Self->Handle = 0; } #endif - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR AUDIO_Free(extAudio *Self, APTR Void) +static ERR AUDIO_Free(extAudio *Self, APTR Void) { if ((Self->Flags & ADF::AUTO_SAVE) != ADF::NIL) Self->saveSettings(); @@ -476,12 +476,12 @@ static ERROR AUDIO_Free(extAudio *Self, APTR Void) Self->~extAudio(); - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR AUDIO_Init(extAudio *Self, APTR Void) +static ERR AUDIO_Init(extAudio *Self, APTR Void) { pf::Log log; @@ -489,12 +489,12 @@ static ERROR AUDIO_Init(extAudio *Self, APTR Void) Self->OutputRate = 44100; // Mix rate is forced for direct sound #endif - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR AUDIO_NewObject(extAudio *Self, APTR Void) +static ERR AUDIO_NewObject(extAudio *Self, APTR Void) { pf::Log log; @@ -511,7 +511,7 @@ static ERROR AUDIO_NewObject(extAudio *Self, APTR Void) Self->MaxChannels = 8; const SystemState *state = GetSystemState(); - if ((!StrMatch(state->Platform, "Native")) or (!StrMatch(state->Platform, "Linux"))) { + if ((StrMatch(state->Platform, "Native") IS ERR::Okay) or (StrMatch(state->Platform, "Linux") IS ERR::Okay)) { Self->Flags |= ADF::SYSTEM_WIDE; } @@ -520,20 +520,20 @@ static ERROR AUDIO_NewObject(extAudio *Self, APTR Void) #ifdef __linux__ Self->Volumes.resize(2); Self->Volumes[0].Name = "Master"; - for (LONG i=0; i < (LONG)Self->Volumes[0].Channels.size(); i++) Self->Volumes[0].Channels[i] = 1.0; + for (LONG i=0; i < std::ssize(Self->Volumes[0].Channels); i++) Self->Volumes[0].Channels[i] = 1.0; Self->Volumes[1].Name = "PCM"; - for (LONG i=0; i < (LONG)Self->Volumes[1].Channels.size(); i++) Self->Volumes[1].Channels[i] = 1.0; + for (LONG i=0; i < std::ssize(Self->Volumes[1].Channels); i++) Self->Volumes[1].Channels[i] = 1.0; #else Self->Volumes.resize(1); Self->Volumes[0].Name = "Master"; Self->Volumes[0].Channels[0] = 1.0; - for (LONG i=1; i < (LONG)Self->Volumes[0].Channels.size(); i++) Self->Volumes[0].Channels[i] = -1; + for (LONG i=1; i < std::ssize(Self->Volumes[0].Channels); i++) Self->Volumes[0].Channels[i] = -1; #endif load_config(Self); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -563,22 +563,22 @@ AllocMemory: Memory for the audio channels could not be allocated. *********************************************************************************************************************/ -static ERROR AUDIO_OpenChannels(extAudio *Self, struct sndOpenChannels *Args) +static ERR AUDIO_OpenChannels(extAudio *Self, struct sndOpenChannels *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); log.branch("Total: %d", Args->Total); Args->Result = 0; if ((Args->Total < 0) or (Args->Total > 64)) { - return log.warning(ERR_OutOfRange); + return log.warning(ERR::OutOfRange); } // Bear in mind that the +1 is for channel set 0 being a dummy entry. - LONG index = Self->Sets.size() + 1; + LONG index = std::ssize(Self->Sets) + 1; Self->Sets.resize(index+1); Self->Sets[index].Channel.resize(Args->Total); @@ -591,7 +591,7 @@ static ERROR AUDIO_OpenChannels(extAudio *Self, struct sndOpenChannels *Args) Self->Sets[index].Commands.reserve(32); Args->Result = index<<16; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -617,19 +617,19 @@ OutOfRange: The provided sample handle is not within the valid range. *********************************************************************************************************************/ -static ERROR AUDIO_RemoveSample(extAudio *Self, struct sndRemoveSample *Args) +static ERR AUDIO_RemoveSample(extAudio *Self, struct sndRemoveSample *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); log.branch("Sample: %d", Args->Handle); - if ((Args->Handle < 1) or (Args->Handle >= (LONG)Self->Samples.size())) return log.warning(ERR_OutOfRange); + if ((Args->Handle < 1) or (Args->Handle >= std::ssize(Self->Samples))) return log.warning(ERR::OutOfRange); Self->Samples[Args->Handle].clear(); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -638,12 +638,12 @@ SaveSettings: Saves the current audio settings. -END- *********************************************************************************************************************/ -static ERROR AUDIO_SaveSettings(extAudio *Self, APTR Void) +static ERR AUDIO_SaveSettings(extAudio *Self, APTR Void) { objFile::create file = { fl::Path("user:config/audio.cfg"), fl::Flags(FL::NEW|FL::WRITE) }; if (file.ok()) return Self->saveToObject(*file); - else return ERR_CreateFile; + else return ERR::CreateFile; } /********************************************************************************************************************* @@ -652,11 +652,11 @@ SaveToObject: Saves the current audio settings to another object. -END- *********************************************************************************************************************/ -static ERROR AUDIO_SaveToObject(extAudio *Self, struct acSaveToObject *Args) +static ERR AUDIO_SaveToObject(extAudio *Self, struct acSaveToObject *Args) { pf::Log log; - if ((!Args) or (!Args->Dest)) return log.warning(ERR_NullArgs); + if ((!Args) or (!Args->Dest)) return log.warning(ERR::NullArgs); objConfig::create config = { }; if (config.ok()) { @@ -675,7 +675,7 @@ static ERROR AUDIO_SaveToObject(extAudio *Self, struct acSaveToObject *Args) else config->write("AUDIO", "Device", "default"); if ((!Self->Volumes.empty()) and ((Self->Flags & ADF::SYSTEM_WIDE) != ADF::NIL)) { - for (unsigned i=0; i < Self->Volumes.size(); i++) { + for (LONG i=0; i < std::ssize(Self->Volumes); i++) { std::ostringstream out; if ((Self->Volumes[i].Flags & VCF::MUTE) != VCF::NIL) out << "1,["; else out << "0,["; @@ -683,7 +683,7 @@ static ERROR AUDIO_SaveToObject(extAudio *Self, struct acSaveToObject *Args) if ((Self->Volumes[i].Flags & VCF::MONO) != VCF::NIL) { out << Self->Volumes[i].Channels[0]; } - else for (LONG c=0; c < (LONG)Self->Volumes[i].Channels.size(); c++) { + else for (LONG c=0; c < std::ssize(Self->Volumes[i].Channels); c++) { if (c > 0) out << ','; out << Self->Volumes[i].Channels[c]; } @@ -746,7 +746,7 @@ static ERROR AUDIO_SaveToObject(extAudio *Self, struct acSaveToObject *Args) config->saveToObject(Args->Dest); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -773,23 +773,23 @@ Failed: Sample is not a stream. *********************************************************************************************************************/ -static ERROR AUDIO_SetSampleLength(extAudio *Self, struct sndSetSampleLength *Args) +static ERR AUDIO_SetSampleLength(extAudio *Self, struct sndSetSampleLength *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); log.msg("Sample: #%d, Length: %" PF64, Args->Sample, Args->Length); - if ((Args->Sample < 0) or (Args->Sample >= (LONG)Self->Samples.size())) return log.warning(ERR_Args); + if ((Args->Sample < 0) or (Args->Sample >= std::ssize(Self->Samples))) return log.warning(ERR::Args); auto &sample = Self->Samples[Args->Sample]; if (sample.Stream) { sample.StreamLength = BYTELEN(Args->Length); - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_Failed); + else return log.warning(ERR::Failed); } /********************************************************************************************************************* @@ -828,7 +828,7 @@ OutOfRange: The Volume or Index is out of the acceptable range. *********************************************************************************************************************/ -static ERROR AUDIO_SetVolume(extAudio *Self, struct sndSetVolume *Args) +static ERR AUDIO_SetVolume(extAudio *Self, struct sndSetVolume *Args) { pf::Log log; @@ -839,28 +839,28 @@ static ERROR AUDIO_SetVolume(extAudio *Self, struct sndSetVolume *Args) snd_mixer_elem_t *elem; long pmin, pmax; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); if (((Args->Volume < 0) or (Args->Volume > 1.0)) and (Args->Volume != -1)) { - return log.warning(ERR_OutOfRange); + return log.warning(ERR::OutOfRange); } - if (Self->Volumes.empty()) return log.warning(ERR_NoSupport); - if (!Self->MixHandle) return ERR_NotInitialised; + if (Self->Volumes.empty()) return log.warning(ERR::NoSupport); + if (!Self->MixHandle) return ERR::NotInitialised; // Determine what mixer we are going to adjust if (Args->Name) { - for (index=0; index < (LONG)Self->Volumes.size(); index++) { + for (index=0; index < std::ssize(Self->Volumes); index++) { if (!StrMatch(Args->Name, Self->Volumes[index].Name.c_str())) break; } - if (index IS (LONG)Self->Volumes.size()) return ERR_Search; + if (index IS (LONG)Self->Volumes.size()) return ERR::Search; } else { index = Args->Index; - if ((index < 0) or (index >= (LONG)Self->Volumes.size())) return ERR_OutOfRange; + if ((index < 0) or (index >= (LONG)Self->Volumes.size())) return ERR::OutOfRange; } - if (!StrMatch("Master", Self->Volumes[index].Name.c_str())) { + if (StrMatch("Master", Self->Volumes[index].Name.c_str()) IS ERR::Okay) { if (Args->Volume != -1) { Self->MasterVolume = Args->Volume; } @@ -884,7 +884,7 @@ static ERROR AUDIO_SetVolume(extAudio *Self, struct sndSetVolume *Args) snd_mixer_selem_id_set_name(sid, Self->Volumes[index].Name.c_str()); if (!(elem = snd_mixer_find_selem(Self->MixHandle, sid))) { log.msg("Mixer \"%s\" not found.", Self->Volumes[index].Name.c_str()); - return ERR_Search; + return ERR::Search; } if (Args->Volume >= 0) { @@ -951,33 +951,33 @@ static ERROR AUDIO_SetVolume(extAudio *Self, struct sndSetVolume *Args) EVENTID evid = GetEventID(EVG::AUDIO, "volume", Self->Volumes[index].Name.c_str()); evVolume event_volume = { evid, Args->Volume, ((Self->Volumes[index].Flags & VCF::MUTE) != VCF::NIL) ? true : false }; BroadcastEvent(&event_volume, sizeof(event_volume)); - return ERR_Okay; + return ERR::Okay; #else LONG index; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); if (((Args->Volume < 0) or (Args->Volume > 1.0)) and (Args->Volume != -1)) { - return log.warning(ERR_OutOfRange); + return log.warning(ERR::OutOfRange); } - if (Self->Volumes.empty()) return log.warning(ERR_NoSupport); + if (Self->Volumes.empty()) return log.warning(ERR::NoSupport); // Determine what mixer we are going to adjust if (Args->Name) { for (index=0; index < (LONG)Self->Volumes.size(); index++) { - if (!StrMatch(Args->Name, Self->Volumes[index].Name.c_str())) break; + if (StrMatch(Args->Name, Self->Volumes[index].Name.c_str()) IS ERR::Okay) break; } - if (index IS (LONG)Self->Volumes.size()) return ERR_Search; + if (index IS (LONG)Self->Volumes.size()) return ERR::Search; } else { index = Args->Index; - if ((index < 0) or (index >= (LONG)Self->Volumes.size())) return ERR_OutOfRange; + if ((index < 0) or (index >= (LONG)Self->Volumes.size())) return ERR::OutOfRange; } - if (!StrMatch("Master", Self->Volumes[index].Name.c_str())) { + if (StrMatch("Master", Self->Volumes[index].Name.c_str()) IS ERR::Okay) { if (Args->Volume != -1) { Self->MasterVolume = Args->Volume; } @@ -1021,7 +1021,7 @@ static ERROR AUDIO_SetVolume(extAudio *Self, struct sndSetVolume *Args) evVolume event_volume = { evid, Args->Volume, ((Self->Volumes[index].Flags & VCF::MUTE) != VCF::NIL) ? true : false }; BroadcastEvent(&event_volume, sizeof(event_volume)); - return ERR_Okay; + return ERR::Okay; #endif } @@ -1036,13 +1036,13 @@ recommended value for CD quality playback. *********************************************************************************************************************/ -static ERROR SET_BitDepth(extAudio *Self, LONG Value) +static ERR SET_BitDepth(extAudio *Self, LONG Value) { if (Value IS 16) Self->BitDepth = 16; else if (Value IS 8) Self->BitDepth = 8; else if (Value IS 24) Self->BitDepth = 24; - else return ERR_Failed; - return ERR_Okay; + else return ERR::Failed; + return ERR::Okay; } /********************************************************************************************************************* @@ -1058,13 +1058,13 @@ The default device can always be referenced with a name of `default`. *********************************************************************************************************************/ -static ERROR GET_Device(extAudio *Self, CSTRING *Value) +static ERR GET_Device(extAudio *Self, CSTRING *Value) { *Value = Self->Device.c_str(); - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_Device(extAudio *Self, CSTRING Value) +static ERR SET_Device(extAudio *Self, CSTRING Value) { if ((!Value) or (!*Value)) Self->Device = "default"; else { @@ -1072,7 +1072,7 @@ static ERROR SET_Device(extAudio *Self, CSTRING Value) std::transform(Self->Device.begin(), Self->Device.end(), Self->Device.begin(), ::tolower); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1104,13 +1104,13 @@ a value between 0 and 1.0. *********************************************************************************************************************/ -static ERROR GET_MasterVolume(extAudio *Self, DOUBLE *Value) +static ERR GET_MasterVolume(extAudio *Self, DOUBLE *Value) { *Value = Self->MasterVolume; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_MasterVolume(extAudio *Self, DOUBLE Value) +static ERR SET_MasterVolume(extAudio *Self, DOUBLE Value) { if (Value < 0) Value = 0; else if (Value > 1.0) Value = 1.0; @@ -1134,10 +1134,10 @@ in seconds and will differ between platforms and user configurations. *********************************************************************************************************************/ -static ERROR GET_MixerLag(extAudio *Self, DOUBLE *Value) +static ERR GET_MixerLag(extAudio *Self, DOUBLE *Value) { *Value = Self->MixerLag(); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1150,19 +1150,19 @@ field to FALSE. Muting does not disable the audio system, which is achieved by *********************************************************************************************************************/ -static ERROR GET_Mute(extAudio *Self, LONG *Value) +static ERR GET_Mute(extAudio *Self, LONG *Value) { *Value = FALSE; - for (LONG i=0; i < (LONG)Self->Volumes.size(); i++) { - if (!StrMatch("Master", Self->Volumes[i].Name.c_str())) { + for (LONG i=0; i < std::ssize(Self->Volumes); i++) { + if (StrMatch("Master", Self->Volumes[i].Name.c_str()) IS ERR::Okay) { if ((Self->Volumes[i].Flags & VCF::MUTE) != VCF::NIL) *Value = TRUE; break; } } - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_Mute(extAudio *Self, LONG Value) +static ERR SET_Mute(extAudio *Self, LONG Value) { struct sndSetVolume setvol = { .Index = 0, @@ -1186,12 +1186,12 @@ The OutputRate can only be set prior to initialisation, further attempts to set *********************************************************************************************************************/ -static ERROR SET_OutputRate(extAudio *Self, LONG Value) +static ERR SET_OutputRate(extAudio *Self, LONG Value) { - if (Value < 0) return ERR_OutOfRange; + if (Value < 0) return ERR::OutOfRange; else if (Value > 44100) Self->OutputRate = 44100; else Self->OutputRate = Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1207,12 +1207,12 @@ The minimum period size is 1K and maximum 16K. *********************************************************************************************************************/ -static ERROR SET_Periods(extAudio *Self, LONG Value) +static ERR SET_Periods(extAudio *Self, LONG Value) { Self->Periods = Value; if (Self->Periods < 2) Self->Periods = 2; else if (Self->Periods > 16) Self->Periods = 16; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1224,12 +1224,12 @@ Refer to the #Periods field for further information. *********************************************************************************************************************/ -static ERROR SET_PeriodSize(extAudio *Self, LONG Value) +static ERR SET_PeriodSize(extAudio *Self, LONG Value) { Self->PeriodSize = Value; if (Self->PeriodSize < 1024) Self->PeriodSize = 1024; else if (Self->PeriodSize > 16384) Self->PeriodSize = 16384; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1246,18 +1246,18 @@ of low quality. *********************************************************************************************************************/ -static ERROR SET_Quality(extAudio *Self, LONG Value) +static ERR SET_Quality(extAudio *Self, LONG Value) { Self->Quality = Value; Self->Flags &= ~(ADF::FILTER_LOW|ADF::FILTER_HIGH|ADF::OVER_SAMPLING); - if (Self->Quality < 10) return ERR_Okay; + if (Self->Quality < 10) return ERR::Okay; else if (Self->Quality < 33) Self->Flags |= ADF::FILTER_LOW; else if (Self->Quality < 66) Self->Flags |= ADF::FILTER_HIGH; else Self->Flags |= ADF::OVER_SAMPLING|ADF::FILTER_HIGH; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1269,18 +1269,18 @@ Stereo: Set to TRUE for stereo output and FALSE for mono output. *********************************************************************************************************************/ -static ERROR GET_Stereo(extAudio *Self, LONG *Value) +static ERR GET_Stereo(extAudio *Self, LONG *Value) { if ((Self->Flags & ADF::STEREO) != ADF::NIL) *Value = TRUE; else *Value = FALSE; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_Stereo(extAudio *Self, LONG Value) +static ERR SET_Stereo(extAudio *Self, LONG Value) { if (Value IS TRUE) Self->Flags |= ADF::STEREO; else Self->Flags &= ~ADF::STEREO; - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -1300,15 +1300,14 @@ static void load_config(extAudio *Self) config->read("AUDIO", "BitDepth", &Self->BitDepth); LONG value; - if (!config->read("AUDIO", "Periods", &value)) SET_Periods(Self, value); - if (!config->read("AUDIO", "PeriodSize", &value)) SET_PeriodSize(Self, value); - - if (config->read("AUDIO", "Device", Self->Device)) Self->Device = "default"; + if (config->read("AUDIO", "Periods", &value) IS ERR::Okay) SET_Periods(Self, value); + if (config->read("AUDIO", "PeriodSize", &value) IS ERR::Okay) SET_PeriodSize(Self, value); + if (config->read("AUDIO", "Device", Self->Device) != ERR::Okay) Self->Device = "default"; std::string str; Self->Flags |= ADF::STEREO; - if (!config->read("AUDIO", "Stereo", str)) { - if (!StrMatch("FALSE", str.c_str())) Self->Flags &= ~ADF::STEREO; + if (config->read("AUDIO", "Stereo", str) IS ERR::Okay) { + if (StrMatch("FALSE", str.c_str()) IS ERR::Okay) Self->Flags &= ~ADF::STEREO; } if ((Self->BitDepth != 8) and (Self->BitDepth != 16) and (Self->BitDepth != 24)) Self->BitDepth = 16; @@ -1317,9 +1316,9 @@ static void load_config(extAudio *Self) // Find the mixer section, then load the mixer information ConfigGroups *groups; - if (!config->getPtr(FID_Data, &groups)) { + if (config->getPtr(FID_Data, &groups) IS ERR::Okay) { for (auto& [group, keys] : groups[0]) { - if (!StrMatch("MIXER", group.c_str())) { + if (StrMatch("MIXER", group.c_str()) IS ERR::Okay) { Self->Volumes.clear(); Self->Volumes.resize(keys.size()); @@ -1379,7 +1378,7 @@ static const FieldArray clAudioFields[] = { //******************************************************************************************************************** -ERROR add_audio_class(void) +ERR add_audio_class(void) { clAudio = objMetaClass::create::global( fl::BaseClassID(ID_AUDIO), @@ -1392,7 +1391,7 @@ ERROR add_audio_class(void) fl::Size(sizeof(extAudio)), fl::Path(MOD_PATH)); - return clAudio ? ERR_Okay : ERR_AddClass; + return clAudio ? ERR::Okay : ERR::AddClass; } void free_audio_class(void) diff --git a/src/audio/class_sound.cpp b/src/audio/class_sound.cpp index 29dff8840..9113c3279 100644 --- a/src/audio/class_sound.cpp +++ b/src/audio/class_sound.cpp @@ -50,9 +50,9 @@ individual samples with more immediacy. #define SIZE_RIFF_CHUNK 12 -static ERROR SOUND_GET_Active(extSound *, LONG *); +static ERR SOUND_GET_Active(extSound *, LONG *); -static ERROR SOUND_SET_Note(extSound *, CSTRING); +static ERR SOUND_SET_Note(extSound *, CSTRING); static const std::array glScale = { 1.0, // C @@ -71,9 +71,9 @@ static const std::array glScale = { static OBJECTPTR clSound = NULL; -static ERROR find_chunk(extSound *, objFile *, CSTRING); +static ERR find_chunk(extSound *, objFile *, CSTRING); #ifdef USE_WIN32_PLAYBACK -static ERROR win32_audio_stream(extSound *, LARGE, LARGE); +static ERR win32_audio_stream(extSound *, LARGE, LARGE); #endif //******************************************************************************************************************** @@ -81,16 +81,16 @@ static ERROR win32_audio_stream(extSound *, LARGE, LARGE); static void sound_stopped_event(extSound *Self) { - if (Self->OnStop.Type IS CALL_STDC) { + if (Self->OnStop.isC()) { pf::SwitchContext context(Self->OnStop.StdC.Context); - auto routine = (void (*)(extSound *))Self->OnStop.StdC.Routine; - routine(Self); + auto routine = (void (*)(extSound *, APTR))Self->OnStop.StdC.Routine; + routine(Self, Self->OnStop.StdC.Meta); } - else if (Self->OnStop.Type IS CALL_SCRIPT) { + else if (Self->OnStop.isScript()) { auto script = Self->OnStop.Script.Script; const ScriptArg args[] = { { "Sound", Self, FD_OBJECTPTR } }; - ERROR error; - scCallback(script, Self->OnStop.Script.ProcedureID, args, ARRAYSIZE(args), &error); + ERR error; + scCallback(script, Self->OnStop.Script.ProcedureID, args, std::ssize(args), &error); } } @@ -123,14 +123,14 @@ static void onstop_event(LONG SampleHandle) // Called when the estimated time for playback is over. #ifdef _WIN32 -static ERROR timer_playback_ended(extSound *Self, LARGE Elapsed, LARGE CurrentTime) +static ERR timer_playback_ended(extSound *Self, LARGE Elapsed, LARGE CurrentTime) { pf::Log log; log.trace("Sound streaming completed."); sound_stopped_event(Self); Self->PlaybackTimer = 0; // NB: We don't manually stop the audio streamer, it will automatically stop once buffers are clear. - return ERR_Terminate; + return ERR::Terminate; } #endif @@ -139,7 +139,7 @@ static ERROR timer_playback_ended(extSound *Self, LARGE Elapsed, LARGE CurrentTi // in determining playback length. #ifdef USE_WIN32_PLAYBACK -static ERROR set_playback_trigger(extSound *Self) +static ERR set_playback_trigger(extSound *Self) { if (Self->OnStop.Type) { pf::Log log(__FUNCTION__); @@ -153,12 +153,11 @@ static ERROR set_playback_trigger(extSound *Self) log.trace("Playback time period set to %.2fs", playback_time); if (Self->PlaybackTimer) return UpdateTimer(Self->PlaybackTimer, playback_time + 0.01); else { - auto call = make_function_stdc(&timer_playback_ended); - return SubscribeTimer(playback_time + 0.01, &call, &Self->PlaybackTimer); + return SubscribeTimer(playback_time + 0.01, FUNCTION(timer_playback_ended), &Self->PlaybackTimer); } } } - return ERR_Okay; + return ERR::Okay; } #endif @@ -179,8 +178,7 @@ extern "C" void end_of_stream(OBJECTPTR Object, LONG BytesRemaining) } else { log.trace("Remaining time period set to %.2fs", playback_time); - auto call = make_function_stdc(&timer_playback_ended); - SubscribeTimer(playback_time, &call, &Self->PlaybackTimer); + SubscribeTimer(playback_time, FUNCTION(timer_playback_ended), &Self->PlaybackTimer); } } } @@ -205,34 +203,34 @@ static SFM sample_format(extSound *Self) return SFM::NIL; } -static ERROR snd_init_audio(extSound *Self) __attribute__((unused)); -static ERROR snd_init_audio(extSound *Self) +static ERR snd_init_audio(extSound *Self) __attribute__((unused)); +static ERR snd_init_audio(extSound *Self) { pf::Log log; - if (!FindObject("SystemAudio", ID_AUDIO, FOF::NIL, &Self->AudioID)) return ERR_Okay; + if (FindObject("SystemAudio", ID_AUDIO, FOF::NIL, &Self->AudioID) IS ERR::Okay) return ERR::Okay; extAudio *audio; - ERROR error; - if (!(error = NewObject(ID_AUDIO, NF::NIL, &audio))) { + ERR error; + if ((error = NewObject(ID_AUDIO, NF::NIL, &audio)) IS ERR::Okay) { SetName(audio, "SystemAudio"); SetOwner(audio, CurrentTask()); - if (!InitObject(audio)) { - if (!(error = audio->activate())) { + if (InitObject(audio) IS ERR::Okay) { + if ((error = audio->activate()) IS ERR::Okay) { Self->AudioID = audio->UID; } else FreeResource(audio); } else { FreeResource(audio); - error = ERR_Init; + error = ERR::Init; } } - else if (error IS ERR_ObjectExists) return ERR_Okay; - else error = ERR_NewObject; + else if (error IS ERR::ObjectExists) return ERR::Okay; + else error = ERR::NewObject; - if (error) return log.warning(ERR_CreateObject); + if (error != ERR::Okay) return log.warning(ERR::CreateObject); return error; } @@ -243,13 +241,13 @@ Activate: Plays the audio sample. -END- *********************************************************************************************************************/ -static ERROR SOUND_Activate(extSound *Self, APTR Void) +static ERR SOUND_Activate(extSound *Self, APTR Void) { pf::Log log; log.traceBranch("Position: %" PF64, Self->Position); - if (!Self->Length) return log.warning(ERR_FieldNotSet); + if (!Self->Length) return log.warning(ERR::FieldNotSet); #ifdef USE_WIN32_PLAYBACK // Optimised playback for Windows - this does not use our internal mixer. @@ -295,7 +293,7 @@ static ERROR SOUND_Activate(extSound *Self, APTR Void) if (strerr) { log.warning("Failed to create audio buffer, reason: %s (sample length %d)", strerr, Self->Length); - return ERR_Failed; + return ERR::Failed; } Self->Active = true; @@ -313,13 +311,12 @@ static ERROR SOUND_Activate(extSound *Self, APTR Void) sndPan((PlatformData *)Self->PlatformData, Self->Pan); if ((Self->Flags & SDF::STREAM) != SDF::NIL) { - auto call = make_function_stdc(win32_audio_stream); - if (SubscribeTimer(0.25, &call, &Self->StreamTimer)) return log.warning(ERR_Failed); + if (SubscribeTimer(0.25, FUNCTION(win32_audio_stream), &Self->StreamTimer) != ERR::Okay) return log.warning(ERR::Failed); } - else if (set_playback_trigger(Self)) return log.warning(ERR_Failed); + else if (set_playback_trigger(Self) != ERR::Okay) return log.warning(ERR::Failed); auto response = sndPlay((PlatformData *)Self->PlatformData, ((Self->Flags & SDF::LOOP) != SDF::NIL) ? TRUE : FALSE, Self->Position); - return response ? log.warning(ERR_Failed) : ERR_Okay; + return response ? log.warning(ERR::Failed) : ERR::Okay; #else if (!Self->Active) { @@ -335,7 +332,7 @@ static ERROR SOUND_Activate(extSound *Self, APTR Void) else sampleformat = SFM::S16_BIT_MONO; } - if (sampleformat IS SFM::NIL) return log.warning(ERR_InvalidData); + if (sampleformat IS SFM::NIL) return log.warning(ERR::InvalidData); // Create the audio buffer and fill it with sample data @@ -363,28 +360,28 @@ static ERROR SOUND_Activate(extSound *Self, APTR Void) stream.LoopSize = 0; } - if (Self->OnStop.Type) stream.OnStop = make_function_stdc(&onstop_event); - else stream.OnStop.Type = CALL_NONE; + if (Self->OnStop.Type) stream.OnStop = FUNCTION(onstop_event); + else stream.OnStop.clear(); stream.PlayOffset = Self->Position; - stream.Callback = make_function_stdc(&read_stream); + stream.Callback = FUNCTION(read_stream); stream.SampleFormat = sampleformat; stream.SampleLength = Self->Length; - if (!ActionMsg(MT_SndAddStream, Self->AudioID, &stream)) { + if (ActionMsg(MT_SndAddStream, Self->AudioID, &stream) IS ERR::Okay) { Self->Handle = stream.Result; } else { log.warning("Failed to add sample to the Audio device."); - return ERR_Failed; + return ERR::Failed; } } - else if (!AllocMemory(Self->Length, MEM::DATA|MEM::NO_CLEAR, &buffer)) { + else if (AllocMemory(Self->Length, MEM::DATA|MEM::NO_CLEAR, &buffer) IS ERR::Okay) { auto client_pos = Self->Position; if (Self->Position) Self->seekStart(0); // Ensure we're reading the entire sample from the start LONG result; - if (!Self->read(buffer, Self->Length, &result)) { + if (Self->read(buffer, Self->Length, &result) IS ERR::Okay) { if (result != Self->Length) log.warning("Expected %d bytes, read %d", Self->Length, result); Self->seekStart(client_pos); @@ -407,13 +404,13 @@ static ERROR SOUND_Activate(extSound *Self, APTR Void) add.LoopSize = 0; } - if (Self->OnStop.Type) add.OnStop = make_function_stdc(&onstop_event); - else add.OnStop.Type = CALL_NONE; + if (Self->OnStop.Type) add.OnStop = FUNCTION(onstop_event); + else add.OnStop.clear(); add.SampleFormat = sampleformat; add.Data = buffer; add.DataSize = Self->Length; - if (!ActionMsg(MT_SndAddSample, Self->AudioID, &add)) { + if (ActionMsg(MT_SndAddSample, Self->AudioID, &add) IS ERR::Okay) { Self->Handle = add.Result; FreeResource(buffer); @@ -421,15 +418,15 @@ static ERROR SOUND_Activate(extSound *Self, APTR Void) else { FreeResource(buffer); log.warning("Failed to add sample to the Audio device."); - return ERR_Failed; + return ERR::Failed; } } else { FreeResource(buffer); - return log.warning(ERR_Read); + return log.warning(ERR::Read); } } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } Self->Active = true; @@ -467,35 +464,35 @@ static ERROR SOUND_Activate(extSound *Self, APTR Void) if (i >= audio->MaxChannels) { if (!(channel = priority)) { log.msg("Audio channel not available for playback."); - return ERR_Failed; + return ERR::Failed; } } } sndMixStop(*audio, Self->ChannelIndex); - if (!sndMixSample(*audio, Self->ChannelIndex, Self->Handle)) { - if (sndMixVolume(*audio, Self->ChannelIndex, Self->Volume)) return log.warning(ERR_Failed); - if (sndMixPan(*audio, Self->ChannelIndex, Self->Pan)) return log.warning(ERR_Failed); - if (sndMixFrequency(*audio, Self->ChannelIndex, Self->Playback)) return log.warning(ERR_Failed); - if (sndMixPlay(*audio, Self->ChannelIndex, Self->Position)) return log.warning(ERR_Failed); + if (sndMixSample(*audio, Self->ChannelIndex, Self->Handle) IS ERR::Okay) { + if (sndMixVolume(*audio, Self->ChannelIndex, Self->Volume)) return log.warning(ERR::Failed); + if (sndMixPan(*audio, Self->ChannelIndex, Self->Pan)) return log.warning(ERR::Failed); + if (sndMixFrequency(*audio, Self->ChannelIndex, Self->Playback)) return log.warning(ERR::Failed); + if (sndMixPlay(*audio, Self->ChannelIndex, Self->Position)) return log.warning(ERR::Failed); - return ERR_Okay; + return ERR::Okay; } else { log.warning("Failed to set sample %d to channel $%.8x", Self->Handle, Self->ChannelIndex); - return ERR_Failed; + return ERR::Failed; } } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); #endif } //******************************************************************************************************************** -static void notify_onstop_free(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, APTR Args) +static void notify_onstop_free(OBJECTPTR Object, ACTIONID ActionID, ERR Result, APTR Args) { - ((extSound *)CurrentContext())->OnStop.Type = CALL_NONE; + ((extSound *)CurrentContext())->OnStop.clear(); } /********************************************************************************************************************* @@ -504,7 +501,7 @@ Deactivate: Stops the audio sample and resets the playback position. -END- *********************************************************************************************************************/ -static ERROR SOUND_Deactivate(extSound *Self, APTR Void) +static ERR SOUND_Deactivate(extSound *Self, APTR Void) { pf::Log log; @@ -525,11 +522,11 @@ static ERROR SOUND_Deactivate(extSound *Self, APTR Void) if (channel->SampleHandle IS Self->Handle) sndMixStop(*audio, Self->ChannelIndex); } } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } #endif - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -538,7 +535,7 @@ Disable: Disable playback of an active audio sample, equivalent to pausing. -END- *********************************************************************************************************************/ -static ERROR SOUND_Disable(extSound *Self, APTR Void) +static ERR SOUND_Disable(extSound *Self, APTR Void) { pf::Log log; @@ -547,7 +544,7 @@ static ERROR SOUND_Disable(extSound *Self, APTR Void) #ifdef USE_WIN32_PLAYBACK sndStop((PlatformData *)Self->PlatformData); #else - if (!Self->ChannelIndex) return ERR_Okay; + if (!Self->ChannelIndex) return ERR::Okay; pf::ScopedObjectLock audio(Self->AudioID, 5000); if (audio.granted()) { @@ -555,10 +552,10 @@ static ERROR SOUND_Disable(extSound *Self, APTR Void) if (channel->SampleHandle IS Self->Handle) sndMixStop(*audio, Self->ChannelIndex); } } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); #endif - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -567,7 +564,7 @@ Enable: Continues playing a sound if it has been disabled. -END- *********************************************************************************************************************/ -static ERROR SOUND_Enable(extSound *Self, APTR Void) +static ERR SOUND_Enable(extSound *Self, APTR Void) { pf::Log log; log.branch(); @@ -579,7 +576,7 @@ static ERROR SOUND_Enable(extSound *Self, APTR Void) else sndPlay((PlatformData *)Self->PlatformData, FALSE, Self->Position); } #else - if (!Self->ChannelIndex) return ERR_Okay; + if (!Self->ChannelIndex) return ERR::Okay; pf::ScopedObjectLock audio(Self->AudioID, 5000); if (audio.granted()) { @@ -587,22 +584,22 @@ static ERROR SOUND_Enable(extSound *Self, APTR Void) if (channel->SampleHandle IS Self->Handle) sndMixContinue(*audio, Self->ChannelIndex); } } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); #endif - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR SOUND_Free(extSound *Self, APTR Void) +static ERR SOUND_Free(extSound *Self, APTR Void) { if (Self->StreamTimer) { UpdateTimer(Self->StreamTimer, 0); Self->StreamTimer = 0; } if (Self->PlaybackTimer) { UpdateTimer(Self->PlaybackTimer, 0); Self->PlaybackTimer = 0; } - if (Self->OnStop.Type IS CALL_SCRIPT) { + if (Self->OnStop.isScript()) { UnsubscribeAction(Self->OnStop.Script.Script, AC_Free); - Self->OnStop.Type = CALL_NONE; + Self->OnStop.clear(); } #if defined(USE_WIN32_PLAYBACK) @@ -623,7 +620,7 @@ static ERROR SOUND_Free(extSound *Self, APTR Void) if (Self->File) { FreeResource(Self->File); Self->File = NULL; } Self->~extSound(); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -644,16 +641,16 @@ The following custom tag values are formally recognised and may be defined autom *********************************************************************************************************************/ -static ERROR SOUND_GetVar(extSound *Self, struct acGetVar *Args) +static ERR SOUND_GetVar(extSound *Self, struct acGetVar *Args) { - if ((!Args) or (!Args->Field)) return ERR_NullArgs; + if ((!Args) or (!Args->Field)) return ERR::NullArgs; std::string name(Args->Field); if (Self->Tags.contains(name)) { StrCopy(Self->Tags[name].c_str(), Args->Buffer, Args->Size); - return ERR_Okay; + return ERR::Okay; } - else return ERR_UnsupportedField; + else return ERR::UnsupportedField; } /********************************************************************************************************************* @@ -664,16 +661,16 @@ Init: Prepares a sound object for usage. #ifdef USE_WIN32_PLAYBACK -static ERROR SOUND_Init(extSound *Self, APTR Void) +static ERR SOUND_Init(extSound *Self, APTR Void) { pf::Log log; LONG id, len; - ERROR error; + ERR error; // Find the local audio object or create one to ease the developer's workload. if (!Self->AudioID) { - if ((error = snd_init_audio(Self))) return error; + if ((error = snd_init_audio(Self)) != ERR::Okay) return error; } // Open channels for sound sample playback. @@ -681,75 +678,75 @@ static ERROR SOUND_Init(extSound *Self, APTR Void) if (!(Self->ChannelIndex = glSoundChannels[Self->AudioID])) { pf::ScopedObjectLock audio(Self->AudioID, 3000); if (audio.granted()) { - if (!sndOpenChannels(*audio, audio->MaxChannels, &Self->ChannelIndex)) { + if (sndOpenChannels(*audio, audio->MaxChannels, &Self->ChannelIndex) IS ERR::Okay) { glSoundChannels[Self->AudioID] = Self->ChannelIndex; } else { log.warning("Failed to open audio channels."); - return ERR_Failed; + return ERR::Failed; } } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } STRING path; - if (((Self->Flags & SDF::NEW) != SDF::NIL) or (Self->get(FID_Path, &path) != ERR_Okay) or (!path)) { + if (((Self->Flags & SDF::NEW) != SDF::NIL) or (Self->get(FID_Path, &path) != ERR::Okay) or (!path)) { // If the sample is new or no path has been specified, create an audio sample from scratch (e.g. to record // audio to disk). - return ERR_Okay; + return ERR::Okay; } // Load the sound file's header and test it to see if it matches our supported file format. if (!Self->File) { if (!(Self->File = objFile::create::integral(fl::Path(path), fl::Flags(FL::READ|FL::APPROXIMATE)))) { - return log.warning(ERR_File); + return log.warning(ERR::File); } } else Self->File->seekStart(0); Self->File->read(Self->Header, (LONG)sizeof(Self->Header)); - if ((StrCompare((CSTRING)Self->Header, "RIFF", 4, STR::CASE) != ERR_Okay) or - (StrCompare((CSTRING)Self->Header + 8, "WAVE", 4, STR::CASE) != ERR_Okay)) { + if ((StrCompare((CSTRING)Self->Header, "RIFF", 4, STR::CASE) != ERR::Okay) or + (StrCompare((CSTRING)Self->Header + 8, "WAVE", 4, STR::CASE) != ERR::Okay)) { FreeResource(Self->File); Self->File = NULL; - return ERR_NoSupport; + return ERR::NoSupport; } // Read the RIFF header Self->File->seekStart(12); - if (flReadLE(Self->File, &id)) return ERR_Read; // Contains the characters "fmt " - if (flReadLE(Self->File, &len)) return ERR_Read; // Length of data in this chunk + if (flReadLE(Self->File, &id) != ERR::Okay) return ERR::Read; // Contains the characters "fmt " + if (flReadLE(Self->File, &len) != ERR::Okay) return ERR::Read; // Length of data in this chunk WAVEFormat WAVE; LONG result; - if (Self->File->read(&WAVE, len, &result) or (result != len)) { - return log.warning(ERR_Read); + if ((Self->File->read(&WAVE, len, &result) != ERR::Okay) or (result != len)) { + return log.warning(ERR::Read); } // Check the format of the sound file's data if ((WAVE.Format != WAVE_ADPCM) and (WAVE.Format != WAVE_RAW)) { log.msg("This file's WAVE data format is not supported (type %d).", WAVE.Format); - return ERR_InvalidData; + return ERR::InvalidData; } // Look for the "data" chunk - if (find_chunk(Self, Self->File, "data") != ERR_Okay) { - return log.warning(ERR_Read); + if (find_chunk(Self, Self->File, "data") != ERR::Okay) { + return log.warning(ERR::Read); } - if (flReadLE(Self->File, &Self->Length)) return ERR_Read; // Length of audio data in this chunk + if (flReadLE(Self->File, &Self->Length) != ERR::Okay) return ERR::Read; // Length of audio data in this chunk if (Self->Length & 1) Self->Length++; // Setup the sound structure - Self->File->get(FID_Position, &Self->DataOffset); + Self->DataOffset = Self->File->get(FID_Position); Self->Format = WAVE.Format; Self->BytesPerSecond = WAVE.AvgBytesPerSecond; @@ -765,16 +762,16 @@ static ERROR SOUND_Init(extSound *Self, APTR Void) log.trace("Bits: %d, Freq: %d, KBPS: %d, ByteLength: %d, DataOffset: %d", Self->BitsPerSample, Self->Frequency, Self->BytesPerSecond, Self->Length, Self->DataOffset); - return ERR_Okay; + return ERR::Okay; } #else // Use the internal mixer -static ERROR SOUND_Init(extSound *Self, APTR Void) +static ERR SOUND_Init(extSound *Self, APTR Void) { pf::Log log; LONG id, len, result, pos; - ERROR error; + ERR error; if (!Self->AudioID) { if ((error = snd_init_audio(Self))) return error; @@ -790,14 +787,13 @@ static ERROR SOUND_Init(extSound *Self, APTR Void) } else { log.warning("Failed to open audio channels."); - return ERR_Failed; + return ERR::Failed; } } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } - STRING path = NULL; - Self->get(FID_Path, &path); + auto path = Self->get(FID_Path); if (((Self->Flags & SDF::NEW) != SDF::NIL) or (!path)) { log.msg("Sample created as new (without sample data)."); @@ -805,55 +801,55 @@ static ERROR SOUND_Init(extSound *Self, APTR Void) // If the sample is new or no path has been specified, create an audio sample from scratch (e.g. to // record audio to disk). - return ERR_Okay; + return ERR::Okay; } // Load the sound file's header and test it to see if it matches our supported file format. if (!Self->File) { if (!(Self->File = objFile::create::integral(fl::Path(path), fl::Flags(FL::READ|FL::APPROXIMATE)))) { - return log.warning(ERR_File); + return log.warning(ERR::File); } } else Self->File->seekStart(0); Self->File->read(Self->Header, (LONG)sizeof(Self->Header)); - if ((StrCompare((CSTRING)Self->Header, "RIFF", 4, STR::CASE) != ERR_Okay) or - (StrCompare((CSTRING)Self->Header + 8, "WAVE", 4, STR::CASE) != ERR_Okay)) { + if ((StrCompare((CSTRING)Self->Header, "RIFF", 4, STR::CASE) != ERR::Okay) or + (StrCompare((CSTRING)Self->Header + 8, "WAVE", 4, STR::CASE) != ERR::Okay)) { FreeResource(Self->File); Self->File = NULL; - return ERR_NoSupport; + return ERR::NoSupport; } // Read the FMT header Self->File->seek(12, SEEK::START); - if (flReadLE(Self->File, &id)) return ERR_Read; // Contains the characters "fmt " - if (flReadLE(Self->File, &len)) return ERR_Read; // Length of data in this chunk + if (flReadLE(Self->File, &id)) return ERR::Read; // Contains the characters "fmt " + if (flReadLE(Self->File, &len)) return ERR::Read; // Length of data in this chunk WAVEFormat WAVE; if (Self->File->read(&WAVE, len, &result) or (result < len)) { log.warning("Failed to read WAVE format header (got %d, expected %d)", result, len); - return ERR_Read; + return ERR::Read; } // Check the format of the sound file's data if ((WAVE.Format != WAVE_ADPCM) and (WAVE.Format != WAVE_RAW)) { log.warning("This file's WAVE data format is not supported (type %d).", WAVE.Format); - return ERR_InvalidData; + return ERR::InvalidData; } // Look for the cue chunk for loop information - Self->File->get(FID_Position, &pos); + pos = Self->File->get(FID_Position); #if 0 - if (find_chunk(Self, Self->File, "cue ") IS ERR_Okay) { + if (find_chunk(Self, Self->File, "cue ") IS ERR::Okay) { data_p += 32; flReadLE(Self->File, &info.loopstart); // if the next chunk is a LIST chunk, look for a cue length marker - if (find_chunk(Self, Self->File, "LIST") IS ERR_Okay) { + if (find_chunk(Self, Self->File, "LIST") IS ERR::Okay) { if (!strncmp (data_p + 28, "mark", 4)) { data_p += 24; flReadLE(Self->File, &i); // samples in loop @@ -866,15 +862,15 @@ static ERROR SOUND_Init(extSound *Self, APTR Void) // Look for the "data" chunk - if (find_chunk(Self, Self->File, "data") != ERR_Okay) { - return log.warning(ERR_Read); + if (find_chunk(Self, Self->File, "data") != ERR::Okay) { + return log.warning(ERR::Read); } // Setup the sound structure flReadLE(Self->File, &Self->Length); // Length of audio data in this chunk - Self->File->get(FID_Position, &Self->DataOffset); + Self->DataOffset = Self->File->get(FID_Position); Self->Format = WAVE.Format; Self->BytesPerSecond = WAVE.AvgBytesPerSecond; @@ -890,17 +886,17 @@ static ERROR SOUND_Init(extSound *Self, APTR Void) if ((Self->BitsPerSample != 8) and (Self->BitsPerSample != 16)) { log.warning("Bits-Per-Sample of %d not supported.", Self->BitsPerSample); - return ERR_InvalidData; + return ERR::InvalidData; } - return ERR_Okay; + return ERR::Okay; } #endif //******************************************************************************************************************** -static ERROR SOUND_NewObject(extSound *Self, APTR Void) +static ERR SOUND_NewObject(extSound *Self, APTR Void) { new (Self) extSound; @@ -910,7 +906,7 @@ static ERROR SOUND_NewObject(extSound *Self, APTR Void) Self->Playback = 0; Self->Note = NOTE_C; // Standard pitch Self->Stream = STREAM::SMART; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -924,31 +920,31 @@ is determined by the #Position value. -END- *********************************************************************************************************************/ -static ERROR SOUND_Read(extSound *Self, struct acRead *Args) +static ERR SOUND_Read(extSound *Self, struct acRead *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); log.traceBranch("Length: %d, Offset: %" PF64, Args->Length, Self->Position); if (Args->Length <= 0) { Args->Result = 0; - return ERR_Okay; + return ERR::Okay; } // Don't read more than the known raw sample length LONG result; if (Self->Position + Args->Length > Self->Length) { - if (auto error = Self->File->read(Args->Buffer, Self->Length - Self->Position, &result)) return error; + if (auto error = Self->File->read(Args->Buffer, Self->Length - Self->Position, &result); error != ERR::Okay) return error; } - else if (auto error = Self->File->read(Args->Buffer, Args->Length, &result)) return error; + else if (auto error = Self->File->read(Args->Buffer, Args->Length, &result); error != ERR::Okay) return error; Self->Position += result; Args->Result = result; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -957,7 +953,7 @@ SaveToObject: Saves audio sample data to an object. -END- *********************************************************************************************************************/ -static ERROR SOUND_SaveToObject(extSound *Self, struct acSaveToObject *Args) +static ERR SOUND_SaveToObject(extSound *Self, struct acSaveToObject *Args) { pf::Log log; @@ -966,14 +962,14 @@ static ERROR SOUND_SaveToObject(extSound *Self, struct acSaveToObject *Args) if ((Args->ClassID) and (Args->ClassID != ID_SOUND)) { auto mclass = (objMetaClass *)FindClass(Args->ClassID); - ERROR (**routine)(OBJECTPTR, APTR); - if ((!mclass->getPtr(FID_ActionTable, (APTR *)&routine)) and (routine)) { + ERR (**routine)(OBJECTPTR, APTR); + if ((mclass->getPtr(FID_ActionTable, (APTR *)&routine) IS ERR::Okay) and (routine)) { if (routine[AC_SaveToObject]) { return routine[AC_SaveToObject](Self, Args); } - else return log.warning(ERR_NoSupport); + else return log.warning(ERR::NoSupport); } - else return log.warning(ERR_GetField); + else return log.warning(ERR::GetField); } // TODO: Save the sound data as a wave file @@ -981,7 +977,7 @@ static ERROR SOUND_SaveToObject(extSound *Self, struct acSaveToObject *Args) - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -994,20 +990,20 @@ Read action. If the sample is in active playback at the time of the call, the p -END- *********************************************************************************************************************/ -static ERROR SOUND_Seek(extSound *Self, struct acSeek *Args) +static ERR SOUND_Seek(extSound *Self, struct acSeek *Args) { pf::Log log; // NB: Sub-classes may divert their functionality to this routine if the sample is fully buffered. - if (!Args) return log.warning(ERR_NullArgs); - if (!Self->initialised()) return log.warning(ERR_NotInitialised); + if (!Args) return log.warning(ERR::NullArgs); + if (!Self->initialised()) return log.warning(ERR::NotInitialised); if (Args->Position IS SEEK::START) Self->Position = F2T(Args->Offset); else if (Args->Position IS SEEK::END) Self->Position = Self->Length - F2T(Args->Offset); else if (Args->Position IS SEEK::CURRENT) Self->Position += F2T(Args->Offset); else if (Args->Position IS SEEK::RELATIVE) Self->Position = Self->Length * Args->Offset; - else return log.warning(ERR_Args); + else return log.warning(ERR::Args); if (Self->Position < 0) Self->Position = 0; else if (Self->Position > Self->Length) Self->Position = Self->Length; @@ -1047,9 +1043,9 @@ static ERROR SOUND_Seek(extSound *Self, struct acSeek *Args) } #endif } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1058,12 +1054,12 @@ SetVar: Define custom tags that will be saved with the sample data. -END- *********************************************************************************************************************/ -static ERROR SOUND_SetVar(extSound *Self, struct acSetVar *Args) +static ERR SOUND_SetVar(extSound *Self, struct acSetVar *Args) { - if ((!Args) or (!Args->Field) or (!Args->Field[0])) return ERR_NullArgs; + if ((!Args) or (!Args->Field) or (!Args->Field[0])) return ERR::NullArgs; Self->Tags[std::string(Args->Field)] = Args->Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1072,7 +1068,7 @@ Active: Returns TRUE if the sound sample is being played back. -END- *********************************************************************************************************************/ -static ERROR SOUND_GET_Active(extSound *Self, LONG *Value) +static ERR SOUND_GET_Active(extSound *Self, LONG *Value) { #ifdef USE_WIN32_PLAYBACK pf::Log log; @@ -1089,7 +1085,7 @@ static ERROR SOUND_GET_Active(extSound *Self, LONG *Value) } else *Value = FALSE; - return ERR_Okay; + return ERR::Okay; #else *Value = FALSE; @@ -1100,11 +1096,11 @@ static ERROR SOUND_GET_Active(extSound *Self, LONG *Value) if (!channel->isStopped()) *Value = TRUE; } } - else return ERR_AccessObject; + else return ERR::AccessObject; } #endif - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1141,14 +1137,14 @@ Duration: Returns the duration of the sample, measured in seconds. *********************************************************************************************************************/ -static ERROR SOUND_GET_Duration(extSound *Self, DOUBLE *Value) +static ERR SOUND_GET_Duration(extSound *Self, DOUBLE *Value) { if (Self->Length) { const LONG bytes_per_sample = ((((Self->Flags & SDF::STEREO) != SDF::NIL) ? 2 : 1) * (Self->BitsPerSample>>3)); *Value = DOUBLE(Self->Length / bytes_per_sample) / DOUBLE(Self->Playback ? Self->Playback : Self->Frequency); - return ERR_Okay; + return ERR::Okay; } - else return ERR_FieldNotSet; + else return ERR::FieldNotSet; } /********************************************************************************************************************* @@ -1159,10 +1155,10 @@ Lookup: SDF *********************************************************************************************************************/ -static ERROR SOUND_SET_Flags(extSound *Self, LONG Value) +static ERR SOUND_SET_Flags(extSound *Self, LONG Value) { Self->Flags = SDF((LONG(Self->Flags) & 0xffff0000) | (Value & 0x0000ffff)); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1186,11 +1182,11 @@ The buffer that is referred to by the Header field is not populated until the In *********************************************************************************************************************/ -static ERROR SOUND_GET_Header(extSound *Self, BYTE **Value, LONG *Elements) +static ERR SOUND_GET_Header(extSound *Self, BYTE **Value, LONG *Elements) { *Value = (BYTE *)Self->Header; *Elements = ARRAYSIZE(Self->Header); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1202,7 +1198,7 @@ value by the #BytesPerSecond field. *********************************************************************************************************************/ -static ERROR SOUND_SET_Length(extSound *Self, LONG Value) +static ERR SOUND_SET_Length(extSound *Self, LONG Value) { pf::Log log; if (Value >= 0) { @@ -1212,19 +1208,19 @@ static ERROR SOUND_SET_Length(extSound *Self, LONG Value) if (Self->initialised()) { sndLength((PlatformData *)Self->PlatformData, Value); } - return ERR_Okay; + return ERR::Okay; #else if ((Self->Handle) and (Self->AudioID)) { pf::ScopedObjectLock audio(Self->AudioID); if (audio.granted()) { return sndSetSampleLength(*audio, Self->Handle, Value); } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } - else return ERR_Okay; + else return ERR::Okay; #endif } - else return log.warning(ERR_InvalidValue); + else return log.warning(ERR::InvalidValue); } /********************************************************************************************************************* @@ -1266,7 +1262,7 @@ and the lowest is 0. Use either the `S` character or the `#` character for refe *********************************************************************************************************************/ -static ERROR SOUND_GET_Note(extSound *Self, CSTRING *Value) +static ERR SOUND_GET_Note(extSound *Self, CSTRING *Value) { switch(Self->Note) { case NOTE_C: Self->NoteString[0] = 'C'; @@ -1326,14 +1322,14 @@ static ERROR SOUND_GET_Note(extSound *Self, CSTRING *Value) } *Value = Self->NoteString; - return ERR_Okay; + return ERR::Okay; } -static ERROR SOUND_SET_Note(extSound *Self, CSTRING Value) +static ERR SOUND_SET_Note(extSound *Self, CSTRING Value) { pf::Log log; - if (!*Value) return ERR_Okay; + if (!*Value) return ERR::Okay; LONG i, note; for (i=0; (Value[i]) and (i < 3); i++) Self->NoteString[i] = Value[i]; @@ -1363,7 +1359,7 @@ static ERROR SOUND_SET_Note(extSound *Self, CSTRING Value) if ((*str IS 'S') or (*str IS 's') or (*str IS '#')) note++; // Sharp note } - if ((note > NOTE_OCTAVE * 5) or (note < -(NOTE_OCTAVE * 5))) return log.warning(ERR_OutOfRange); + if ((note > NOTE_OCTAVE * 5) or (note < -(NOTE_OCTAVE * 5))) return log.warning(ERR::OutOfRange); Self->Flags |= SDF::NOTE; @@ -1383,7 +1379,7 @@ static ERROR SOUND_SET_Note(extSound *Self, CSTRING Value) // Return if there is no frequency setting yet - if (!Self->Frequency) return ERR_Okay; + if (!Self->Frequency) return ERR::Okay; // Get the default frequency and adjust it to suit the requested octave/scale Self->Playback = Self->Frequency; @@ -1410,11 +1406,11 @@ static ERROR SOUND_SET_Note(extSound *Self, CSTRING Value) if (audio.granted()) { sndMixFrequency(*audio, Self->ChannelIndex, Self->Playback); } - else return ERR_AccessObject; + else return ERR::AccessObject; } #endif - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1430,7 +1426,7 @@ you need to quickly double or halve the playback rate. *********************************************************************************************************************/ -static ERROR SOUND_SET_Octave(extSound *Self, LONG Value) +static ERR SOUND_SET_Octave(extSound *Self, LONG Value) { if ((Value < -10) or (Value > 10)) Self->Octave = Value; @@ -1454,27 +1450,26 @@ in most cases. *********************************************************************************************************************/ -static ERROR SOUND_GET_OnStop(extSound *Self, FUNCTION **Value) +static ERR SOUND_GET_OnStop(extSound *Self, FUNCTION **Value) { - if (Self->OnStop.Type != CALL_NONE) { + if (Self->OnStop.defined()) { *Value = &Self->OnStop; - return ERR_Okay; + return ERR::Okay; } - else return ERR_FieldNotSet; + else return ERR::FieldNotSet; } -static ERROR SOUND_SET_OnStop(extSound *Self, FUNCTION *Value) +static ERR SOUND_SET_OnStop(extSound *Self, FUNCTION *Value) { if (Value) { - if (Self->OnStop.Type IS CALL_SCRIPT) UnsubscribeAction(Self->OnStop.Script.Script, AC_Free); + if (Self->OnStop.isScript()) UnsubscribeAction(Self->OnStop.Script.Script, AC_Free); Self->OnStop = *Value; - if (Self->OnStop.Type IS CALL_SCRIPT) { - auto callback = make_function_stdc(notify_onstop_free); - SubscribeAction(Self->OnStop.Script.Script, AC_Free, &callback); + if (Self->OnStop.isScript()) { + SubscribeAction(Self->OnStop.Script.Script, AC_Free, FUNCTION(notify_onstop_free)); } } - else Self->OnStop.Type = CALL_NONE; - return ERR_Okay; + else Self->OnStop.clear(); + return ERR::Okay; } /********************************************************************************************************************* @@ -1487,7 +1482,7 @@ value is -1.0 to force play through the left speaker and the maximum value is 1. *********************************************************************************************************************/ -static ERROR SOUND_SET_Pan(extSound *Self, DOUBLE Value) +static ERR SOUND_SET_Pan(extSound *Self, DOUBLE Value) { Self->Pan = Value; @@ -1504,11 +1499,11 @@ static ERROR SOUND_SET_Pan(extSound *Self, DOUBLE Value) if (audio.granted()) { sndMixPan(*audio, Self->ChannelIndex, Self->Pan); } - else return ERR_AccessObject; + else return ERR::AccessObject; } #endif - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1521,13 +1516,13 @@ with the `SDF::NEW` flag, it is not necessary to define a file source. *********************************************************************************************************************/ -static ERROR SOUND_GET_Path(extSound *Self, STRING *Value) +static ERR SOUND_GET_Path(extSound *Self, STRING *Value) { - if ((*Value = Self->Path)) return ERR_Okay; - else return ERR_FieldNotSet; + if ((*Value = Self->Path)) return ERR::Okay; + else return ERR::FieldNotSet; } -static ERROR SOUND_SET_Path(extSound *Self, CSTRING Value) +static ERR SOUND_SET_Path(extSound *Self, CSTRING Value) { pf::Log log; @@ -1535,13 +1530,13 @@ static ERROR SOUND_SET_Path(extSound *Self, CSTRING Value) if ((Value) and (*Value)) { LONG i = strlen(Value); - if (!AllocMemory(i+1, MEM::STRING|MEM::NO_CLEAR, (void **)&Self->Path)) { + if (AllocMemory(i+1, MEM::STRING|MEM::NO_CLEAR, (void **)&Self->Path) IS ERR::Okay) { for (i=0; Value[i]; i++) Self->Path[i] = Value[i]; Self->Path[i] = 0; } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1554,11 +1549,11 @@ any time, including during audio playback if real-time adjustments to a sample's *********************************************************************************************************************/ -static ERROR SOUND_SET_Playback(extSound *Self, LONG Value) +static ERR SOUND_SET_Playback(extSound *Self, LONG Value) { pf::Log log; - if ((Value < 0) or (Value > 500000)) return ERR_OutOfRange; + if ((Value < 0) or (Value > 500000)) return ERR::OutOfRange; Self->Playback = Value; Self->Flags &= ~SDF::NOTE; @@ -1574,11 +1569,11 @@ static ERROR SOUND_SET_Playback(extSound *Self, LONG Value) if (audio.granted()) { sndMixFrequency(*audio, Self->ChannelIndex, Self->Playback); } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } #endif - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1590,7 +1585,7 @@ playback position, either when the sample is next played, or immediately if it i *********************************************************************************************************************/ -static ERROR SOUND_SET_Position(extSound *Self, LARGE Value) +static ERR SOUND_SET_Position(extSound *Self, LARGE Value) { return Self->seekStart(Value); } @@ -1607,12 +1602,12 @@ The minimum priority value allowed is -100, the maximum is 100. *********************************************************************************************************************/ -static ERROR SOUND_SET_Priority(extSound *Self, LONG Value) +static ERR SOUND_SET_Priority(extSound *Self, LONG Value) { Self->Priority = Value; if (Self->Priority < -100) Self->Priority = -100; else if (Self->Priority > 100) Self->Priority = 100; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1630,7 +1625,7 @@ playback will dynamically alter the volume. *********************************************************************************************************************/ -static ERROR SOUND_SET_Volume(extSound *Self, DOUBLE Value) +static ERR SOUND_SET_Volume(extSound *Self, DOUBLE Value) { if (Value < 0) Value = 0; else if (Value > 1.0) Value = 1.0; @@ -1649,25 +1644,25 @@ static ERROR SOUND_SET_Volume(extSound *Self, DOUBLE Value) if (audio.granted()) { sndMixVolume(*audio, Self->ChannelIndex, Self->Volume); } - else return ERR_AccessObject; + else return ERR::AccessObject; } #endif - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR find_chunk(extSound *Self, objFile *File, CSTRING ChunkName) +static ERR find_chunk(extSound *Self, objFile *File, CSTRING ChunkName) { while (1) { char chunk[4]; LONG len; - if (File->read(chunk, sizeof(chunk), &len) or (len != sizeof(chunk))) { - return ERR_Read; + if ((File->read(chunk, sizeof(chunk), &len) != ERR::Okay) or (len != sizeof(chunk))) { + return ERR::Read; } - if (!StrCompare(ChunkName, chunk, 4, STR::CASE)) return ERR_Okay; + if (StrCompare(ChunkName, chunk, 4, STR::CASE) IS ERR::Okay) return ERR::Okay; flReadLE(Self->File, &len); // Length of data in this chunk Self->File->seekCurrent(len); @@ -1677,7 +1672,7 @@ static ERROR find_chunk(extSound *Self, objFile *File, CSTRING ChunkName) //******************************************************************************************************************** #ifdef USE_WIN32_PLAYBACK -static ERROR win32_audio_stream(extSound *Self, LARGE Elapsed, LARGE CurrentTime) +static ERR win32_audio_stream(extSound *Self, LARGE Elapsed, LARGE CurrentTime) { pf::Log log(__FUNCTION__); @@ -1689,14 +1684,14 @@ static ERROR win32_audio_stream(extSound *Self, LARGE Elapsed, LARGE CurrentTime sound_stopped_event(Self); if (Self->PlaybackTimer) { UpdateTimer(Self->PlaybackTimer, 0); Self->PlaybackTimer = 0; } Self->StreamTimer = 0; - return ERR_Terminate; + return ERR::Terminate; } else if (response IS 1) { Self->StreamTimer = 0; - return ERR_Terminate; + return ERR::Terminate; } - return ERR_Okay; + return ERR::Okay; } #endif @@ -1765,7 +1760,7 @@ static const ActionArray clActions[] = { //******************************************************************************************************************** -ERROR add_sound_class(void) +ERR add_sound_class(void) { clSound = objMetaClass::create::global( fl::BaseClassID(ID_SOUND), @@ -1780,7 +1775,7 @@ ERROR add_sound_class(void) fl::Size(sizeof(extSound)), fl::Path(MOD_PATH)); - return clSound ? ERR_Okay : ERR_AddClass; + return clSound ? ERR::Okay : ERR::AddClass; } void free_sound_class(void) diff --git a/src/audio/commands.cpp b/src/audio/commands.cpp index e918f7a2a..978c8c793 100644 --- a/src/audio/commands.cpp +++ b/src/audio/commands.cpp @@ -36,9 +36,9 @@ static void add_mix_cmd(objAudio *Audio, CMD Command, LONG Handle) //******************************************************************************************************************** // It is a requirement that VOL_RAMPING or OVER_SAMPLING flags have been set in the target Audio object. -static ERROR fade_in(extAudio *Audio, AudioChannel *channel) +static ERR fade_in(extAudio *Audio, AudioChannel *channel) { - if (((Audio->Flags & ADF::VOL_RAMPING) IS ADF::NIL) or ((Audio->Flags & ADF::OVER_SAMPLING) IS ADF::NIL)) return ERR_Okay; + if (((Audio->Flags & ADF::VOL_RAMPING) IS ADF::NIL) or ((Audio->Flags & ADF::OVER_SAMPLING) IS ADF::NIL)) return ERR::Okay; channel->LVolume = 0; channel->RVolume = 0; @@ -48,23 +48,23 @@ static ERROR fade_in(extAudio *Audio, AudioChannel *channel) //******************************************************************************************************************** // In oversampling mode, active samples are faded-out on a shadow channel rather than stopped abruptly. -static ERROR fade_out(extAudio *Audio, LONG Handle) +static ERR fade_out(extAudio *Audio, LONG Handle) { - if ((Audio->Flags & ADF::OVER_SAMPLING) IS ADF::NIL) return ERR_Okay; + if ((Audio->Flags & ADF::OVER_SAMPLING) IS ADF::NIL) return ERR::Okay; auto channel = Audio->GetChannel(Handle); auto shadow = Audio->GetShadow(Handle); if (channel->isStopped() or (shadow->State IS CHS::FADE_OUT) or - ((channel->LVolume < 0.01) and (channel->RVolume < 0.01))) return ERR_Okay; + ((channel->LVolume < 0.01) and (channel->RVolume < 0.01))) return ERR::Okay; *shadow = *channel; shadow->Volume = 0; shadow->State = CHS::FADE_OUT; set_channel_volume(Audio, shadow); shadow->Flags |= CHF::VOL_RAMP; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -89,17 +89,17 @@ NullArgs *********************************************************************************************************************/ -static ERROR sndMixStartSequence(objAudio *Audio, LONG Handle) +static ERR sndMixStartSequence(objAudio *Audio, LONG Handle) { pf::Log log(__FUNCTION__); - if ((!Audio) or (!Handle)) return log.warning(ERR_NullArgs); + if ((!Audio) or (!Handle)) return log.warning(ERR::NullArgs); log.traceBranch("Audio: #%d, Channel: $%.8x", Audio->UID, Handle); auto channel = ((extAudio *)Audio)->GetChannel(Handle); channel->Buffering = true; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -120,11 +120,11 @@ NullArgs *********************************************************************************************************************/ -static ERROR sndMixEndSequence(objAudio *Audio, LONG Handle) +static ERR sndMixEndSequence(objAudio *Audio, LONG Handle) { pf::Log log(__FUNCTION__); - if ((!Audio) or (!Handle)) return log.warning(ERR_NullArgs); + if ((!Audio) or (!Handle)) return log.warning(ERR::NullArgs); log.traceBranch("Audio: #%d, Channel: $%.8x", Audio->UID, Handle); @@ -135,7 +135,7 @@ static ERROR sndMixEndSequence(objAudio *Audio, LONG Handle) add_mix_cmd(Audio, CMD::END_SEQUENCE, Handle); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -156,29 +156,29 @@ NullArgs *********************************************************************************************************************/ -static ERROR sndMixContinue(objAudio *Audio, LONG Handle) +static ERR sndMixContinue(objAudio *Audio, LONG Handle) { pf::Log log(__FUNCTION__); log.traceBranch("Audio: #%d, Channel: $%.8x", Audio->UID, Handle); - if ((!Audio) or (!Handle)) return log.warning(ERR_NullArgs); + if ((!Audio) or (!Handle)) return log.warning(ERR::NullArgs); auto channel = ((extAudio *)Audio)->GetChannel(Handle); if (channel->Buffering) { add_mix_cmd(Audio, CMD::CONTINUE, Handle); - return ERR_Okay; + return ERR::Okay; } - if (channel->State IS CHS::PLAYING) return ERR_Okay; + if (channel->State IS CHS::PLAYING) return ERR::Okay; // Check if the read position is already at the end of the sample auto &sample = ((extAudio *)Audio)->Samples[channel->SampleHandle]; - if ((sample.Stream) and (sample.PlayPos >= sample.StreamLength)) return ERR_Okay; - else if (channel->Position >= sample.SampleLength) return ERR_Okay; + if ((sample.Stream) and (sample.PlayPos >= sample.StreamLength)) return ERR::Okay; + else if (channel->Position >= sample.SampleLength) return ERR::Okay; fade_out((extAudio *)Audio, Handle); @@ -192,12 +192,9 @@ static ERROR sndMixContinue(objAudio *Audio, LONG Handle) pf::SwitchContext context(Audio); if (((extAudio *)Audio)->Timer) UpdateTimer(((extAudio *)Audio)->Timer, -MIX_INTERVAL); - else { - auto call = make_function_stdc(audio_timer); - SubscribeTimer(MIX_INTERVAL, &call, &((extAudio *)Audio)->Timer); - } + else SubscribeTimer(MIX_INTERVAL, FUNCTION(audio_timer), &((extAudio *)Audio)->Timer); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -219,11 +216,11 @@ NullArgs *********************************************************************************************************************/ -static ERROR sndMixMute(objAudio *Audio, LONG Handle, LONG Mute) +static ERR sndMixMute(objAudio *Audio, LONG Handle, LONG Mute) { pf::Log log(__FUNCTION__); - if ((!Audio) or (!Handle)) return log.warning(ERR_NullArgs); + if ((!Audio) or (!Handle)) return log.warning(ERR::NullArgs); log.traceBranch("Audio: #%d, Channel: $%.8x, Mute: %c", Audio->UID, Handle, Mute ? 'Y' : 'N'); @@ -231,13 +228,13 @@ static ERROR sndMixMute(objAudio *Audio, LONG Handle, LONG Mute) if (channel->Buffering) { add_mix_cmd(Audio, CMD::MUTE, Handle, Mute); - return ERR_Okay; + return ERR::Okay; } if (Mute != 0) channel->Flags |= CHF::MUTE; else channel->Flags &= ~CHF::MUTE; set_channel_volume((extAudio *)Audio, channel); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -259,11 +256,11 @@ NullArgs *********************************************************************************************************************/ -static ERROR sndMixFrequency(objAudio *Audio, LONG Handle, LONG Frequency) +static ERR sndMixFrequency(objAudio *Audio, LONG Handle, LONG Frequency) { pf::Log log(__FUNCTION__); - if ((!Audio) or (!Handle)) return log.warning(ERR_NullArgs); + if ((!Audio) or (!Handle)) return log.warning(ERR::NullArgs); log.traceBranch("Audio: #%d, Channel: $%.8x, Frequency: %d", Audio->UID, Handle, Frequency); @@ -271,11 +268,11 @@ static ERROR sndMixFrequency(objAudio *Audio, LONG Handle, LONG Frequency) if (channel->Buffering) { add_mix_cmd(Audio, CMD::FREQUENCY, Handle, Frequency); - return ERR_Okay; + return ERR::Okay; } channel->Frequency = Frequency; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -297,11 +294,11 @@ NullArgs *********************************************************************************************************************/ -static ERROR sndMixPan(objAudio *Audio, LONG Handle, DOUBLE Pan) +static ERR sndMixPan(objAudio *Audio, LONG Handle, DOUBLE Pan) { pf::Log log(__FUNCTION__); - if ((!Audio) or (!Handle)) return log.warning(ERR_NullArgs); + if ((!Audio) or (!Handle)) return log.warning(ERR::NullArgs); log.traceBranch("Audio: #%d, Channel: $%.8x, Pan: %.2f", Audio->UID, Handle, Pan); @@ -309,7 +306,7 @@ static ERROR sndMixPan(objAudio *Audio, LONG Handle, DOUBLE Pan) if (channel->Buffering) { add_mix_cmd(Audio, CMD::PAN, Handle, Pan); - return ERR_Okay; + return ERR::Okay; } if (Pan < -1.0) channel->Pan = -1.0; @@ -317,7 +314,7 @@ static ERROR sndMixPan(objAudio *Audio, LONG Handle, DOUBLE Pan) else channel->Pan = Pan; set_channel_volume((extAudio *)Audio, channel); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -340,13 +337,13 @@ NullArgs *********************************************************************************************************************/ -static ERROR sndMixPlay(objAudio *Audio, LONG Handle, LONG Position) +static ERR sndMixPlay(objAudio *Audio, LONG Handle, LONG Position) { pf::Log log(__FUNCTION__); - if ((!Audio) or (!Handle)) return log.warning(ERR_NullArgs); + if ((!Audio) or (!Handle)) return log.warning(ERR::NullArgs); - if (Position < 0) return log.warning(ERR_OutOfRange); + if (Position < 0) return log.warning(ERR::OutOfRange); auto channel = ((extAudio *)Audio)->GetChannel(Handle); @@ -354,12 +351,12 @@ static ERROR sndMixPlay(objAudio *Audio, LONG Handle, LONG Position) if (channel->Buffering) { add_mix_cmd(Audio, CMD::PLAY, Position); - return ERR_Okay; + return ERR::Okay; } if (!channel->SampleHandle) { // A sample must be defined for the channel. log.warning("Channel not associated with a sample."); - return ERR_Failed; + return ERR::Failed; } ((extAudio *)Audio)->finish(*channel, false); // Turn off previous sound @@ -372,15 +369,15 @@ static ERROR sndMixPlay(objAudio *Audio, LONG Handle, LONG Position) if (!sample.Data) { // The sample reference must be valid and not stale. log.warning("On channel %d, referenced sample %d is unconfigured.", Handle, channel->SampleHandle); - return ERR_Failed; + return ERR::Failed; } if (sample.Stream) { - if (Position > sample.StreamLength) return log.warning(ERR_OutOfRange); + if (Position > sample.StreamLength) return log.warning(ERR::OutOfRange); sample.PlayPos = BYTELEN(Position) + fill_stream_buffer(Handle, sample, Position); Position = 0; // Internally we want to start from byte position zero in our stream buffer } - else if (bitpos > sample.SampleLength) return log.warning(ERR_OutOfRange); + else if (bitpos > sample.SampleLength) return log.warning(ERR::OutOfRange); fade_out((extAudio *)Audio, Handle); @@ -393,7 +390,7 @@ static ERROR sndMixPlay(objAudio *Audio, LONG Handle, LONG Position) if ((sample.LoopMode != LOOP::SINGLE_RELEASE) and (sample.LoopMode != LOOP::DOUBLE) and (channel->State IS CHS::RELEASED)) { ((extAudio *)Audio)->finish(*channel, true); - return ERR_Okay; + return ERR::Okay; } } @@ -505,13 +502,10 @@ static ERROR sndMixPlay(objAudio *Audio, LONG Handle, LONG Position) if (channel->State IS CHS::PLAYING) { pf::SwitchContext context(Audio); if (((extAudio *)Audio)->Timer) UpdateTimer(((extAudio *)Audio)->Timer, -MIX_INTERVAL); - else { - auto call = make_function_stdc(audio_timer); - SubscribeTimer(MIX_INTERVAL, &call, &((extAudio *)Audio)->Timer); - } + else SubscribeTimer(MIX_INTERVAL, FUNCTION(audio_timer), &((extAudio *)Audio)->Timer); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -534,29 +528,29 @@ NullArgs *********************************************************************************************************************/ -static ERROR sndMixRate(objAudio *Audio, LONG Handle, LONG Rate) +static ERR sndMixRate(objAudio *Audio, LONG Handle, LONG Rate) { pf::Log log(__FUNCTION__); - if ((!Audio) or (!Handle)) return log.warning(ERR_NullArgs); + if ((!Audio) or (!Handle)) return log.warning(ERR::NullArgs); log.traceBranch("Audio: #%d, Channel: $%.8x", Audio->UID, Handle); - if ((Rate < 1) or (Rate > 100000)) return log.warning(ERR_OutOfRange); + if ((Rate < 1) or (Rate > 100000)) return log.warning(ERR::OutOfRange); auto channel = ((extAudio *)Audio)->GetChannel(Handle); if (channel->Buffering) { add_mix_cmd(Audio, CMD::RATE, Handle, Rate); - return ERR_Okay; + return ERR::Okay; } WORD index = Handle>>16; if ((index >= 0) and (index < (LONG)((extAudio *)Audio)->Sets.size())) { ((extAudio *)Audio)->Sets[index].UpdateRate = Rate; - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_OutOfRange); + else return log.warning(ERR::OutOfRange); } /********************************************************************************************************************* @@ -582,36 +576,36 @@ NullArgs *********************************************************************************************************************/ -ERROR sndMixSample(objAudio *Audio, LONG Handle, LONG SampleIndex) +ERR sndMixSample(objAudio *Audio, LONG Handle, LONG SampleIndex) { pf::Log log(__FUNCTION__); - if ((!Audio) or (!Handle)) return log.warning(ERR_NullArgs); + if ((!Audio) or (!Handle)) return log.warning(ERR::NullArgs); LONG idx = SampleIndex; log.traceBranch("Audio: #%d, Channel: $%.8x, Sample: %d", Audio->UID, Handle, idx); if ((idx <= 0) or (idx >= (LONG)((extAudio *)Audio)->Samples.size())) { - return log.warning(ERR_OutOfRange); + return log.warning(ERR::OutOfRange); } else if (!((extAudio *)Audio)->Samples[idx].Data) { log.warning("Sample #%d refers to a dead sample.", idx); - return ERR_Failed; + return ERR::Failed; } else if (((extAudio *)Audio)->Samples[idx].SampleLength <= 0) { log.warning("Sample #%d has invalid sample length %d", idx, ((extAudio *)Audio)->Samples[idx].SampleLength); - return ERR_Failed; + return ERR::Failed; } auto channel = ((extAudio *)Audio)->GetChannel(Handle); if (channel->Buffering) { add_mix_cmd(Audio, CMD::SAMPLE, Handle, SampleIndex); - return ERR_Okay; + return ERR::Okay; } - if (channel->SampleHandle IS idx) return ERR_Okay; // Already associated? + if (channel->SampleHandle IS idx) return ERR::Okay; // Already associated? channel->SampleHandle = idx; // Set new sample number to channel channel->Flags |= CHF::CHANGED; // Sample has been changed @@ -629,7 +623,7 @@ ERROR sndMixSample(objAudio *Audio, LONG Handle, LONG SampleIndex) } } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -650,19 +644,19 @@ NullArgs *********************************************************************************************************************/ -ERROR sndMixStop(objAudio *Audio, LONG Handle) +ERR sndMixStop(objAudio *Audio, LONG Handle) { pf::Log log(__FUNCTION__); log.traceBranch("Audio: #%d, Channel: $%.8x", Audio->UID, Handle); - if ((!Audio) or (!Handle)) return log.warning(ERR_NullArgs); + if ((!Audio) or (!Handle)) return log.warning(ERR::NullArgs); auto channel = ((extAudio *)Audio)->GetChannel(Handle); if (channel->Buffering) { add_mix_cmd(Audio, CMD::STOP, Handle); - return ERR_Okay; + return ERR::Okay; } ((extAudio *)Audio)->finish(*channel, true); @@ -673,7 +667,7 @@ ERROR sndMixStop(objAudio *Audio, LONG Handle) shadow->State = CHS::STOPPED; } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -695,22 +689,22 @@ NullArgs *********************************************************************************************************************/ -static ERROR sndMixStopLoop(objAudio *Audio, LONG Handle) +static ERR sndMixStopLoop(objAudio *Audio, LONG Handle) { pf::Log log(__FUNCTION__); log.traceBranch("Audio: #%d, Channel: $%.8x", Audio->UID, Handle); - if ((!Audio) or (!Handle)) return log.warning(ERR_NullArgs); + if ((!Audio) or (!Handle)) return log.warning(ERR::NullArgs); auto channel = ((extAudio *)Audio)->GetChannel(Handle); if (channel->Buffering) { add_mix_cmd(Audio, CMD::STOP_LOOPING, Handle); - return ERR_Okay; + return ERR::Okay; } - if (channel->State != CHS::PLAYING) return ERR_Okay; + if (channel->State != CHS::PLAYING) return ERR::Okay; auto &sample = ((extAudio *)Audio)->Samples[channel->SampleHandle]; @@ -718,7 +712,7 @@ static ERROR sndMixStopLoop(objAudio *Audio, LONG Handle) channel->State = CHS::RELEASED; } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -741,19 +735,19 @@ NullArgs *********************************************************************************************************************/ -static ERROR sndMixVolume(objAudio *Audio, LONG Handle, DOUBLE Volume) +static ERR sndMixVolume(objAudio *Audio, LONG Handle, DOUBLE Volume) { pf::Log log(__FUNCTION__); log.traceBranch("Audio: #%d, Channel: $%.8x", Audio->UID, Handle); - if ((!Audio) or (!Handle)) return log.warning(ERR_NullArgs); + if ((!Audio) or (!Handle)) return log.warning(ERR::NullArgs); auto channel = ((extAudio *)Audio)->GetChannel(Handle); if (channel->Buffering) { add_mix_cmd(Audio, CMD::VOLUME, Volume); - return ERR_Okay; + return ERR::Okay; } if (Volume > 1.0) channel->Volume = 1.0; @@ -761,5 +755,5 @@ static ERROR sndMixVolume(objAudio *Audio, LONG Handle, DOUBLE Volume) else channel->Volume = Volume; set_channel_volume((extAudio *)Audio, channel); - return ERR_Okay; + return ERR::Okay; } diff --git a/src/audio/dsound.cpp b/src/audio/dsound.cpp index e314ce146..bd5908c59 100644 --- a/src/audio/dsound.cpp +++ b/src/audio/dsound.cpp @@ -195,8 +195,14 @@ void sndStop(PlatformData *Sound) //******************************************************************************************************************** // Used by the Sound class to play WAV or raw audio samples that are independent of our custom mixer. -int sndPlay(PlatformData *Sound, bool Loop, int Offset) +__declspec(no_sanitize_address) int sndPlay(PlatformData *Sound, bool Loop, int Offset) { +#ifdef __SANITIZE_ADDRESS__ + // There is an issue with the address sanitizer being tripped in calls to DirectSound under no client fault. + // The no_sanitize_address option doesn't seem to work as expected, so for the time being DirectSound + // is disabled if the sanitizer is enabled. + return -1; +#else if ((!Sound) or (!Sound->SoundBuffer)) return -1; if (Offset < 0) Offset = 0; @@ -240,6 +246,7 @@ int sndPlay(PlatformData *Sound, bool Loop, int Offset) else IDirectSoundBuffer_Play(Sound->SoundBuffer, 0, 0, 0); return 0; +#endif } //******************************************************************************************************************** diff --git a/src/audio/functions.cpp b/src/audio/functions.cpp index db7da9774..ae7e16a22 100644 --- a/src/audio/functions.cpp +++ b/src/audio/functions.cpp @@ -7,27 +7,27 @@ static FLOAT *glMixDest = NULL; // TODO: Global requires deprecation static void filter_float_mono(extAudio *, FLOAT *, LONG); static void filter_float_stereo(extAudio *, FLOAT *, LONG); static void mix_channel(extAudio *, AudioChannel &, LONG, APTR); -static ERROR mix_data(extAudio *, LONG, APTR); -static ERROR process_commands(extAudio *, SAMPLE); +static ERR mix_data(extAudio *, LONG, APTR); +static ERR process_commands(extAudio *, SAMPLE); //******************************************************************************************************************** static void audio_stopped_event(extAudio &Audio, LONG SampleHandle) { auto &sample = Audio.Samples[SampleHandle]; - if (sample.OnStop.Type IS CALL_STDC) { + if (sample.OnStop.isC()) { pf::SwitchContext context(sample.OnStop.StdC.Context); - auto routine = (void (*)(extAudio *, LONG))sample.OnStop.StdC.Routine; - routine(&Audio, SampleHandle); + auto routine = (void (*)(extAudio *, LONG, APTR))sample.OnStop.StdC.Routine; + routine(&Audio, SampleHandle, sample.OnStop.StdC.Meta); } - else if (sample.OnStop.Type IS CALL_SCRIPT) { + else if (sample.OnStop.isScript()) { auto script = sample.OnStop.Script.Script; const ScriptArg args[] = { { "Audio", &Audio, FD_OBJECTPTR }, { "Handle", SampleHandle } }; - ERROR error; - scCallback(script, sample.OnStop.Script.ProcedureID, args, ARRAYSIZE(args), &error); + ERR error; + scCallback(script, sample.OnStop.Script.ProcedureID, args, std::ssize(args), &error); } } @@ -36,12 +36,12 @@ static void audio_stopped_event(extAudio &Audio, LONG SampleHandle) static BYTELEN fill_stream_buffer(LONG Handle, AudioSample &Sample, LONG Offset) { - if (Sample.Callback.Type IS CALL_STDC) { + if (Sample.Callback.isC()) { pf::SwitchContext context(Sample.Callback.StdC.Context); - auto routine = (BYTELEN (*)(LONG, LONG, UBYTE *, LONG))Sample.Callback.StdC.Routine; - return routine(Handle, Offset, Sample.Data, Sample.SampleLength<Sets.size(); i++) { @@ -71,7 +71,7 @@ static ERROR get_mix_amount(extAudio *Self, SAMPLE *MixLeft) } *MixLeft = ml; - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -81,7 +81,7 @@ static ERROR get_mix_amount(extAudio *Self, SAMPLE *MixLeft) extern "C" int dsReadData(BaseClass *Self, void *Buffer, int Length) { if (Self->Class->BaseClassID IS ID_SOUND) { LONG result; - if (((objSound *)Self)->read(Buffer, Length, &result)) return 0; + if (((objSound *)Self)->read(Buffer, Length, &result) != ERR::Okay) return 0; else return result; } else if (Self->Class->BaseClassID IS ID_AUDIO) { @@ -95,7 +95,7 @@ extern "C" int dsReadData(BaseClass *Self, void *Buffer, int Length) { SAMPLE elements = (mix_left < space_left) ? mix_left : space_left; - if (mix_data((extAudio *)Self, elements, Buffer) != ERR_Okay) break; + if (mix_data((extAudio *)Self, elements, Buffer) != ERR::Okay) break; // Drop the mix amount. This may also update buffered channels for the next round @@ -121,11 +121,11 @@ extern "C" void dsSeekData(BaseClass *Self, LONG Offset) { //******************************************************************************************************************** // Defines the L/RVolume and Ramping values for an AudioChannel. These values are derived from the Volume and Pan. -static ERROR set_channel_volume(extAudio *Self, AudioChannel *Channel) +static ERR set_channel_volume(extAudio *Self, AudioChannel *Channel) { pf::Log log(__FUNCTION__); - if ((!Self) or (!Channel)) return log.warning(ERR_NullArgs); + if ((!Self) or (!Channel)) return log.warning(ERR::NullArgs); if (Channel->Volume > 1.0) Channel->Volume = 1.0; else if (Channel->Volume < 0) Channel->Volume = 0; @@ -170,13 +170,13 @@ static ERROR set_channel_volume(extAudio *Self, AudioChannel *Channel) Channel->RVolumeTarget = rightvol; } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** // Process as many command batches as possible that will fit within MixLeft. -ERROR process_commands(extAudio *Self, SAMPLE Elements) +ERR process_commands(extAudio *Self, SAMPLE Elements) { pf::Log log(__FUNCTION__); @@ -217,12 +217,12 @@ ERROR process_commands(extAudio *Self, SAMPLE Elements) } } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR audio_timer(extAudio *Self, LARGE Elapsed, LARGE CurrentTime) +static ERR audio_timer(extAudio *Self, LARGE Elapsed, LARGE CurrentTime) { #ifdef ALSA_ENABLED @@ -251,7 +251,7 @@ static ERROR audio_timer(extAudio *Self, LARGE Elapsed, LARGE CurrentTime) } else { log.warning("ALSA not in an initialised state."); - return ERR_Terminate; + return ERR::Terminate; } // If the audio system is inactive or in a bad state, try to fix it. @@ -265,14 +265,14 @@ static ERROR audio_timer(extAudio *Self, LARGE Elapsed, LARGE CurrentTime) Self->deactivate(); - if (Self->activate() != ERR_Okay) { + if (Self->activate() != ERR::Okay) { log.warning("Audio error is terminal, self-destructing..."); SendMessage(MSGID_FREE, MSF::NIL, &Self->UID, sizeof(OBJECTID)); - return ERR_Failed; + return ERR::Failed; } } - return ERR_Okay; + return ERR::Okay; } if (space_left > SAMPLE(Self->AudioBufferSize / Self->DriverBitSize)) { @@ -293,7 +293,7 @@ static ERROR audio_timer(extAudio *Self, LARGE Elapsed, LARGE CurrentTime) // Produce the audio data - if (mix_data(Self, elements, buffer) != ERR_Okay) break; + if (mix_data(Self, elements, buffer) != ERR::Okay) break; // Drop the mix amount. This may also update buffered channels for the next round @@ -316,7 +316,7 @@ static ERROR audio_timer(extAudio *Self, LARGE Elapsed, LARGE CurrentTime) snd_pcm_status_t *status; snd_pcm_status_alloca(&status); if (snd_pcm_status(Self->Handle, status) < 0) { - return ERR_Okay; + return ERR::Okay; } auto code = snd_pcm_status_get_state(status); @@ -338,17 +338,17 @@ static ERROR audio_timer(extAudio *Self, LARGE Elapsed, LARGE CurrentTime) } } - return ERR_Okay; + return ERR::Okay; #elif _WIN32 sndStreamAudio((PlatformData *)Self->PlatformData); - return ERR_Okay; + return ERR::Okay; #else #warning No audio timer support on this platform. - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -635,7 +635,7 @@ static bool handle_sample_end(extAudio *Self, AudioChannel &Channel) //******************************************************************************************************************** // Main entry point for mixing sound data to destination -static ERROR mix_data(extAudio *Self, LONG Elements, APTR Dest) +static ERR mix_data(extAudio *Self, LONG Elements, APTR Dest) { pf::Log log(__FUNCTION__); @@ -685,7 +685,7 @@ static ERROR mix_data(extAudio *Self, LONG Elements, APTR Dest) Elements -= window; } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** diff --git a/src/audio/module_def.c b/src/audio/module_def.c index 3699917b7..dda2992f5 100644 --- a/src/audio/module_def.c +++ b/src/audio/module_def.c @@ -1,18 +1,18 @@ // Auto-generated by idl-c.fluid extern "C" { -static ERROR sndMixContinue(objAudio * Audio, LONG Handle); -static ERROR sndMixFrequency(objAudio * Audio, LONG Handle, LONG Frequency); -static ERROR sndMixMute(objAudio * Audio, LONG Handle, LONG Mute); -static ERROR sndMixPan(objAudio * Audio, LONG Handle, DOUBLE Pan); -static ERROR sndMixPlay(objAudio * Audio, LONG Handle, LONG Position); -static ERROR sndMixRate(objAudio * Audio, LONG Handle, LONG Rate); -static ERROR sndMixSample(objAudio * Audio, LONG Handle, LONG Sample); -static ERROR sndMixStop(objAudio * Audio, LONG Handle); -static ERROR sndMixStopLoop(objAudio * Audio, LONG Handle); -static ERROR sndMixVolume(objAudio * Audio, LONG Handle, DOUBLE Volume); -static ERROR sndMixStartSequence(objAudio * Audio, LONG Handle); -static ERROR sndMixEndSequence(objAudio * Audio, LONG Handle); +static ERR sndMixContinue(objAudio * Audio, LONG Handle); +static ERR sndMixFrequency(objAudio * Audio, LONG Handle, LONG Frequency); +static ERR sndMixMute(objAudio * Audio, LONG Handle, LONG Mute); +static ERR sndMixPan(objAudio * Audio, LONG Handle, DOUBLE Pan); +static ERR sndMixPlay(objAudio * Audio, LONG Handle, LONG Position); +static ERR sndMixRate(objAudio * Audio, LONG Handle, LONG Rate); +static ERR sndMixSample(objAudio * Audio, LONG Handle, LONG Sample); +static ERR sndMixStop(objAudio * Audio, LONG Handle); +static ERR sndMixStopLoop(objAudio * Audio, LONG Handle); +static ERR sndMixVolume(objAudio * Audio, LONG Handle, DOUBLE Volume); +static ERR sndMixStartSequence(objAudio * Audio, LONG Handle); +static ERR sndMixEndSequence(objAudio * Audio, LONG Handle); } // extern c #ifndef FDEF @@ -49,4 +49,4 @@ const struct Function glFunctions[] = { }; #undef MOD_IDL -#define MOD_IDL "s.AudioLoop:wLoopMode,cLoop1Type[LTYPE],cLoop2Type[LTYPE],lLoop1Start,lLoop1End,lLoop2Start,lLoop2End\nc.ADF:AUTO_SAVE=0x20,FILTER_HIGH=0x4,FILTER_LOW=0x2,OVER_SAMPLING=0x1,STEREO=0x8,SYSTEM_WIDE=0x40,VOL_RAMPING=0x10\nc.CHF:BACKWARD=0x2,CHANGED=0x8,MUTE=0x1,VOL_RAMP=0x4\nc.CHS:FADE_OUT=0x4,FINISHED=0x1,PLAYING=0x2,RELEASED=0x3,STOPPED=0x0\nc.LOOP:AMIGA=0x5,AMIGA_NONE=0x4,DOUBLE=0x3,SINGLE=0x1,SINGLE_RELEASE=0x2\nc.LTYPE:BIDIRECTIONAL=0x2,UNIDIRECTIONAL=0x1\nc.NOTE:A=0x9,AS=0xa,B=0xb,C=0x0,CS=0x1,D=0x2,DS=0x3,E=0x4,F=0x5,FS=0x6,G=0x7,GS=0x8,OCTAVE=0xc\nc.SDF:LOOP=0x1,NEW=0x2,NOTE=0x80000000,RESTRICT_PLAY=0x8,STEREO=0x4,STREAM=0x40000000\nc.SFM:END=0x5,F_BIG_ENDIAN=0x80000000,S16_BIT_MONO=0x2,S16_BIT_STEREO=0x4,U8_BIT_MONO=0x1,U8_BIT_STEREO=0x3\nc.STREAM:ALWAYS=0x3,NEVER=0x1,SMART=0x2\nc.SVF:CAPTURE=0x10000,MUTE=0x100,UNMUTE=0x1000\nc.VCF:CAPTURE=0x10,JOINED=0x100,MONO=0x1000,MUTE=0x10000,PLAYBACK=0x1,SYNC=0x100000\n" +#define MOD_IDL "s.AudioLoop:wLoopMode,cLoop1Type,cLoop2Type,lLoop1Start,lLoop1End,lLoop2Start,lLoop2End\nc.ADF:AUTO_SAVE=0x20,FILTER_HIGH=0x4,FILTER_LOW=0x2,OVER_SAMPLING=0x1,STEREO=0x8,SYSTEM_WIDE=0x40,VOL_RAMPING=0x10\nc.CHF:BACKWARD=0x2,CHANGED=0x8,MUTE=0x1,VOL_RAMP=0x4\nc.CHS:FADE_OUT=0x4,FINISHED=0x1,PLAYING=0x2,RELEASED=0x3,STOPPED=0x0\nc.LOOP:AMIGA=0x5,AMIGA_NONE=0x4,DOUBLE=0x3,SINGLE=0x1,SINGLE_RELEASE=0x2\nc.LTYPE:BIDIRECTIONAL=0x2,UNIDIRECTIONAL=0x1\nc.NOTE:A=0x9,AS=0xa,B=0xb,C=0x0,CS=0x1,D=0x2,DS=0x3,E=0x4,F=0x5,FS=0x6,G=0x7,GS=0x8,OCTAVE=0xc\nc.SDF:LOOP=0x1,NEW=0x2,NOTE=0x80000000,RESTRICT_PLAY=0x8,STEREO=0x4,STREAM=0x40000000\nc.SFM:END=0x5,F_BIG_ENDIAN=0x80000000,S16_BIT_MONO=0x2,S16_BIT_STEREO=0x4,U8_BIT_MONO=0x1,U8_BIT_STEREO=0x3\nc.STREAM:ALWAYS=0x3,NEVER=0x1,SMART=0x2\nc.SVF:CAPTURE=0x10000,MUTE=0x100,UNMUTE=0x1000\nc.VCF:CAPTURE=0x10,JOINED=0x100,MONO=0x1000,MUTE=0x10000,PLAYBACK=0x1,SYNC=0x100000\n" diff --git a/src/audio/windows.h b/src/audio/windows.h index 21383d1d9..f7b5489b5 100644 --- a/src/audio/windows.h +++ b/src/audio/windows.h @@ -10,7 +10,7 @@ void sndFrequency(struct PlatformData *, int); void sndSetPosition(struct PlatformData *, int); const char * sndInitialiseAudio(void); void sndPan(struct PlatformData *, float); -int sndPlay(struct PlatformData *, bool, int); +__declspec(no_sanitize_address) int sndPlay(struct PlatformData *, bool, int); void sndReleaseAudio(void); void sndStop(struct PlatformData *); extern "C" int sndStreamAudio(struct PlatformData *); diff --git a/src/config.h.in b/src/config.h.in index c97993a66..29ccd8377 100644 --- a/src/config.h.in +++ b/src/config.h.in @@ -26,6 +26,7 @@ #ifdef PARASOL_STATIC #cmakedefine INC_MOD_AUDIO #cmakedefine INC_MOD_DISPLAY +#cmakedefine INC_MOD_DOCUMENT #cmakedefine INC_MOD_FLUID #cmakedefine INC_MOD_FONT #cmakedefine INC_MOD_HTTP diff --git a/src/core/CMakeLists.txt b/src/core/CMakeLists.txt index 73948cb94..92e1c5f4f 100644 --- a/src/core/CMakeLists.txt +++ b/src/core/CMakeLists.txt @@ -138,7 +138,7 @@ target_include_directories (core PRIVATE target_link_libraries (core PRIVATE zlib) if (PARASOL_STATIC) - target_link_libraries (core PRIVATE audio display fluid font http json mp3 network picture jpeg scintilla svg vector xml) + target_link_libraries (core PRIVATE ${LIB_LIST}) if (X11_Xrandr_FOUND) target_link_libraries (core PRIVATE xrandr) diff --git a/src/core/classes/class_assets.cpp b/src/core/classes/class_assets.cpp index af38b358f..ebe3acc3d 100644 --- a/src/core/classes/class_assets.cpp +++ b/src/core/classes/class_assets.cpp @@ -96,7 +96,7 @@ ERROR add_asset_class(void) if (!(openinfo = GetResourcePtr(RES::OPENINFO))) { log.warning("No OpenInfo structure set during Core initialisation."); - return ERR_Failed; + return ERR::Failed; } classname = NULL; @@ -127,7 +127,7 @@ ERROR add_asset_class(void) if ((!env) or (!classname)) { log.warning("Android env and class name must be defined when opening the Core."); - return ERR_Failed; + return ERR::Failed; } jclass glActivityClass = ((*env)->FindClass)(env, classname); @@ -138,11 +138,11 @@ ERROR add_asset_class(void) if (glAssetManager) { glAssetManager = (*env)->NewGlobalRef(env, glAssetManager); // This call is required to prevent the Java GC from collecting the reference. } - else { log.traceWarning("Failed to get assetManager field."); return ERR_SystemCall; } + else { log.traceWarning("Failed to get assetManager field."); return ERR::SystemCall; } } - else { log.traceWarning("Failed to get assetManager field ID."); return ERR_SystemCall; } + else { log.traceWarning("Failed to get assetManager field ID."); return ERR::SystemCall; } } - else { log.traceWarning("Failed to get Java class %s", classname); return ERR_SystemCall; } + else { log.traceWarning("Failed to get Java class %s", classname); return ERR::SystemCall; } } // Create the assets: control class @@ -154,7 +154,7 @@ ERROR add_asset_class(void) fl::Actions(clActions), fl::Methods(clMethods), fl::Fields(clFields), - fl::Path("modules:core")))) return ERR_CreateObject; + fl::Path("modules:core")))) return ERR::CreateObject; // Create the 'assets' virtual volume @@ -165,7 +165,7 @@ ERROR add_asset_class(void) VAS_GET_INFO, &get_info, 0); - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -186,14 +186,14 @@ void free_asset_class(void) static ERROR ASSET_Delete(objFile *Self, APTR Void) { - return ERR_NoSupport; // Asset files cannot be deleted. + return ERR::NoSupport; // Asset files cannot be deleted. } //******************************************************************************************************************** static ERROR ASSET_Free(objFile *Self, APTR Void) { - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -203,13 +203,13 @@ static ERROR ASSET_Init(objFile *Self, APTR Void) pf::Log log(__FUNCTION__); prvFileAsset *prv; - if (!Self->Path) return ERR_FieldNotSet; + if (!Self->Path) return ERR::FieldNotSet; log.trace("Path: %s", Self->Path); - if (StrCompare("assets:", Self->Path, LEN_ASSETS) != ERR_Okay) return ERR_NoSupport; + if (StrCompare("assets:", Self->Path, LEN_ASSETS) != ERR::Okay) return ERR::NoSupport; - if (Self->Flags & (FL::NEW|FL::WRITE)) return log.warning(ERR_ReadOnly); + if (Self->Flags & (FL::NEW|FL::WRITE)) return log.warning(ERR::ReadOnly); // Allocate private structure @@ -218,7 +218,7 @@ static ERROR ASSET_Init(objFile *Self, APTR Void) for (len=0; Self->Path[len]; len++); if (Self->Path[len-1] IS ':') { - return ERR_Okay; + return ERR::Okay; } else if (Self->Path[len-1] IS '/') { // Check that the folder exists. @@ -233,12 +233,12 @@ static ERROR ASSET_Init(objFile *Self, APTR Void) if ((dir = AAssetManager_openDir(get_asset_manager(), dirpath))) { // Folder exists, close it and return OK AAssetDir_close(dir); - return ERR_Okay; + return ERR::Okay; } else { FreeResource(Self->ChildPrivate); Self->ChildPrivate = NULL; - return ERR_DoesNotExist; + return ERR::DoesNotExist; } } else { @@ -249,24 +249,24 @@ static ERROR ASSET_Init(objFile *Self, APTR Void) AAssetManager *mgr = get_asset_manager(); if (mgr) { if ((prv->Asset = AAssetManager_open(mgr, Self->Path+LEN_ASSETS, AASSET_MODE_RANDOM))) { // AASSET_MODE_UNKNOWN, AASSET_MODE_RANDOM - return ERR_Okay; + return ERR::Okay; } else log.warning("Failed to open asset file \"%s\"", Self->Path+LEN_ASSETS); } FreeResource(Self->ChildPrivate); Self->ChildPrivate = NULL; - return ERR_Failed; + return ERR::Failed; } } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } //******************************************************************************************************************** static ERROR ASSET_Move(objFile *Self, struct mtFileMove *Args) { - return ERR_NoSupport; // Assets cannot be moved + return ERR::NoSupport; // Assets cannot be moved } //******************************************************************************************************************** @@ -276,8 +276,8 @@ static ERROR ASSET_Read(objFile *Self, struct acRead *Args) pf::Log log(__FUNCTION__); prvFileAsset *prv; - if (!(prv = Self->ChildPrivate)) return log.warning(ERR_ObjectCorrupt); - if (!(Self->Flags & FL::READ)) return log.warning(ERR_FileReadFlag); + if (!(prv = Self->ChildPrivate)) return log.warning(ERR::ObjectCorrupt); + if (!(Self->Flags & FL::READ)) return log.warning(ERR::FileReadFlag); Args->Result = AAsset_read(prv->Asset, Args->Buffer, Args->Length); @@ -285,18 +285,18 @@ static ERROR ASSET_Read(objFile *Self, struct acRead *Args) if (Args->Result IS -1) { log.msg("Failed to read %d bytes from the file.", Args->Length); Args->Result = 0; - return ERR_Failed; + return ERR::Failed; } - // Return ERR_Okay even though not all data was read, because this was not due to a failure. + // Return ERR::Okay even though not all data was read, because this was not due to a failure. log.msg("%d of the intended %d bytes were read from the file.", Args->Result, Args->Length); Self->Position += Args->Result; - return ERR_Okay; + return ERR::Okay; } else { Self->Position += Args->Result; - return ERR_Okay; + return ERR::Okay; } } @@ -304,7 +304,7 @@ static ERROR ASSET_Read(objFile *Self, struct acRead *Args) static ERROR ASSET_Rename(objFile *Self, struct acRename *Args) { - return ERR_NoSupport; // Assets cannot be renamed. + return ERR::NoSupport; // Assets cannot be renamed. } //******************************************************************************************************************** @@ -314,18 +314,18 @@ static ERROR ASSET_Seek(objFile *Self, struct acSeek *Args) prvFileAsset *prv; LONG method; - if (!(prv = Self->ChildPrivate)) return log.warning(ERR_ObjectCorrupt); + if (!(prv = Self->ChildPrivate)) return log.warning(ERR::ObjectCorrupt); if (Args->Position IS POS_START) method = SEEK::SET; else if (Args->Position IS POS_END) method = SEEK::END; else if (Args->Position IS POS_CURRENT) method = SEEK::CUR; - else return log.warning(ERR_Args); + else return log.warning(ERR::Args); off_t offset = AAsset_seek(prv->Asset, Args->Offset, method); if (offset != -1) Self->Position = offset; - else return ERR_Failed; + else return ERR::Failed; - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -334,7 +334,7 @@ static ERROR ASSET_Seek(objFile *Self, struct acSeek *Args) static ERROR ASSET_Write(objFile *Self, struct acWrite *Args) { - return ERR_NoSupport; // Writing to assets is disallowed + return ERR::NoSupport; // Writing to assets is disallowed } //******************************************************************************************************************** @@ -342,12 +342,12 @@ static ERROR ASSET_Write(objFile *Self, struct acWrite *Args) static ERROR GET_Permissions(objFile *Self, APTR *Value) { *Value = NULL; - return ERR_Okay; + return ERR::Okay; } static ERROR SET_Permissions(objFile *Self, APTR Value) { - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -356,14 +356,14 @@ static ERROR GET_Size(objFile *Self, LARGE *Value) { prvFileAsset *prv; - if (!(prv = Self->ChildPrivate)) return log.warning(ERR_ObjectCorrupt); + if (!(prv = Self->ChildPrivate)) return log.warning(ERR::ObjectCorrupt); if (prv->Asset) { *Value = AAsset_getLength(prv->Asset); - if (*Value >= 0) return ERR_Okay; - else return ERR_Failed; + if (*Value >= 0) return ERR::Okay; + else return ERR::Failed; } - else return ERR_Failed; // Either the file is a folder or hasn't been opened. + else return ERR::Failed; // Either the file is a folder or hasn't been opened. } //******************************************************************************************************************** @@ -377,7 +377,7 @@ static ERROR open_dir(DirInfo *Dir) log.traceBranch("%s", Dir->prvResolvedPath); - if (!(mgr = get_asset_manager())) return log.warning(ERR_SystemCall); + if (!(mgr = get_asset_manager())) return log.warning(ERR::SystemCall); // openDir() doesn't like trailing slashes, this code will handle such circumstances. @@ -392,9 +392,9 @@ static ERROR open_dir(DirInfo *Dir) } if (Dir->prvHandle) { - return ERR_Okay; + return ERR::Okay; } - else return ERR_InvalidPath; + else return ERR::InvalidPath; } //******************************************************************************************************************** @@ -408,7 +408,7 @@ static ERROR scan_dir(DirInfo *Dir) log.traceBranch("Asset file scan on %s", Dir->prvResolvedPath); if (!(mgr = get_asset_manager())) { - return log.warning(ERR_SystemCall); + return log.warning(ERR::SystemCall); } while ((filename = AAssetDir_getNextFileName(Dir->prvHandle))) { @@ -422,7 +422,7 @@ static ERROR scan_dir(DirInfo *Dir) Dir->prvIndex++; Dir->prvTotal++; - return ERR_Okay; + return ERR::Okay; } } @@ -436,12 +436,12 @@ static ERROR scan_dir(DirInfo *Dir) Dir->prvIndex++; Dir->prvTotal++; - return ERR_Okay; + return ERR::Okay; } } } - return ERR_DirEmpty; + return ERR::DirEmpty; } //******************************************************************************************************************** @@ -457,7 +457,7 @@ static ERROR close_dir(DirInfo *Dir) Dir->prvHandle = NULL; } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -485,9 +485,9 @@ static ERROR get_info(CSTRING Path, FileInfo *Info, LONG InfoSize) AAssetDir_close(assetdir); } } - else return ERR_NoSupport; + else return ERR::NoSupport; } - else return ERR_SystemCall; + else return ERR::SystemCall; Info->Flags = 0; Info->Time.Year = 2013; @@ -522,7 +522,7 @@ static ERROR get_info(CSTRING Path, FileInfo *Info, LONG InfoSize) Info->UserID = 0; Info->GroupID = 0; Info->Tags = NULL; - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -538,7 +538,7 @@ static ERROR test_path(CSTRING Path, LONG Flags, LOC *Type) log.traceBranch("%s", Path); - if (!(mgr = get_asset_manager())) return ERR_SystemCall; + if (!(mgr = get_asset_manager())) return ERR::SystemCall; for (len=0; Path[len]; len++); // Check if the reference is explicitly defined as a folder. if (Path[len-1] != '/') { @@ -546,7 +546,7 @@ static ERROR test_path(CSTRING Path, LONG Flags, LOC *Type) log.trace("Path identified as a file."); *Type = LOC::FILE; AAsset_close(asset); - return ERR_Okay; + return ERR::Okay; } dir = AAssetManager_openDir(mgr, Path+LEN_ASSETS); @@ -569,13 +569,13 @@ static ERROR test_path(CSTRING Path, LONG Flags, LOC *Type) log.trace("Path identified as a folder."); *Type = LOC::DIRECTORY; AAssetDir_close(dir); - return ERR_Okay; + return ERR::Okay; } else AAssetDir_close(dir); } log.trace("Path '%s' does not exist.", Path + LEN_ASSETS); - return ERR_DoesNotExist; + return ERR::DoesNotExist; } //******************************************************************************************************************** @@ -592,7 +592,7 @@ static ERROR read_dir(CSTRING Path, DirInfo **Result, LONG Flags) log.traceBranch("Path: %s, Flags: $%.8x", Path, Flags); if (!(mgr = get_asset_manager())) { - return log.warning(ERR_SystemCall); + return log.warning(ERR::SystemCall); } // openDir() doesn't like trailing slashes, this code will handle such circumstances. @@ -608,12 +608,12 @@ static ERROR read_dir(CSTRING Path, DirInfo **Result, LONG Flags) } if (!dir) { - return ERR_InvalidPath; + return ERR::InvalidPath; } if (AllocMemory(sizeof(DirInfo), MEM::DATA, &dirinfo, NULL)) { AAssetDir_close(dir); - return ERR_AllocMemory; + return ERR::AllocMemory; } const char *filename; @@ -625,7 +625,7 @@ static ERROR read_dir(CSTRING Path, DirInfo **Result, LONG Flags) current = NULL; dirinfo->Total = 0; - ERROR error = ERR_Okay; + ERROR error = ERR::Okay; LONG insert = StrCopy(Path+LEN_ASSETS, assetpath, sizeof(assetpath)-2); if (assetpath[insert-1] != '/') assetpath[insert++] = '/'; while ((filename = AAssetDir_getNextFileName(dir)) and (!error)) { @@ -633,7 +633,7 @@ static ERROR read_dir(CSTRING Path, DirInfo **Result, LONG Flags) StrCopy(filename, assetpath+insert, sizeof(assetpath)-insert-1); if (insert >= sizeof(assetpath)-1) { - error = ERR_BufferOverflow; + error = ERR::BufferOverflow; break; } @@ -665,7 +665,7 @@ static ERROR read_dir(CSTRING Path, DirInfo **Result, LONG Flags) dirinfo->Total++; } - else error = ERR_AllocMemory; + else error = ERR::AllocMemory; } AAsset_close(asset); } @@ -685,7 +685,7 @@ static ERROR read_dir(CSTRING Path, DirInfo **Result, LONG Flags) dirinfo->Total++; } - else error = ERR_AllocMemory; + else error = ERR::AllocMemory; } // Insert entry into the linked list @@ -717,7 +717,7 @@ static ERROR read_dir(CSTRING Path, DirInfo **Result, LONG Flags) } else { if (Result) *Result = dirinfo; - return ERR_Okay; + return ERR::Okay; } } #endif diff --git a/src/core/classes/class_config.cpp b/src/core/classes/class_config.cpp index ba309e4a2..6bbd94950 100644 --- a/src/core/classes/class_config.cpp +++ b/src/core/classes/class_config.cpp @@ -56,11 +56,11 @@ class FilterConfig { std::list values; }; -static ERROR GET_KeyFilter(extConfig *, CSTRING *); -static ERROR GET_GroupFilter(extConfig *, CSTRING *); -static ERROR GET_TotalGroups(extConfig *, LONG *); +static ERR GET_KeyFilter(extConfig *, CSTRING *); +static ERR GET_GroupFilter(extConfig *, CSTRING *); +static ERR GET_TotalGroups(extConfig *, LONG *); -static ERROR CONFIG_SaveSettings(extConfig *, APTR); +static ERR CONFIG_SaveSettings(extConfig *, APTR); static const FieldDef clFlags[] = { { "AutoSave", CNF::AUTO_SAVE }, @@ -76,7 +76,7 @@ static const FieldDef clFlags[] = { //******************************************************************************************************************** static bool check_for_key(CSTRING); -static ERROR parse_config(extConfig *, CSTRING); +static ERR parse_config(extConfig *, CSTRING); static ConfigKeys * find_group_wild(extConfig *Self, CSTRING Group); static void apply_key_filter(extConfig *, CSTRING); static void apply_group_filter(extConfig *, CSTRING); @@ -147,29 +147,28 @@ static ULONG calc_crc(extConfig *Self) // Note that multiple files can be specified by separating each file path with a pipe. This allows you to merge // many configuration files into one object. -static ERROR parse_file(extConfig *Self, CSTRING Path) +static ERR parse_file(extConfig *Self, CSTRING Path) { - ERROR error = ERR_Okay; - while ((*Path) and (!error)) { + ERR error = ERR::Okay; + while ((*Path) and (error IS ERR::Okay)) { objFile::create file = { fl::Path(Path), fl::Flags(FL::READ|FL::APPROXIMATE) }; if (file.ok()) { - LONG filesize; - file->get(FID_Size, &filesize); + auto filesize = file->get(FID_Size); if (filesize > 0) { STRING data; - if (!AllocMemory(filesize + 3, MEM::DATA|MEM::NO_CLEAR, (APTR *)&data, NULL)) { + if (AllocMemory(filesize + 3, MEM::DATA|MEM::NO_CLEAR, (APTR *)&data, NULL) IS ERR::Okay) { file->read(data, filesize); // Read the entire file data[filesize++] = '\n'; data[filesize] = 0; error = parse_config(Self, (CSTRING)data); FreeResource(data); } - else error = ERR_AllocMemory; + else error = ERR::AllocMemory; } } - else if ((Self->Flags & CNF::OPTIONAL_FILES) != CNF::NIL) error = ERR_Okay; + else if ((Self->Flags & CNF::OPTIONAL_FILES) != CNF::NIL) error = ERR::Okay; while ((*Path) and (*Path != ';') and (*Path != '|')) Path++; if (*Path) Path++; // Skip separator @@ -184,12 +183,12 @@ Clear: Clears all configuration data. -END- *********************************************************************************************************************/ -static ERROR CONFIG_Clear(extConfig *Self, APTR Void) +static ERR CONFIG_Clear(extConfig *Self, APTR Void) { if (Self->Groups) { Self->Groups->clear(); } if (Self->KeyFilter) { FreeResource(Self->KeyFilter); Self->KeyFilter = NULL; } if (Self->GroupFilter) { FreeResource(Self->GroupFilter); Self->GroupFilter = NULL; } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -201,22 +200,22 @@ be overwritten with new values. -END- *********************************************************************************************************************/ -static ERROR CONFIG_DataFeed(extConfig *Self, struct acDataFeed *Args) +static ERR CONFIG_DataFeed(extConfig *Self, struct acDataFeed *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); if (Args->Datatype IS DATA::TEXT) { - ERROR error = parse_config(Self, (CSTRING)Args->Buffer); - if (!error) { + ERR error = parse_config(Self, (CSTRING)Args->Buffer); + if (error IS ERR::Okay) { if (Self->GroupFilter) apply_group_filter(Self, Self->GroupFilter); if (Self->KeyFilter) apply_key_filter(Self, Self->KeyFilter); } return error; } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -238,22 +237,22 @@ Search *********************************************************************************************************************/ -static ERROR CONFIG_DeleteKey(extConfig *Self, struct cfgDeleteKey *Args) +static ERR CONFIG_DeleteKey(extConfig *Self, struct cfgDeleteKey *Args) { pf::Log log; - if ((!Args) or (!Args->Group) or (!Args->Key)) return ERR_NullArgs; + if ((!Args) or (!Args->Group) or (!Args->Key)) return ERR::NullArgs; log.msg("Group: %s, Key: %s", Args->Group, Args->Key); for (auto& [group, keys] : Self->Groups[0]) { if (!group.compare(Args->Group)) { keys.erase(Args->Key); - return ERR_Okay; + return ERR::Okay; } } - return ERR_Search; + return ERR::Search; } /********************************************************************************************************************* @@ -273,18 +272,18 @@ NullArgs *********************************************************************************************************************/ -static ERROR CONFIG_DeleteGroup(extConfig *Self, struct cfgDeleteGroup *Args) +static ERR CONFIG_DeleteGroup(extConfig *Self, struct cfgDeleteGroup *Args) { - if ((!Args) or (!Args->Group)) return ERR_NullArgs; + if ((!Args) or (!Args->Group)) return ERR::NullArgs; for (auto it = Self->Groups->begin(); it != Self->Groups->end(); it++) { if (!it->first.compare(Args->Group)) { Self->Groups->erase(it); - return(ERR_Okay); + return(ERR::Okay); } } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -293,14 +292,14 @@ Flush: Diverts to #SaveSettings(). -END- *********************************************************************************************************************/ -static ERROR CONFIG_Flush(extConfig *Self, APTR Void) +static ERR CONFIG_Flush(extConfig *Self, APTR Void) { return CONFIG_SaveSettings(Self, NULL); } //******************************************************************************************************************** -static ERROR CONFIG_Free(extConfig *Self, APTR Void) +static ERR CONFIG_Free(extConfig *Self, APTR Void) { pf::Log log; @@ -322,7 +321,7 @@ static ERROR CONFIG_Free(extConfig *Self, APTR Void) if (Self->Path) { FreeResource(Self->Path); Self->Path = 0; } if (Self->KeyFilter) { FreeResource(Self->KeyFilter); Self->KeyFilter = 0; } if (Self->GroupFilter) { FreeResource(Self->GroupFilter); Self->GroupFilter = 0; } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -344,31 +343,31 @@ NoData: There is no data loaded into the config object. *********************************************************************************************************************/ -static ERROR CONFIG_GetGroupFromIndex(extConfig *Self, struct cfgGetGroupFromIndex *Args) +static ERR CONFIG_GetGroupFromIndex(extConfig *Self, struct cfgGetGroupFromIndex *Args) { pf::Log log; - if ((!Args) or (Args->Index < 0)) return log.warning(ERR_Args); + if ((!Args) or (Args->Index < 0)) return log.warning(ERR::Args); if ((Args->Index >= 0) and (Args->Index < (LONG)Self->Groups->size())) { Args->Group = Self->Groups[0][Args->Index].first.c_str(); - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_OutOfRange); + else return log.warning(ERR::OutOfRange); } //******************************************************************************************************************** -static ERROR CONFIG_Init(extConfig *Self, APTR Void) +static ERR CONFIG_Init(extConfig *Self, APTR Void) { pf::Log log; - if ((Self->Flags & CNF::NEW) != CNF::NIL) return ERR_Okay; // Do not load any data even if the path is defined. + if ((Self->Flags & CNF::NEW) != CNF::NIL) return ERR::Okay; // Do not load any data even if the path is defined. - ERROR error = ERR_Okay; + ERR error = ERR::Okay; if (Self->Path) { error = parse_file(Self, Self->Path); - if (!error) { + if (error IS ERR::Okay) { if (Self->GroupFilter) apply_group_filter(Self, Self->GroupFilter); if (Self->KeyFilter) apply_key_filter(Self, Self->KeyFilter); } @@ -387,7 +386,7 @@ The Merge method is used to merge configuration data from one config object prov Existing data in the target will be overwritten by the source in cases where there matching set of group keys. -INPUT- -obj Source: The ID of the config object to be merged. +obj Source: The config object to be merged. -ERRORS- Okay @@ -397,20 +396,20 @@ AccessObject: The source configuration object could not be accessed. *********************************************************************************************************************/ -static ERROR CONFIG_Merge(extConfig *Self, struct cfgMerge *Args) +static ERR CONFIG_Merge(extConfig *Self, struct cfgMerge *Args) { - if ((!Args) or (!Args->Source)) return ERR_NullArgs; - if (Args->Source->Class->ClassID != ID_CONFIG) return ERR_Args; + if ((!Args) or (!Args->Source)) return ERR::NullArgs; + if (Args->Source->Class->ClassID != ID_CONFIG) return ERR::Args; auto src = (extConfig *)Args->Source; merge_groups(Self->Groups[0], src->Groups[0]); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* -METHOD- -MergeFile: Merges a foreign configuration file into existing configuration data. +MergeFile: Merges a configuration file into existing configuration data. The MergeFile method is used to pull configuration data from a file and merge it into the target config object. The path to the configuration file is all that is required. Existing data in the target will be overwritten by the @@ -427,11 +426,11 @@ File: Failed to load the source file. *********************************************************************************************************************/ -static ERROR CONFIG_MergeFile(extConfig *Self, struct cfgMergeFile *Args) +static ERR CONFIG_MergeFile(extConfig *Self, struct cfgMergeFile *Args) { pf::Log log; - if ((!Args) or (!Args->Path)) return log.warning(ERR_NullArgs); + if ((!Args) or (!Args->Path)) return log.warning(ERR::NullArgs); log.branch("%s", Args->Path); @@ -439,17 +438,17 @@ static ERROR CONFIG_MergeFile(extConfig *Self, struct cfgMergeFile *Args) if (src.ok()) { merge_groups(Self->Groups[0], src->Groups[0]); - return ERR_Okay; + return ERR::Okay; } - else return ERR_File; + else return ERR::File; } //******************************************************************************************************************** -static ERROR CONFIG_NewObject(extConfig *Self, APTR Void) +static ERR CONFIG_NewObject(extConfig *Self, APTR Void) { - Self->Groups = new ConfigGroups; - return ERR_Okay; + if (!(Self->Groups = new (std::nothrow) ConfigGroups)) return ERR::Memory; + return ERR::Okay; } /********************************************************************************************************************* @@ -479,28 +478,28 @@ Search: The requested configuration entry does not exist. *********************************************************************************************************************/ -static ERROR CONFIG_ReadValue(extConfig *Self, struct cfgReadValue *Args) +static ERR CONFIG_ReadValue(extConfig *Self, struct cfgReadValue *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); for (auto & [group, keys] : Self->Groups[0]) { if ((Args->Group) and (group.compare(Args->Group))) continue; if (!Args->Key) { Args->Data = keys.cbegin()->second.c_str(); - return ERR_Okay; + return ERR::Okay; } else if (keys.contains(Args->Key)) { Args->Data = keys[Args->Key].c_str(); - return ERR_Okay; + return ERR::Okay; } } log.trace("Could not find key %s : %s.", Args->Group, Args->Key); Args->Data = NULL; - return ERR_Search; + return ERR::Search; } /********************************************************************************************************************* @@ -512,13 +511,13 @@ This action will save the configuration data back to its original file source (a *********************************************************************************************************************/ -static ERROR CONFIG_SaveSettings(extConfig *Self, APTR Void) +static ERR CONFIG_SaveSettings(extConfig *Self, APTR Void) { pf::Log log; log.branch(); ULONG crc = calc_crc(Self); - if (((Self->Flags & CNF::AUTO_SAVE) != CNF::NIL) and (crc IS Self->CRC)) return ERR_Okay; + if (((Self->Flags & CNF::AUTO_SAVE) != CNF::NIL) and (crc IS Self->CRC)) return ERR::Okay; if (Self->Path) { objFile::create file = { @@ -526,12 +525,12 @@ static ERROR CONFIG_SaveSettings(extConfig *Self, APTR Void) }; if (file.ok()) { - if (!Self->saveToObject(*file)) Self->CRC = crc; - return ERR_Okay; + if (Self->saveToObject(*file) IS ERR::Okay) Self->CRC = crc; + return ERR::Okay; } - else return ERR_File; + else return ERR::File; } - else return ERR_MissingPath; + else return ERR::MissingPath; } /********************************************************************************************************************* @@ -540,7 +539,7 @@ SaveToObject: Saves configuration data to an object, using standard config text -END- *********************************************************************************************************************/ -static ERROR CONFIG_SaveToObject(extConfig *Self, struct acSaveToObject *Args) +static ERR CONFIG_SaveToObject(extConfig *Self, struct acSaveToObject *Args) { pf::Log log; @@ -557,7 +556,7 @@ static ERROR CONFIG_SaveToObject(extConfig *Self, struct acSaveToObject *Args) } } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -566,7 +565,7 @@ static ERROR CONFIG_SaveToObject(extConfig *Self, struct acSaveToObject *Args) Set: Sets keys in existing config groups (aborts if the group does not exist). This method is identical to #WriteValue() except it will abort if the name of the referred group does not exist in the -config object. The error code ERR_Search is returned if this is the case. Please refer to #WriteValue() for further +config object. The error code ERR::Search is returned if this is the case. Please refer to #WriteValue() for further information on the behaviour of this function. -INPUT- @@ -584,15 +583,15 @@ GetField: The Entries field could not be retrieved. *********************************************************************************************************************/ -static ERROR CONFIG_Set(extConfig *Self, struct cfgSet *Args) +static ERR CONFIG_Set(extConfig *Self, struct cfgSet *Args) { - if (!Args) return ERR_NullArgs; - if ((!Args->Group) or (!Args->Group[0])) return ERR_NullArgs; - if ((!Args->Key) or (!Args->Key[0])) return ERR_NullArgs; + if (!Args) return ERR::NullArgs; + if ((!Args->Group) or (!Args->Group[0])) return ERR::NullArgs; + if ((!Args->Key) or (!Args->Key[0])) return ERR::NullArgs; auto group = find_group_wild(Self, Args->Group); if (group) return Action(MT_CfgWriteValue, Self, Args); - else return ERR_Search; + else return ERR::Search; } /********************************************************************************************************************* @@ -601,7 +600,7 @@ Sort: Sorts config groups into alphabetical order. -END- *********************************************************************************************************************/ -static ERROR CONFIG_Sort(extConfig *Self, APTR Void) +static ERR CONFIG_Sort(extConfig *Self, APTR Void) { pf::Log log; @@ -612,7 +611,7 @@ static ERROR CONFIG_Sort(extConfig *Self, APTR Void) return a.first < b.first; }); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -633,7 +632,7 @@ NoData *********************************************************************************************************************/ -static ERROR CONFIG_SortByKey(extConfig *Self, struct cfgSortByKey *Args) +static ERR CONFIG_SortByKey(extConfig *Self, struct cfgSortByKey *Args) { if ((!Args) or (!Args->Key)) return CONFIG_Sort(Self, NULL); // If no args are provided then use the default Sort action instead @@ -656,7 +655,7 @@ static ERROR CONFIG_SortByKey(extConfig *Self, struct cfgSortByKey *Args) }); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -685,12 +684,12 @@ GetField: The Entries field could not be retrieved. *********************************************************************************************************************/ -static ERROR CONFIG_WriteValue(extConfig *Self, struct cfgWriteValue *Args) +static ERR CONFIG_WriteValue(extConfig *Self, struct cfgWriteValue *Args) { pf::Log log; - if ((!Args) or (!Args->Group) or (!Args->Key)) return log.warning(ERR_NullArgs); - if ((!Args->Group[0]) or (!Args->Key[0])) return log.warning(ERR_EmptyString); + if ((!Args) or (!Args->Group) or (!Args->Key)) return log.warning(ERR::NullArgs); + if ((!Args->Group[0]) or (!Args->Key[0])) return log.warning(ERR::EmptyString); log.trace("%s.%s = %s", Args->Group, Args->Key, Args->Data); @@ -700,14 +699,14 @@ static ERROR CONFIG_WriteValue(extConfig *Self, struct cfgWriteValue *Args) for (auto& [group, keys] : groups) { if (!group.compare(Args->Group)) { keys[Args->Key] = Args->Data; - return ERR_Okay; + return ERR::Okay; } } auto &new_group = Self->Groups->emplace_back(); new_group.first.assign(Args->Group); new_group.second[Args->Key].assign(Args->Data); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -720,10 +719,10 @@ that is included with the standard framework. *********************************************************************************************************************/ -static ERROR GET_Data(extConfig *Self, ConfigGroups **Value) +static ERR GET_Data(extConfig *Self, ConfigGroups **Value) { *Value = Self->Groups; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -761,29 +760,29 @@ To create a filter based on group names, refer to the #GroupFilter field. *********************************************************************************************************************/ -static ERROR GET_KeyFilter(extConfig *Self, CSTRING *Value) +static ERR GET_KeyFilter(extConfig *Self, CSTRING *Value) { if (Self->KeyFilter) { *Value = Self->KeyFilter; - return ERR_Okay; + return ERR::Okay; } else { *Value = NULL; - return ERR_FieldNotSet; + return ERR::FieldNotSet; } } -static ERROR SET_KeyFilter(extConfig *Self, CSTRING Value) +static ERR SET_KeyFilter(extConfig *Self, CSTRING Value) { if (Self->KeyFilter) { FreeResource(Self->KeyFilter); Self->KeyFilter = NULL; } if ((Value) and (*Value)) { - if (!(Self->KeyFilter = StrClone(Value))) return ERR_AllocMemory; + if (!(Self->KeyFilter = StrClone(Value))) return ERR::AllocMemory; } if (Self->initialised()) apply_key_filter(Self, Self->KeyFilter); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -815,29 +814,29 @@ To create a filter based on key names, refer to the #KeyFilter field. *********************************************************************************************************************/ -static ERROR GET_GroupFilter(extConfig *Self, CSTRING *Value) +static ERR GET_GroupFilter(extConfig *Self, CSTRING *Value) { if (Self->GroupFilter) { *Value = Self->GroupFilter; - return ERR_Okay; + return ERR::Okay; } else { *Value = NULL; - return ERR_FieldNotSet; + return ERR::FieldNotSet; } } -static ERROR SET_GroupFilter(extConfig *Self, CSTRING Value) +static ERR SET_GroupFilter(extConfig *Self, CSTRING Value) { if (Self->GroupFilter) { FreeResource(Self->GroupFilter); Self->GroupFilter = NULL; } if ((Value) and (*Value)) { - if (!(Self->GroupFilter = StrClone(Value))) return ERR_AllocMemory; + if (!(Self->GroupFilter = StrClone(Value))) return ERR::AllocMemory; } if (Self->initialised()) apply_group_filter(Self, Self->GroupFilter); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -846,15 +845,15 @@ Path: Set this field to the location of the source configuration file. *********************************************************************************************************************/ -static ERROR SET_Path(extConfig *Self, CSTRING Value) +static ERR SET_Path(extConfig *Self, CSTRING Value) { if (Self->Path) { FreeResource(Self->Path); Self->Path = NULL; } if ((Value) and (*Value)) { - if (!(Self->Path = StrClone(Value))) return ERR_AllocMemory; + if (!(Self->Path = StrClone(Value))) return ERR::AllocMemory; } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -863,10 +862,10 @@ TotalGroups: Returns the total number of groups in a config object. *********************************************************************************************************************/ -static ERROR GET_TotalGroups(extConfig *Self, LONG *Value) +static ERR GET_TotalGroups(extConfig *Self, LONG *Value) { *Value = Self->Groups->size(); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -877,14 +876,14 @@ TotalKeys: The total number of key values loaded into the config object. *********************************************************************************************************************/ -static ERROR GET_TotalKeys(extConfig *Self, LONG *Value) +static ERR GET_TotalKeys(extConfig *Self, LONG *Value) { LONG total = 0; for (const auto& [group, keys] : Self->Groups[0]) { total += keys.size(); } *Value = total; - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -973,11 +972,11 @@ static FilterConfig parse_filter(std::string Filter, bool KeyValue = false) //******************************************************************************************************************** -static ERROR parse_config(extConfig *Self, CSTRING Buffer) +static ERR parse_config(extConfig *Self, CSTRING Buffer) { pf::Log log(__FUNCTION__); - if (!Buffer) return ERR_NoData; + if (!Buffer) return ERR::NoData; log.traceBranch("%.20s", Buffer); @@ -1034,7 +1033,7 @@ static ERROR parse_config(extConfig *Self, CSTRING Buffer) data = next_group(data, group_name); } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -1051,9 +1050,9 @@ static void apply_key_filter(extConfig *Self, CSTRING Filter) for (auto group = Self->Groups->begin(); group != Self->Groups->end(); ) { bool matched = (f.reverse) ? true : false; for (auto & [k, v] : group->second) { - if (!StrMatch(f.name.c_str(), k.c_str())) { + if (StrMatch(f.name.c_str(), k.c_str()) IS ERR::Okay) { for (auto const &cmp : f.values) { - if (!StrMatch(cmp.c_str(), v.c_str())) { + if (StrMatch(cmp.c_str(), v.c_str()) IS ERR::Okay) { matched = f.reverse ? false : true; break; } @@ -1100,7 +1099,7 @@ static ConfigKeys * find_group_wild(extConfig *Self, CSTRING Group) if ((!Group) or (!*Group)) return NULL; for (auto & [group, keys] : Self->Groups[0]) { - if (!StrCompare(Group, group.c_str(), 0, STR::WILDCARD)) return &keys; + if (StrCompare(Group, group.c_str(), 0, STR::WILDCARD) IS ERR::Okay) return &keys; } return NULL; @@ -1124,7 +1123,7 @@ static const FieldArray clFields[] = { //******************************************************************************************************************** -extern "C" ERROR add_config_class(void) +extern "C" ERR add_config_class(void) { glConfigClass = extMetaClass::create::global( fl::BaseClassID(ID_CONFIG), @@ -1139,6 +1138,6 @@ extern "C" ERROR add_config_class(void) fl::Size(sizeof(extConfig)), fl::Path("modules:core")); - return glConfigClass ? ERR_Okay : ERR_AddClass; + return glConfigClass ? ERR::Okay : ERR::AddClass; } diff --git a/src/core/classes/class_file.cpp b/src/core/classes/class_file.cpp index b8cc4e768..295b91553 100644 --- a/src/core/classes/class_file.cpp +++ b/src/core/classes/class_file.cpp @@ -100,15 +100,15 @@ in a file. extern "C" void path_monitor(HOSTHANDLE, extFile *); -static ERROR FILE_Init(extFile *, APTR); -static ERROR FILE_Watch(extFile *, struct flWatch *); +static ERR FILE_Init(extFile *, APTR); +static ERR FILE_Watch(extFile *, struct flWatch *); -static ERROR SET_Path(extFile *, CSTRING); -static ERROR SET_Size(extFile *, LARGE); +static ERR SET_Path(extFile *, CSTRING); +static ERR SET_Size(extFile *, LARGE); -static ERROR GET_ResolvedPath(extFile *, CSTRING *); +static ERR GET_ResolvedPath(extFile *, CSTRING *); -static ERROR set_permissions(extFile *, PERMIT); +static ERR set_permissions(extFile *, PERMIT); /********************************************************************************************************************* -ACTION- @@ -116,12 +116,12 @@ Activate: Opens the file. Performed automatically if NEW, READ or WRITE flags w -END- *********************************************************************************************************************/ -static ERROR FILE_Activate(extFile *Self, APTR Void) +static ERR FILE_Activate(extFile *Self, APTR Void) { pf::Log log; - if (Self->Handle != -1) return ERR_Okay; - if ((Self->Flags & (FL::NEW|FL::READ|FL::WRITE)) IS FL::NIL) return log.warning(ERR_NothingDone); + if (Self->Handle != -1) return ERR::Okay; + if ((Self->Flags & (FL::NEW|FL::READ|FL::WRITE)) IS FL::NIL) return log.warning(ERR::NothingDone); // Setup the open flags. Note that for new files, the owner will always have read/write/delete permissions by // default. Extra flags can be set through the Permissions field. If the user wishes to turn off his access to @@ -131,7 +131,7 @@ static ERROR FILE_Activate(extFile *Self, APTR Void) if ((Self->Flags & FL::NEW) != FL::NIL) openflags |= O_CREAT|O_TRUNC; CSTRING path; - if (GET_ResolvedPath(Self, &path)) return ERR_ResolvePath; + if (GET_ResolvedPath(Self, &path) != ERR::Okay) return ERR::ResolvePath; #ifdef __unix__ LONG secureflags = S_IRUSR|S_IWUSR|convert_permissions(Self->Permissions); @@ -143,7 +143,7 @@ static ERROR FILE_Activate(extFile *Self, APTR Void) } else if (!StrCompare("/dev/", path, 0)) { log.warning("Opening devices not permitted without the DEVICE flag."); - return ERR_NoPermission; + return ERR::NoPermission; } #else LONG secureflags = S_IRUSR|S_IWUSR; @@ -184,15 +184,15 @@ static ERROR FILE_Activate(extFile *Self, APTR Void) if ((Self->Flags & FL::NEW) != FL::NIL) { // Attempt to create the necessary directories that might be required for this new file. - if (check_paths(path, Self->Permissions) IS ERR_Okay) { + if (check_paths(path, Self->Permissions) IS ERR::Okay) { Self->Handle = open(path, openflags|WIN32OPEN|O_LARGEFILE, secureflags); } if (Self->Handle IS -1) { log.warning("New file error \"%s\"", path); - if (err IS EACCES) return log.warning(ERR_NoPermission); - else if (err IS ENAMETOOLONG) return log.warning(ERR_BufferOverflow); - else return ERR_CreateFile; + if (err IS EACCES) return log.warning(ERR::NoPermission); + else if (err IS ENAMETOOLONG) return log.warning(ERR::BufferOverflow); + else return ERR::CreateFile; } } else if ((errno IS EROFS) and ((Self->Flags & FL::READ) != FL::NIL)) { @@ -211,13 +211,13 @@ static ERROR FILE_Activate(extFile *Self, APTR Void) if ((Self->Handle IS -1) and ((Self->Flags & FL::LINK) IS FL::NIL)) { switch(errno) { - case EACCES: return log.warning(ERR_NoPermission); - case EEXIST: return log.warning(ERR_FileExists); - case EINVAL: return log.warning(ERR_Args); - case ENOENT: return log.warning(ERR_FileNotFound); + case EACCES: return log.warning(ERR::NoPermission); + case EEXIST: return log.warning(ERR::FileExists); + case EINVAL: return log.warning(ERR::Args); + case ENOENT: return log.warning(ERR::FileNotFound); default: log.warning("Could not open \"%s\", error: %s", path, strerror(errno)); - return ERR_Failed; + return ERR::Failed; } } } @@ -242,7 +242,7 @@ static ERROR FILE_Activate(extFile *Self, APTR Void) if ((Self->Flags & FL::BUFFER) != FL::NIL) return flBufferContent(Self); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -267,12 +267,12 @@ Read: Failed to read the file content. *********************************************************************************************************************/ -static ERROR FILE_BufferContent(extFile *Self, APTR Void) +static ERR FILE_BufferContent(extFile *Self, APTR Void) { pf::Log log; LONG len; - if (Self->Buffer) return ERR_Okay; + if (Self->Buffer) return ERR::Okay; acSeek(Self, 0, SEEK::START); @@ -280,16 +280,16 @@ static ERROR FILE_BufferContent(extFile *Self, APTR Void) // If the file has no size, it could be a stream (or simply empty). This routine handles this situation. char ch; - if (!acRead(Self, &ch, 1, &len)) { + if (acRead(Self, &ch, 1, &len) IS ERR::Okay) { Self->Flags |= FL::STREAM; // Allocate a 1 MB memory block, read the stream into it, then reallocate the block to the correct size. UBYTE *buffer; - if (!AllocMemory(1024 * 1024, MEM::NO_CLEAR, (APTR *)&buffer, NULL)) { + if (AllocMemory(1024 * 1024, MEM::NO_CLEAR, (APTR *)&buffer, NULL) IS ERR::Okay) { acSeekStart(Self, 0); acRead(Self, buffer, 1024 * 1024, &len); if (len > 0) { - if (!AllocMemory(len, MEM::NO_CLEAR, (APTR *)&Self->Buffer, NULL)) { + if (AllocMemory(len, MEM::NO_CLEAR, (APTR *)&Self->Buffer, NULL) IS ERR::Okay) { CopyMemory(buffer, Self->Buffer, len); Self->Size = len; } @@ -303,24 +303,24 @@ static ERROR FILE_BufferContent(extFile *Self, APTR Void) // the file content is treated as a string. BYTE *buffer; - if (!AllocMemory(Self->Size+1, MEM::NO_CLEAR, (APTR *)&buffer, NULL)) { + if (AllocMemory(Self->Size+1, MEM::NO_CLEAR, (APTR *)&buffer, NULL) IS ERR::Okay) { buffer[Self->Size] = 0; - if (!acRead(Self, buffer, Self->Size, &len)) { + if (acRead(Self, buffer, Self->Size, &len) IS ERR::Okay) { Self->Buffer = buffer; } else { FreeResource(buffer); - return log.warning(ERR_Read); + return log.warning(ERR::Read); } } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } // If the file was empty, allocate a 1-byte memory block for the Buffer field, in order to satisfy condition tests. if (!Self->Buffer) { - if (AllocMemory(1, MEM::DATA, (APTR *)&Self->Buffer, NULL) != ERR_Okay) { - return log.warning(ERR_AllocMemory); + if (AllocMemory(1, MEM::DATA, (APTR *)&Self->Buffer, NULL) != ERR::Okay) { + return log.warning(ERR::AllocMemory); } } @@ -330,7 +330,7 @@ static ERROR FILE_BufferContent(extFile *Self, APTR Void) Self->Handle = -1; Self->Position = 0; Self->Flags |= FL::BUFFER; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -342,11 +342,11 @@ Streaming data of any type to a file will result in the content being written to *********************************************************************************************************************/ -static ERROR FILE_DataFeed(extFile *Self, struct acDataFeed *Args) +static ERR FILE_DataFeed(extFile *Self, struct acDataFeed *Args) { pf::Log log; - if ((!Args) or (!Args->Buffer)) return log.warning(ERR_NullArgs); + if ((!Args) or (!Args->Buffer)) return log.warning(ERR::NullArgs); if (Args->Size) return acWrite(Self, Args->Buffer, Args->Size, NULL); else return acWrite(Self, Args->Buffer, StrLength((CSTRING)Args->Buffer), NULL); @@ -386,7 +386,7 @@ Loop: Performing the copy would cause infinite recursion. *********************************************************************************************************************/ -static ERROR FILE_Copy(extFile *Self, struct flCopy *Args) +static ERR FILE_Copy(extFile *Self, struct flCopy *Args) { return CopyFile(Self->Path, Args->Dest, Args->Callback); } @@ -415,11 +415,11 @@ BufferOverflow: The file path string is too long. *********************************************************************************************************************/ -static ERROR FILE_Delete(extFile *Self, struct flDelete *Args) +static ERR FILE_Delete(extFile *Self, struct flDelete *Args) { pf::Log log; - if ((!Self->Path) or (!*Self->Path)) return log.warning(ERR_MissingPath); + if ((!Self->Path) or (!*Self->Path)) return log.warning(ERR::MissingPath); if ((Self->Stream) and ((Self->Flags & FL::LINK) IS FL::NIL)) { log.branch("Delete Folder: %s", Self->Path); @@ -428,20 +428,20 @@ static ERROR FILE_Delete(extFile *Self, struct flDelete *Args) LONG len = StrLength(Self->Path); if (Self->Path[len-1] IS ':') { - if (!DeleteVolume(Self->Path)) { + if (DeleteVolume(Self->Path) IS ERR::Okay) { #ifdef __unix__ closedir((DIR *)Self->Stream); #endif Self->Stream = 0; - return ERR_Okay; + return ERR::Okay; } - else return ERR_DeleteFile; + else return ERR::DeleteFile; } // Delete the folder and its contents CSTRING path; - if (!GET_ResolvedPath(Self, &path)) { + if (GET_ResolvedPath(Self, &path) IS ERR::Okay) { char buffer[512]; #ifdef __unix__ @@ -459,19 +459,19 @@ static ERROR FILE_Delete(extFile *Self, struct flDelete *Args) fb.Path = buffer; } - ERROR error; - if (!(error = delete_tree(buffer, sizeof(buffer), Args->Callback, &fb))); - else if (error != ERR_Cancelled) log.warning("Failed to delete folder \"%s\"", buffer); + ERR error; + if ((error = delete_tree(buffer, sizeof(buffer), Args->Callback, &fb)) IS ERR::Okay); + else if (error != ERR::Cancelled) log.warning("Failed to delete folder \"%s\"", buffer); return error; } - else return log.warning(ERR_ResolvePath); + else return log.warning(ERR::ResolvePath); } else { log.branch("Delete File: %s", Self->Path); CSTRING path; - if (!GET_ResolvedPath(Self, &path)) { + if (GET_ResolvedPath(Self, &path) IS ERR::Okay) { char buffer[512]; LONG len = StrCopy(path, buffer, sizeof(buffer)); if ((buffer[len-1] IS '/') or (buffer[len-1] IS '\\')) buffer[len-1] = 0; @@ -480,19 +480,19 @@ static ERROR FILE_Delete(extFile *Self, struct flDelete *Args) // Unlinking the file deletes it - if (!unlink(buffer)) return ERR_Okay; + if (!unlink(buffer)) return ERR::Okay; else { log.warning("unlink() failed on file \"%s\": %s", buffer, strerror(errno)); - return convert_errno(errno, ERR_Failed); + return convert_errno(errno, ERR::Failed); } } - else return log.warning(ERR_ResolvePath); + else return log.warning(ERR::ResolvePath); } } //******************************************************************************************************************** -static ERROR FILE_Free(extFile *Self, APTR Void) +static ERR FILE_Free(extFile *Self, APTR Void) { pf::Log log; @@ -539,7 +539,7 @@ static ERROR FILE_Free(extFile *Self, APTR Void) } #endif - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -576,11 +576,11 @@ NoPermission: Permission was denied when accessing or creating the file. *********************************************************************************************************************/ -static ERROR FILE_Init(extFile *Self, APTR Void) +static ERR FILE_Init(extFile *Self, APTR Void) { pf::Log log; LONG len; - ERROR error; + ERR error; // If the BUFFER flag is set then the file will be located in RAM. Very little initialisation is needed for this. // If a path has been specified, we'll load the entire file into memory. Please see the end of this @@ -593,30 +593,30 @@ static ERROR FILE_Init(extFile *Self, APTR Void) // Allocate buffer if none specified. An extra byte is allocated for a NULL byte on the end, in case the file // content is treated as a string. - if (AllocMemory((Self->Size < 1) ? 1 : Self->Size+1, MEM::NO_CLEAR, (APTR *)&Self->Buffer, NULL) != ERR_Okay) { - return log.warning(ERR_AllocMemory); + if (AllocMemory((Self->Size < 1) ? 1 : Self->Size+1, MEM::NO_CLEAR, (APTR *)&Self->Buffer, NULL) != ERR::Okay) { + return log.warning(ERR::AllocMemory); } ((BYTE *)Self->Buffer)[Self->Size] = 0; } - return ERR_Okay; + return ERR::Okay; } - if (!Self->Path) return log.warning(ERR_MissingPath); + if (!Self->Path) return log.warning(ERR::MissingPath); if (glDefaultPermissions != PERMIT::NIL) Self->Permissions = glDefaultPermissions; - if (!StrCompare("string:", Self->Path, 7)) { + if (StrCompare("string:", Self->Path, 7) IS ERR::Okay) { Self->Size = StrLength(Self->Path + 7); if (Self->Size > 0) { - if (!AllocMemory(Self->Size, MEM::DATA, (APTR *)&Self->Buffer, NULL)) { + if (AllocMemory(Self->Size, MEM::DATA, (APTR *)&Self->Buffer, NULL) IS ERR::Okay) { Self->Flags |= FL::READ|FL::WRITE; CopyMemory(Self->Path + 7, Self->Buffer, Self->Size); - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } - else return log.warning(ERR_Failed); + else return log.warning(ERR::Failed); } if ((Self->Permissions IS PERMIT::NIL) or ((Self->Permissions & PERMIT::INHERIT) != PERMIT::NIL)) { @@ -625,7 +625,7 @@ static ERROR FILE_Init(extFile *Self, APTR Void) // If the file already exists, pull the permissions from it. Otherwise use a default set of permissions (if // possible, inherit permissions from the file's folder). - if (((Self->Flags & FL::NEW) != FL::NIL) and (!get_file_info(Self->Path, &info, sizeof(info)))) { + if (((Self->Flags & FL::NEW) != FL::NIL) and (get_file_info(Self->Path, &info, sizeof(info)) IS ERR::Okay)) { log.msg("Using permissions of the original file."); Self->Permissions |= info.Permissions; } @@ -642,12 +642,12 @@ static ERROR FILE_Init(extFile *Self, APTR Void) // Do not do anything if the File is used as a static object in a script - if ((Self->Static) and ((!Self->Path) or (!Self->Path[0]))) return ERR_Okay; + if ((Self->Static) and ((!Self->Path) or (!Self->Path[0]))) return ERR::Okay; if (Self->Path[0] IS ':') { - if ((Self->Flags & FL::FILE) != FL::NIL) return log.warning(ERR_ExpectedFile); + if ((Self->Flags & FL::FILE) != FL::NIL) return log.warning(ERR::ExpectedFile); log.trace("Root folder initialised."); - return ERR_Okay; + return ERR::Okay; } // If the FL::FOLDER flag was set after the Path field was set, we may need to reset the Path field so @@ -656,37 +656,39 @@ static ERROR FILE_Init(extFile *Self, APTR Void) retrydir: if ((Self->Flags & FL::FOLDER) != FL::NIL) { LONG len = StrLength(Self->Path); - if (len > 512) return log.warning(ERR_BufferOverflow); + if (len > 512) return log.warning(ERR::BufferOverflow); if ((Self->Path[len-1] != '/') and (Self->Path[len-1] != '\\') and (Self->Path[len-1] != ':')) { std::string buffer(Self->Path, len); - if (Self->setPath(buffer.c_str()) != ERR_Okay) { - return log.warning(ERR_SetField); + if (Self->setPath(buffer.c_str()) != ERR::Okay) { + return log.warning(ERR::SetField); } } } if (Self->Stream) { log.trace("Folder stream already set."); - return ERR_Okay; + return ERR::Okay; } // Use RSF::CHECK_VIRTUAL to cause failure if the volume name is reserved by a support class. By doing this we can - // return ERR_UseSubClass and a support class can then initialise the file instead. + // return ERR::UseSubClass and a support class can then initialise the file instead. auto resolveflags = RSF::NIL; if ((Self->Flags & FL::NEW) != FL::NIL) resolveflags |= RSF::NO_FILE_CHECK; if ((Self->Flags & FL::APPROXIMATE) != FL::NIL) resolveflags |= RSF::APPROXIMATE; - if ((error = ResolvePath(Self->Path, resolveflags|RSF::CHECK_VIRTUAL, &Self->prvResolvedPath)) != ERR_Okay) { - if (error IS ERR_VirtualVolume) { + if (Self->prvResolvedPath) { FreeResource(Self->prvResolvedPath); Self->prvResolvedPath = NULL; } + + if ((error = ResolvePath(Self->Path, resolveflags|RSF::CHECK_VIRTUAL, &Self->prvResolvedPath)) != ERR::Okay) { + if (error IS ERR::VirtualVolume) { // For virtual volumes, update the path to ensure that the volume name is referenced in the path string. - // Then return ERR_UseSubClass to have support delegated to the correct File sub-class. - if (StrMatch(Self->Path, Self->prvResolvedPath) != ERR_Okay) { + // Then return ERR::UseSubClass to have support delegated to the correct File sub-class. + if (StrMatch(Self->Path, Self->prvResolvedPath) != ERR::Okay) { SET_Path(Self, Self->prvResolvedPath); } log.trace("ResolvePath() reports virtual volume, will delegate to sub-class..."); - return ERR_UseSubClass; + return ERR::UseSubClass; } else { // The file may path may actually be a folder. Add a / and retest to see if this is the case. @@ -697,7 +699,7 @@ static ERROR FILE_Init(extFile *Self, APTR Void) } log.msg("File not found \"%s\".", Self->Path); - return ERR_FileNotFound; + return ERR::FileNotFound; } } @@ -720,25 +722,25 @@ static ERROR FILE_Init(extFile *Self, APTR Void) #endif if (Self->prvType & STAT_FOLDER) { // Open the folder - if ((Self->Flags & FL::FILE) != FL::NIL) return log.warning(ERR_ExpectedFile); + if ((Self->Flags & FL::FILE) != FL::NIL) return log.warning(ERR::ExpectedFile); Self->Flags |= FL::FOLDER; acQuery(Self); #ifdef __unix__ - if ((Self->Stream = opendir(Self->prvResolvedPath))) return ERR_Okay; + if ((Self->Stream = opendir(Self->prvResolvedPath))) return ERR::Okay; #elif _WIN32 // Note: The CheckDiretoryExists() function does not return a true handle, just a code of 1 to indicate that the folder is present. - if ((Self->Stream = winCheckDirectoryExists(Self->prvResolvedPath))) return ERR_Okay; + if ((Self->Stream = winCheckDirectoryExists(Self->prvResolvedPath))) return ERR::Okay; #else #error Require folder open or folder marking code. #endif if ((Self->Flags & FL::NEW) != FL::NIL) { log.msg("Making dir \"%s\", Permissions: $%.8x", Self->prvResolvedPath, LONG(Self->Permissions)); - if (!CreateFolder(Self->prvResolvedPath, Self->Permissions)) { + if (CreateFolder(Self->prvResolvedPath, Self->Permissions) IS ERR::Okay) { #ifdef __unix__ if (!(Self->Stream = opendir(Self->prvResolvedPath))) { log.warning("Failed to open the folder after creating it."); @@ -751,13 +753,13 @@ static ERROR FILE_Init(extFile *Self, APTR Void) #error Require folder open or folder marking code. #endif - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_CreateFile); + else return log.warning(ERR::CreateFile); } else { log.warning("Could not open folder \"%s\", %s.", Self->prvResolvedPath, strerror(errno)); - return ERR_File; + return ERR::File; } } else { @@ -766,8 +768,8 @@ static ERROR FILE_Init(extFile *Self, APTR Void) // Automatically open the file if access is required on initialisation. if ((Self->Flags & (FL::NEW|FL::READ|FL::WRITE)) != FL::NIL) { - ERROR error = acActivate(Self); - if (!error) error = acQuery(Self); + ERR error = acActivate(Self); + if (error IS ERR::Okay) error = acQuery(Self); return error; } else return acQuery(Self); @@ -799,18 +801,18 @@ Failed *********************************************************************************************************************/ -static ERROR FILE_MoveFile(extFile *Self, struct flMove *Args) +static ERR FILE_MoveFile(extFile *Self, struct flMove *Args) { pf::Log log; - if ((!Args) or (!Args->Dest)) return log.warning(ERR_NullArgs); - if (!Self->Path) return log.warning(ERR_FieldNotSet); + if ((!Args) or (!Args->Dest)) return log.warning(ERR::NullArgs); + if (!Self->Path) return log.warning(ERR::FieldNotSet); STRING src = Self->Path; CSTRING dest = Args->Dest; LONG len = StrLength(dest); - if (len <= 1) return log.warning(ERR_Args); + if (len <= 1) return log.warning(ERR::Args); log.msg("%s to %s", src, dest); @@ -820,7 +822,7 @@ static ERROR FILE_MoveFile(extFile *Self, struct flMove *Args) LONG i = StrLength(src) - 1; if (src[i] IS ':') { log.warning("Moving volumes is illegal."); - return ERR_Failed; + return ERR::Failed; } else if ((src[i] IS '/') or (src[i] IS '\\')) i--; @@ -830,7 +832,7 @@ static ERROR FILE_MoveFile(extFile *Self, struct flMove *Args) } STRING newpath; - if (!AllocMemory(len + 1, MEM::STRING|MEM::NO_CLEAR, (APTR *)&newpath, NULL)) { + if (AllocMemory(len + 1, MEM::STRING|MEM::NO_CLEAR, (APTR *)&newpath, NULL) IS ERR::Okay) { LONG j = StrCopy(dest, newpath); i++; while ((src[i]) and (src[i] != '/') and (src[i] != '\\')) newpath[j++] = src[i++]; @@ -840,8 +842,8 @@ static ERROR FILE_MoveFile(extFile *Self, struct flMove *Args) if (Self->Handle != -1) { close(Self->Handle); Self->Handle = -1; } #endif - ERROR error; - if (!(error = fs_copy(src, newpath, Args->Callback, TRUE))) { + ERR error; + if ((error = fs_copy(src, newpath, Args->Callback, TRUE)) IS ERR::Okay) { FreeResource(Self->Path); Self->Path = newpath; } @@ -851,39 +853,38 @@ static ERROR FILE_MoveFile(extFile *Self, struct flMove *Args) } return error; } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } else { STRING newpath; - if (!AllocMemory(len+1, MEM::STRING|MEM::NO_CLEAR, (APTR *)&newpath, NULL)) { + if (AllocMemory(len+1, MEM::STRING|MEM::NO_CLEAR, (APTR *)&newpath, NULL) IS ERR::Okay) { CopyMemory(dest, newpath, len+1); #ifdef _WIN32 if (Self->Handle != -1) { close(Self->Handle); Self->Handle = -1; } #endif - ERROR error; - if (!(error = fs_copy(src, newpath, Args->Callback, TRUE))) { + if (auto error = fs_copy(src, newpath, Args->Callback, TRUE); error IS ERR::Okay) { FreeResource(Self->Path); Self->Path = newpath; - return ERR_Okay; + return ERR::Okay; } else { FreeResource(newpath); return log.warning(error); } } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } } //******************************************************************************************************************** -static ERROR FILE_NewObject(extFile *Self, APTR Void) +static ERR FILE_NewObject(extFile *Self, APTR Void) { Self->Handle = -1; Self->Permissions = PERMIT::READ|PERMIT::WRITE|PERMIT::GROUP_READ|PERMIT::GROUP_WRITE; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -913,12 +914,12 @@ DirEmpty: The index has reached the end of the file list. *********************************************************************************************************************/ -static ERROR FILE_NextFile(extFile *Self, struct flNext *Args) +static ERR FILE_NextFile(extFile *Self, struct flNext *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); - if ((Self->Flags & FL::FOLDER) IS FL::NIL) return log.warning(ERR_ExpectedFolder); + if (!Args) return log.warning(ERR::NullArgs); + if ((Self->Flags & FL::FOLDER) IS FL::NIL) return log.warning(ERR::ExpectedFolder); if (!Self->prvList) { auto flags = RDF::QUALIFY; @@ -927,19 +928,19 @@ static ERROR FILE_NextFile(extFile *Self, struct flNext *Args) else if ((Self->Flags & FL::EXCLUDE_FILES) != FL::NIL) flags |= RDF::FOLDER; else flags |= RDF::FILE|RDF::FOLDER; - if (auto error = OpenDir(Self->Path, flags, &Self->prvList)) return error; + if (auto error = OpenDir(Self->Path, flags, &Self->prvList); error != ERR::Okay) return error; } - ERROR error; - if (!(error = ScanDir(Self->prvList))) { + ERR error; + if ((error = ScanDir(Self->prvList)) IS ERR::Okay) { std::string path(Self->Path); path.append(Self->prvList->Info->Name); if (auto file = extFile::create::global(fl::Path(path))) { Args->File = file; - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_CreateObject); + else return log.warning(ERR::CreateObject); } else { // Automatically close the list in the event of an error and repurpose the return code. Subsequent @@ -957,12 +958,12 @@ Query: Read a file's meta information from source. -END- *********************************************************************************************************************/ -static ERROR FILE_Query(extFile *Self, APTR Void) +static ERR FILE_Query(extFile *Self, APTR Void) { #ifdef _WIN32 - return ERR_Okay; + return ERR::Okay; #else - return ERR_Okay; + return ERR::Okay; #endif } @@ -992,15 +993,15 @@ Failed: The file object refers to a folder, or the object is corrupt. *********************************************************************************************************************/ -static ERROR FILE_Read(extFile *Self, struct acRead *Args) +static ERR FILE_Read(extFile *Self, struct acRead *Args) { pf::Log log; - if ((!Args) or (!Args->Buffer)) return log.warning(ERR_NullArgs); - else if (Args->Length == 0) return ERR_Okay; - else if (Args->Length < 0) return ERR_OutOfRange; + if ((!Args) or (!Args->Buffer)) return log.warning(ERR::NullArgs); + else if (Args->Length == 0) return ERR::Okay; + else if (Args->Length < 0) return ERR::OutOfRange; - if ((Self->Flags & FL::READ) IS FL::NIL) return log.warning(ERR_FileReadFlag); + if ((Self->Flags & FL::READ) IS FL::NIL) return log.warning(ERR::FileReadFlag); if (Self->Buffer) { if ((Self->Flags & FL::LOOP) != FL::NIL) { @@ -1026,20 +1027,20 @@ static ERROR FILE_Read(extFile *Self, struct acRead *Args) Self->Position += Args->Length; */ Args->Result = Args->Length; - return ERR_Okay; + return ERR::Okay; } else { if (Self->Position + Args->Length > Self->Size) Args->Result = Self->Size - Self->Position; else Args->Result = Args->Length; CopyMemory(Self->Buffer + Self->Position, Args->Buffer, Args->Result); Self->Position += Args->Result; - return ERR_Okay; + return ERR::Okay; } } - if (Self->prvType & STAT_FOLDER) return log.warning(ERR_ExpectedFile); + if (Self->prvType & STAT_FOLDER) return log.warning(ERR::ExpectedFile); - if (Self->Handle IS -1) return ERR_NotInitialised; + if (Self->Handle IS -1) return ERR::NotInitialised; Args->Result = read(Self->Handle, Args->Buffer, (LONG)Args->Length); @@ -1047,18 +1048,18 @@ static ERROR FILE_Read(extFile *Self, struct acRead *Args) if (Args->Result IS -1) { log.msg("Failed to read %d bytes from the file.", Args->Length); Args->Result = 0; - return ERR_SystemCall; + return ERR::SystemCall; } - // Return ERR_Okay because even though not all data was read, this was not due to a failure. + // Return ERR::Okay because even though not all data was read, this was not due to a failure. log.trace("%d of the requested %d bytes were read from the file.", Args->Result, Args->Length); Self->Position += Args->Result; - return ERR_Okay; + return ERR::Okay; } else { Self->Position += Args->Result; - return ERR_Okay; + return ERR::Okay; } } @@ -1072,7 +1073,7 @@ increase the #Position field by the amount of bytes read from the file. You mus the #Flags field when you initialised the file, or the call will fail. The line buffer is managed internally, so there is no need for you to free the result string. This method returns -ERR_NoData when it runs out of information to read from the file. +ERR::NoData when it runs out of information to read from the file. -INPUT- &str Result: The resulting string is returned in this parameter. @@ -1088,12 +1089,12 @@ NoData: There is no more data left to read. *********************************************************************************************************************/ -static ERROR FILE_ReadLine(extFile *Self, struct flReadLine *Args) +static ERR FILE_ReadLine(extFile *Self, struct flReadLine *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); - if ((Self->Flags & FL::READ) IS FL::NIL) return log.warning(ERR_FileReadFlag); + if (!Args) return log.warning(ERR::NullArgs); + if ((Self->Flags & FL::READ) IS FL::NIL) return log.warning(ERR::FileReadFlag); LONG len; char line[4096]; @@ -1110,8 +1111,8 @@ static ERROR FILE_ReadLine(extFile *Self, struct flReadLine *Args) Self->Position = i; } else { - if (Self->prvType & STAT_FOLDER) return log.warning(ERR_ExpectedFile); - if (Self->Handle IS -1) return log.warning(ERR_ObjectCorrupt); + if (Self->prvType & STAT_FOLDER) return log.warning(ERR::ExpectedFile); + if (Self->Handle IS -1) return log.warning(ERR::ObjectCorrupt); // Read the line @@ -1123,7 +1124,7 @@ static ERROR FILE_ReadLine(extFile *Self, struct flReadLine *Args) if (line[len] IS '\n') break; if (++len >= (LONG)sizeof(line)) { // Buffer overflow lseek64(Self->Handle, Self->Position, SEEK_SET); // Reset the file position back to normal - return log.warning(ERR_BufferOverflow); + return log.warning(ERR::BufferOverflow); } } if (line[len] IS '\n') break; @@ -1141,19 +1142,19 @@ static ERROR FILE_ReadLine(extFile *Self, struct flReadLine *Args) line[len] = 0; } - if (Self->Position IS pos) return ERR_NoData; + if (Self->Position IS pos) return ERR::NoData; if (Self->prvLineLen >= len+1) { CopyMemory(line, Self->prvLine, len+1); Args->Result = Self->prvLine; - return ERR_Okay; + return ERR::Okay; } else { if (Self->prvLine) { FreeResource(Self->prvLine); Self->prvLine = NULL; } Self->prvLine = StrClone(line); Self->prvLineLen = len + 1; Args->Result = Self->prvLine; - return ERR_Okay; + return ERR::Okay; } } @@ -1163,16 +1164,16 @@ Rename: Changes the name of a file. -END- *********************************************************************************************************************/ -static ERROR FILE_Rename(extFile *Self, struct acRename *Args) +static ERR FILE_Rename(extFile *Self, struct acRename *Args) { pf::Log log; LONG j; STRING n; - if ((!Args) or (!Args->Name)) return log.warning(ERR_NullArgs); + if ((!Args) or (!Args->Name)) return log.warning(ERR::NullArgs); LONG namelen = StrLength(Args->Name); - if (!namelen) return log.warning(ERR_NullArgs); - if (!Self->Path) return log.warning(ERR_FieldNotSet); + if (!namelen) return log.warning(ERR::NullArgs); + if (!Self->Path) return log.warning(ERR::FieldNotSet); log.branch("%s to %s", Self->Path, Args->Name); @@ -1180,54 +1181,54 @@ static ERROR FILE_Rename(extFile *Self, struct acRename *Args) if ((Self->prvType & STAT_FOLDER) or ((Self->Flags & FL::FOLDER) != FL::NIL)) { if (Self->Path[i-1] IS ':') { // Renaming a volume - if (!AllocMemory(namelen+2, MEM::STRING, (APTR *)&n, NULL)) { + if (AllocMemory(namelen+2, MEM::STRING, (APTR *)&n, NULL) IS ERR::Okay) { for (i=0; (Args->Name[i]) and (Args->Name[i] != ':') and (Args->Name[i] != '/') and (Args->Name[i] != '\\'); i++) n[i] = Args->Name[i]; n[i] = 0; - if (!RenameVolume(Self->Path, n)) { + if (RenameVolume(Self->Path, n) IS ERR::Okay) { n[i++] = ':'; n[i++] = 0; FreeResource(Self->Path); Self->Path = n; - return ERR_Okay; + return ERR::Okay; } else { FreeResource(n); - return log.warning(ERR_Failed); + return log.warning(ERR::Failed); } } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } else { // We are renaming a folder for (--i; (i > 0) and (Self->Path[i-1] != ':') and (Self->Path[i-1] != '/') and (Self->Path[i-1] != '\\'); i--); - if (!AllocMemory(i+namelen+2, MEM::STRING, (APTR *)&n, NULL)) { + if (AllocMemory(i+namelen+2, MEM::STRING, (APTR *)&n, NULL) IS ERR::Okay) { for (j=0; j < i; j++) n[j] = Self->Path[j]; for (i=0; (Args->Name[i]) and (Args->Name[i] != '/') and (Args->Name[i] != '\\') and (Args->Name[i] != ':'); i++) { n[j++] = Args->Name[i]; } - if (!fs_copy(Self->Path, n, NULL, TRUE)) { + if (fs_copy(Self->Path, n, NULL, TRUE) IS ERR::Okay) { // Add the trailing slash if (n[j-1] != '/') n[j++] = '/'; n[j] = 0; FreeResource(Self->Path); Self->Path = n; - return ERR_Okay; + return ERR::Okay; } else { FreeResource(n); - return log.warning(ERR_Failed); + return log.warning(ERR::Failed); } } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } } else { // We are renaming a file while ((i > 0) and (Self->Path[i-1] != ':') and (Self->Path[i-1] != '/') and (Self->Path[i-1] != '\\')) i--; - if (!AllocMemory(i+namelen+1, MEM::STRING, (APTR *)&n, NULL)) { + if (AllocMemory(i+namelen+1, MEM::STRING, (APTR *)&n, NULL) IS ERR::Okay) { // Generate the new path, then rename the file for (j=0; j < i; j++) n[j] = Self->Path[j]; @@ -1241,17 +1242,17 @@ static ERROR FILE_Rename(extFile *Self, struct acRename *Args) if (Self->Handle != -1) { close(Self->Handle); Self->Handle = -1; } #endif - if (!fs_copy(Self->Path, n, NULL, TRUE)) { + if (fs_copy(Self->Path, n, NULL, TRUE) IS ERR::Okay) { FreeResource(Self->Path); Self->Path = n; - return ERR_Okay; + return ERR::Okay; } else { FreeResource(n); - return log.warning(ERR_Failed); + return log.warning(ERR::Failed); } } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } } @@ -1261,13 +1262,13 @@ Reset: If the file represents a folder, the file list index is reset by this act -END- *********************************************************************************************************************/ -static ERROR FILE_Reset(extFile *Self, APTR Void) +static ERR FILE_Reset(extFile *Self, APTR Void) { if ((Self->Flags & FL::FOLDER) != FL::NIL) { if (Self->prvList) { FreeResource(Self->prvList); Self->prvList = NULL; } } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1276,7 +1277,7 @@ Seek: Seeks to a new read/write position within a file. -END- *********************************************************************************************************************/ -static ERROR FILE_Seek(extFile *Self, struct acSeek *Args) +static ERR FILE_Seek(extFile *Self, struct acSeek *Args) { pf::Log log; @@ -1288,35 +1289,33 @@ static ERROR FILE_Seek(extFile *Self, struct acSeek *Args) Self->Position = (LARGE)Args->Offset; } else if (Args->Position IS SEEK::END) { - LARGE filesize; - Self->get(FID_Size, &filesize); - Self->Position = filesize - (LARGE)Args->Offset; + Self->Position = Self->get(FID_Size) - (LARGE)Args->Offset; } else if (Args->Position IS SEEK::CURRENT) { Self->Position = Self->Position + (LARGE)Args->Offset; } - else return log.warning(ERR_Args); + else return log.warning(ERR::Args); // Make sure we are greater than zero, otherwise set as zero if (Self->Position < 0) Self->Position = 0; if (Self->Buffer) { - if ((Self->Flags & FL::LOOP) != FL::NIL) return ERR_Okay; // In loop mode, the position marker can legally be above the buffer size + if ((Self->Flags & FL::LOOP) != FL::NIL) return ERR::Okay; // In loop mode, the position marker can legally be above the buffer size else if (Self->Position > Self->Size) Self->Position = Self->Size; - return ERR_Okay; + return ERR::Okay; } - if (Self->Handle IS -1) return log.warning(ERR_ObjectCorrupt); + if (Self->Handle IS -1) return log.warning(ERR::ObjectCorrupt); LARGE ret; if ((ret = lseek64(Self->Handle, Self->Position, SEEK_SET)) != Self->Position) { log.warning("Failed to Seek to new position of %" PF64 " (return %" PF64 ").", Self->Position, ret); Self->Position = oldpos; - return ERR_SystemCall; + return ERR::SystemCall; } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1333,7 +1332,7 @@ and the date it was last archived (backed up). The following types are supporte -If the specified datestamp is not supported by the filesystem, ERR_NoSupport is returned by this method. +If the specified datestamp is not supported by the filesystem, ERR::NoSupport is returned by this method. -INPUT- int Year: Year (-ve for BC, +ve for AD). @@ -1353,24 +1352,24 @@ NoSupport: The platform does not support file date setting. *********************************************************************************************************************/ -static ERROR FILE_SetDate(extFile *Self, struct flSetDate *Args) +static ERR FILE_SetDate(extFile *Self, struct flSetDate *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); log.msg("%d/%d/%d %.2d:%.2d:%.2d", Args->Day, Args->Month, Args->Year, Args->Hour, Args->Minute, Args->Second); #ifdef _WIN32 CSTRING path; - if (!GET_ResolvedPath(Self, &path)) { + if (GET_ResolvedPath(Self, &path) IS ERR::Okay) { if (winSetFileTime(path, Args->Year, Args->Month, Args->Day, Args->Hour, Args->Minute, Args->Second)) { Self->Flags |= FL::RESET_DATE; - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_SystemCall); + else return log.warning(ERR::SystemCall); } - else return ERR_ResolvePath; + else return ERR::ResolvePath; #elif __unix__ @@ -1394,19 +1393,19 @@ static ERROR FILE_SetDate(extFile *Self, struct flSetDate *Args) if (utimes(path, filetime) != -1) { Self->Flags |= FL::RESET_DATE; - return ERR_Okay; + return ERR::Okay; } else { log.warning("Failed to set the file date."); - return log.warning(ERR_SystemCall); + return log.warning(ERR::SystemCall); } } - else return log.warning(ERR_SystemCall); + else return log.warning(ERR::SystemCall); } - else return ERR_ResolvePath; + else return ERR::ResolvePath; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -1450,15 +1449,15 @@ NoSupport: The file is not streamed. *********************************************************************************************************************/ -static ERROR FILE_StartStream(extFile *Self, struct flStartStream *Args) +static ERR FILE_StartStream(extFile *Self, struct flStartStream *Args) { pf::Log log; - if ((!Args) or (!Args->SubscriberID)) return log.warning(ERR_NullArgs); + if ((!Args) or (!Args->SubscriberID)) return log.warning(ERR::NullArgs); // Streaming from standard files is pointless - it's the virtual drives that provide streaming features. - return ERR_NoSupport; + return ERR::NoSupport; } /********************************************************************************************************************* @@ -1476,9 +1475,9 @@ NoSupport: The file is not streamed. *********************************************************************************************************************/ -static ERROR FILE_StopStream(extFile *Self, APTR Void) +static ERR FILE_StopStream(extFile *Self, APTR Void) { - return ERR_NoSupport; + return ERR::NoSupport; } /********************************************************************************************************************* @@ -1496,13 +1495,13 @@ are supported as targets. The optional MFF Flags are used to filter events to those that are desired for monitoring. The client must provide a Callback that will be triggered when a monitored event is triggered. The Callback must -follow the format `ERROR Routine(*File, STRING Path, LARGE Custom, LONG Flags)` +follow the format `ERR Routine(*File, STRING Path, LARGE Custom, LONG Flags)` Each event will be delivered in the sequence that they are originally raised. The Flags parameter will reflect the specific event that has occurred. The Custom parameter is identical to the Custom argument originally passed to this method. The Path is a string that is relative to the File's #Path field. -If the callback routine returns ERR_Terminate, the watch will be disabled. It is also possible to disable an existing +If the callback routine returns ERR::Terminate, the watch will be disabled. It is also possible to disable an existing watch by calling this method with no parameters, or by setting the Flags parameter to 0. -INPUT- @@ -1517,7 +1516,7 @@ NullArgs *********************************************************************************************************************/ -static ERROR FILE_Watch(extFile *Self, struct flWatch *Args) +static ERR FILE_Watch(extFile *Self, struct flWatch *Args) { pf::Log log; @@ -1536,29 +1535,29 @@ static ERROR FILE_Watch(extFile *Self, struct flWatch *Args) Self->prvWatch = NULL; } - if ((!Args) or (!Args->Callback) or (Args->Flags IS MFF::NIL)) return ERR_Okay; + if ((!Args) or (!Args->Callback) or (Args->Flags IS MFF::NIL)) return ERR::Okay; #ifdef __linux__ // Initialise inotify if not done already. if (glInotify IS -1) { - ERROR error; + ERR error; if ((glInotify = inotify_init()) != -1) { fcntl(glInotify, F_SETFL, fcntl(glInotify, F_GETFL)|O_NONBLOCK); error = RegisterFD(glInotify, RFD::READ, (void (*)(HOSTHANDLE, APTR))path_monitor, NULL); } - else error = log.warning(ERR_SystemCall); + else error = log.warning(ERR::SystemCall); if (error) return error; } #endif CSTRING resolve; - ERROR error; - if (!(error = GET_ResolvedPath(Self, &resolve))) { + ERR error; + if ((error = GET_ResolvedPath(Self, &resolve)) IS ERR::Okay) { auto vd = get_fs(resolve); if (vd->WatchPath) { #ifdef _WIN32 - if (!AllocMemory(sizeof(rkWatchPath) + winGetWatchBufferSize(), MEM::DATA, (APTR *)&Self->prvWatch, NULL)) { + if (AllocMemory(sizeof(rkWatchPath) + winGetWatchBufferSize(), MEM::DATA, (APTR *)&Self->prvWatch, NULL) IS ERR::Okay) { #else if (!AllocMemory(sizeof(rkWatchPath), MEM::DATA, (APTR *)&Self->prvWatch, NULL)) { #endif @@ -1569,9 +1568,9 @@ static ERROR FILE_Watch(extFile *Self, struct flWatch *Args) error = vd->WatchPath(Self); } - else error = ERR_AllocMemory; + else error = ERR::AllocMemory; } - else error = ERR_NoSupport; + else error = ERR::NoSupport; } return error; @@ -1599,13 +1598,13 @@ LimitedSuccess: Only some of the data was written to the file. Check the Result *********************************************************************************************************************/ -static ERROR FILE_Write(extFile *Self, struct acWrite *Args) +static ERR FILE_Write(extFile *Self, struct acWrite *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); - if (Args->Length <= 0) return ERR_Args; - if ((Self->Flags & FL::WRITE) IS FL::NIL) return log.warning(ERR_FileWriteFlag); + if (!Args) return log.warning(ERR::NullArgs); + if (Args->Length <= 0) return ERR::Args; + if ((Self->Flags & FL::WRITE) IS FL::NIL) return log.warning(ERR::FileWriteFlag); if (Self->Buffer) { if ((Self->Flags & FL::LOOP) != FL::NIL) { @@ -1633,17 +1632,17 @@ static ERROR FILE_Write(extFile *Self, struct acWrite *Args) */ Args->Result = Args->Length; - return ERR_Okay; + return ERR::Okay; } else { if (Self->Position + Args->Length > Self->Size) { // Increase the size of the buffer to cater for the write. A null byte (not included in the official size) // is always placed at the end. - if (!ReallocMemory(Self->Buffer, Self->Position + Args->Length + 1, (APTR *)&Self->Buffer, NULL)) { + if (ReallocMemory(Self->Buffer, Self->Position + Args->Length + 1, (APTR *)&Self->Buffer, NULL) IS ERR::Okay) { Self->Size = Self->Position + Args->Length; Self->Buffer[Self->Size] = 0; } - else return log.warning(ERR_ReallocMemory); + else return log.warning(ERR::ReallocMemory); } Args->Result = Args->Length; @@ -1651,13 +1650,13 @@ static ERROR FILE_Write(extFile *Self, struct acWrite *Args) CopyMemory(Args->Buffer, Self->Buffer + Self->Position, Args->Result); Self->Position += Args->Result; - return ERR_Okay; + return ERR::Okay; } } - if ((Self->prvType & STAT_FOLDER) or ((Self->Flags & FL::FOLDER) != FL::NIL)) return log.warning(ERR_ExpectedFile); + if ((Self->prvType & STAT_FOLDER) or ((Self->Flags & FL::FOLDER) != FL::NIL)) return log.warning(ERR::ExpectedFile); - if (Self->Handle IS -1) return log.warning(ERR_ObjectCorrupt); + if (Self->Handle IS -1) return log.warning(ERR::ObjectCorrupt); // If no buffer was supplied then we will write out null values to a limit indicated by the Length field. @@ -1687,10 +1686,10 @@ static ERROR FILE_Write(extFile *Self, struct acWrite *Args) if (Args->Result != Args->Length) { log.msg("%d of the intended %d bytes were written to the file.", Args->Result, Args->Length); - return ERR_LimitedSuccess; + return ERR::LimitedSuccess; } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1703,11 +1702,11 @@ the address of that buffer. The size of the buffer will match the #Size field. *********************************************************************************************************************/ -static ERROR GET_Buffer(extFile *Self, APTR *Value, LONG *Elements) +static ERR GET_Buffer(extFile *Self, APTR *Value, LONG *Elements) { *Value = Self->Buffer; *Elements = Self->Size; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1724,7 +1723,7 @@ To simplify time management, information is read and set via a &DateTime structu *********************************************************************************************************************/ -static ERROR GET_Created(extFile *Self, DateTime **Value) +static ERR GET_Created(extFile *Self, DateTime **Value) { pf::Log log; @@ -1735,26 +1734,27 @@ static ERROR GET_Created(extFile *Self, DateTime **Value) if (!fstat64(Self->Handle, &stats)) { // Timestamp has to match that produced by fs_getinfo() - struct tm *local; - if ((local = localtime(&stats.st_mtime))) { - Self->prvCreated.Year = 1900 + local->tm_year; - Self->prvCreated.Month = local->tm_mon + 1; - Self->prvCreated.Day = local->tm_mday; - Self->prvCreated.Hour = local->tm_hour; - Self->prvCreated.Minute = local->tm_min; - Self->prvCreated.Second = local->tm_sec; + if (auto local = localtime(&stats.st_mtime)) { + Self->prvCreated = DateTime { + .Year = WORD(1900 + local->tm_year), + .Month = BYTE(local->tm_mon + 1), + .Day = BYTE(local->tm_mday), + .Hour = BYTE(local->tm_hour), + .Minute = BYTE(local->tm_min), + .Second = BYTE(local->tm_sec) + }; *Value = &Self->prvCreated; - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_SystemCall); + else return log.warning(ERR::SystemCall); } - else return log.warning(ERR_SystemCall); + else return log.warning(ERR::SystemCall); } else { CSTRING path; - ERROR error; - if (!GET_ResolvedPath(Self, &path)) { + ERR error; + if (GET_ResolvedPath(Self, &path) IS ERR::Okay) { char buffer[512]; LONG len = StrCopy(path, buffer, sizeof(buffer)); if ((buffer[len-1] IS '/') or (buffer[len-1] IS '\\')) buffer[len-1] = 0; @@ -1763,23 +1763,24 @@ static ERROR GET_Created(extFile *Self, DateTime **Value) if (!stat64(buffer, &stats)) { // Timestamp has to match that produced by fs_getinfo() - struct tm *local; - if ((local = localtime(&stats.st_mtime))) { - Self->prvCreated.Year = 1900 + local->tm_year; - Self->prvCreated.Month = local->tm_mon + 1; - Self->prvCreated.Day = local->tm_mday; - Self->prvCreated.Hour = local->tm_hour; - Self->prvCreated.Minute = local->tm_min; - Self->prvCreated.Second = local->tm_sec; + if (auto local = localtime(&stats.st_mtime)) { + Self->prvCreated = { + .Year = WORD(1900 + local->tm_year), + .Month = BYTE(local->tm_mon + 1), + .Day = BYTE(local->tm_mday), + .Hour = BYTE(local->tm_hour), + .Minute = BYTE(local->tm_min), + .Second = BYTE(local->tm_sec) + }; *Value = &Self->prvCreated; - error = ERR_Okay; + error = ERR::Okay; } - else error = log.warning(ERR_SystemCall); + else error = log.warning(ERR::SystemCall); } - else error = log.warning(ERR_SystemCall); + else error = log.warning(ERR::SystemCall); } - else error = log.warning(ERR_ResolvePath); + else error = log.warning(ERR::ResolvePath); return error; } @@ -1797,7 +1798,7 @@ Information is read and set using a standard &DateTime structure. *********************************************************************************************************************/ -static ERROR GET_Date(extFile *Self, DateTime **Value) +static ERR GET_Date(extFile *Self, DateTime **Value) { pf::Log log; @@ -1805,32 +1806,33 @@ static ERROR GET_Date(extFile *Self, DateTime **Value) if (Self->Handle != -1) { struct stat64 stats; - ERROR error; + ERR error; if (!fstat64(Self->Handle, &stats)) { // Timestamp has to match that produced by fs_getinfo() - struct tm *local; - if ((local = localtime(&stats.st_mtime))) { - Self->prvModified.Year = 1900 + local->tm_year; - Self->prvModified.Month = local->tm_mon + 1; - Self->prvModified.Day = local->tm_mday; - Self->prvModified.Hour = local->tm_hour; - Self->prvModified.Minute = local->tm_min; - Self->prvModified.Second = local->tm_sec; + if (auto local = localtime(&stats.st_mtime)) { + Self->prvModified = DateTime { + .Year = WORD(1900 + local->tm_year), + .Month = BYTE(local->tm_mon + 1), + .Day = BYTE(local->tm_mday), + .Hour = BYTE(local->tm_hour), + .Minute = BYTE(local->tm_min), + .Second = BYTE(local->tm_sec) + }; *Value = &Self->prvModified; - error = ERR_Okay; + error = ERR::Okay; } - else error = log.warning(ERR_SystemCall); + else error = log.warning(ERR::SystemCall); } - else error = log.warning(ERR_SystemCall); + else error = log.warning(ERR::SystemCall); return error; } else { CSTRING path; - ERROR error; - if (!GET_ResolvedPath(Self, &path)) { + ERR error; + if (GET_ResolvedPath(Self, &path) IS ERR::Okay) { char buffer[512]; LONG len = StrCopy(path, buffer, sizeof(buffer)); if ((buffer[len-1] IS '/') or (buffer[len-1] IS '\\')) buffer[len-1] = 0; @@ -1839,44 +1841,45 @@ static ERROR GET_Date(extFile *Self, DateTime **Value) if (!stat64(buffer, &stats)) { // Timestamp has to match that produced by fs_getinfo() - struct tm *local; - if ((local = localtime(&stats.st_mtime))) { - Self->prvModified.Year = 1900 + local->tm_year; - Self->prvModified.Month = local->tm_mon + 1; - Self->prvModified.Day = local->tm_mday; - Self->prvModified.Hour = local->tm_hour; - Self->prvModified.Minute = local->tm_min; - Self->prvModified.Second = local->tm_sec; + if (auto local = localtime(&stats.st_mtime)) { + Self->prvModified = DateTime { + .Year = WORD(1900 + local->tm_year), + .Month = BYTE(local->tm_mon + 1), + .Day = BYTE(local->tm_mday), + .Hour = BYTE(local->tm_hour), + .Minute = BYTE(local->tm_min), + .Second = BYTE(local->tm_sec) + }; *Value = &Self->prvModified; - error = ERR_Okay; + error = ERR::Okay; } - else error = log.warning(ERR_SystemCall); + else error = log.warning(ERR::SystemCall); } - else error = log.warning(ERR_SystemCall); + else error = log.warning(ERR::SystemCall); } - else error = log.warning(ERR_ResolvePath); + else error = log.warning(ERR::ResolvePath); return error; } } -ERROR SET_Date(extFile *Self, DateTime *Date) +ERR SET_Date(extFile *Self, DateTime *Date) { pf::Log log; - if (!Date) return log.warning(ERR_NullArgs); + if (!Date) return log.warning(ERR::NullArgs); #ifdef _WIN32 CSTRING path; - if (!GET_ResolvedPath(Self, &path)) { + if (GET_ResolvedPath(Self, &path) IS ERR::Okay) { if (winSetFileTime(path, Date->Year, Date->Month, Date->Day, Date->Hour, Date->Minute, Date->Second)) { Self->Flags |= FL::RESET_DATE; - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_SystemCall); + else return log.warning(ERR::SystemCall); } - else return log.warning(ERR_ResolvePath); + else return log.warning(ERR::ResolvePath); #elif __unix__ @@ -1901,16 +1904,16 @@ ERROR SET_Date(extFile *Self, DateTime *Date) if (utime(path, &utm) != -1) { Self->Flags |= FL::RESET_DATE; - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_SystemCall); + else return log.warning(ERR::SystemCall); } - else return log.warning(ERR_SystemCall); + else return log.warning(ERR::SystemCall); } - else return ERR_ResolvePath; + else return ERR::ResolvePath; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -1927,34 +1930,34 @@ case the ID has been changed after initialisation of the file object. You can also change the group ID of a file by writing an integer value to this field. -If the file system does not support group ID's, `ERR_NoSupport` is returned. +If the file system does not support group ID's, `ERR::NoSupport` is returned. *********************************************************************************************************************/ -static ERROR GET_Group(extFile *Self, LONG *Value) +static ERR GET_Group(extFile *Self, LONG *Value) { #ifdef __unix__ struct stat64 info; - if (fstat64(Self->Handle, &info) IS -1) return ERR_FileNotFound; + if (fstat64(Self->Handle, &info) IS -1) return ERR::FileNotFound; *Value = info.st_gid; - return ERR_Okay; + return ERR::Okay; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } -static ERROR SET_Group(extFile *Self, LONG Value) +static ERR SET_Group(extFile *Self, LONG Value) { #ifdef __unix__ pf::Log log; if (Self->initialised()) { log.msg("Changing group to #%d", Value); - if (!fchown(Self->Handle, -1, Value)) return ERR_Okay; - else return log.warning(convert_errno(errno, ERR_Failed)); + if (!fchown(Self->Handle, -1, Value)) return ERR::Okay; + else return log.warning(convert_errno(errno, ERR::Failed)); } - else return log.warning(ERR_NotInitialised); + else return log.warning(ERR::NotInitialised); #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -1968,10 +1971,10 @@ is returned as a 64-bit integer. *********************************************************************************************************************/ -static ERROR GET_Handle(extFile *Self, LARGE *Value) +static ERR GET_Handle(extFile *Self, LARGE *Value) { *Value = Self->Handle; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1985,18 +1988,18 @@ The resulting string is returned in the format `icons:category/name` and can be *********************************************************************************************************************/ -static ERROR GET_Icon(extFile *Self, CSTRING *Value) +static ERR GET_Icon(extFile *Self, CSTRING *Value) { if (Self->prvIcon) { *Value = Self->prvIcon; - return ERR_Okay; + return ERR::Okay; } pf::SwitchContext context(Self); if ((!Self->Path) or (!Self->Path[0])) { *Value = Self->prvIcon = StrClone("icons:filetypes/empty"); - return ERR_Okay; + return ERR::Okay; } // If the location is a volume, look the icon up in the SystemVolumes object @@ -2016,23 +2019,23 @@ static ERROR GET_Icon(extFile *Self, CSTRING *Value) } *Value = Self->prvIcon = StrClone(icon.c_str()); - return ERR_Okay; + return ERR::Okay; } FileInfo info; bool link = false; - if (!get_file_info(Self->Path, &info, sizeof(info))) { + if (get_file_info(Self->Path, &info, sizeof(info)) IS ERR::Okay) { if ((info.Flags & RDF::LINK) != RDF::NIL) link = true; if ((info.Flags & RDF::VIRTUAL) != RDF::NIL) { // Virtual drives can specify custom icons, even for folders *Value = Self->prvIcon = info.Tags[0]["Icon"].c_str(); - if (*Value) return ERR_Okay; + if (*Value) return ERR::Okay; } if ((info.Flags & RDF::FOLDER) != RDF::NIL) { if (link) *Value = Self->prvIcon = StrClone("icons:folders/folder_shortcut"); else *Value = Self->prvIcon = StrClone("icons:folders/folder"); - return ERR_Okay; + return ERR::Okay; } } @@ -2040,23 +2043,23 @@ static ERROR GET_Icon(extFile *Self, CSTRING *Value) if ((Self->Path[i-1] IS '/') or (Self->Path[i-1] IS '\\')) { if (link) *Value = Self->prvIcon = StrClone("icons:folders/folder_shortcut"); else *Value = Self->prvIcon = StrClone("icons:folders/folder"); - return ERR_Okay; + return ERR::Okay; } // Load the file association data files. Information is merged between the global association file and the user's // personal association file. if (!glDatatypes) { - if (load_datatypes() != ERR_Okay) { + if (load_datatypes() != ERR::Okay) { if (link) *Value = Self->prvIcon = StrClone("icons:filetypes/empty_shortcut"); else *Value = Self->prvIcon = StrClone("icons:filetypes/empty"); - return ERR_Okay; + return ERR::Okay; } } ConfigGroups *groups; char icon[80] = ""; - if (!glDatatypes->getPtr(FID_Data, &groups)) { + if (glDatatypes->getPtr(FID_Data, &groups) IS ERR::Okay) { // Scan file extensions first, because this saves us from having to open and read the file content. LONG k; @@ -2065,7 +2068,7 @@ static ERROR GET_Icon(extFile *Self, CSTRING *Value) if (Self->Path[k]) { for (auto& [group, keys] : groups[0]) { if (keys.contains("Match")) { - if (!StrCompare(keys["Match"].c_str(), Self->Path+k, 0, STR::WILDCARD)) { + if (StrCompare(keys["Match"].c_str(), Self->Path+k, 0, STR::WILDCARD) IS ERR::Okay) { if (keys.contains("Icon")) { StrCopy(keys["Icon"].c_str(), icon, sizeof(icon)); break; @@ -2081,7 +2084,7 @@ static ERROR GET_Icon(extFile *Self, CSTRING *Value) std::string subclass, baseclass; CLASSID class_id, subclass_id; - if (!IdentifyFile(Self->Path, &class_id, &subclass_id)) { + if (IdentifyFile(Self->Path, &class_id, &subclass_id) IS ERR::Okay) { if (glClassDB.contains(subclass_id)) { subclass = glClassDB[subclass_id].Name; } @@ -2096,11 +2099,11 @@ static ERROR GET_Icon(extFile *Self, CSTRING *Value) if ((!subclass.empty()) or (!baseclass.empty())) { for (auto& [group, keys] : groups[0]) { if (keys.contains("Class")) { - if (!StrMatch(keys["Class"].c_str(), subclass.c_str())) { + if (StrMatch(keys["Class"].c_str(), subclass.c_str()) IS ERR::Okay) { if (keys.contains("Icon")) StrCopy(keys["Icon"].c_str(), icon, sizeof(icon)); break; } - else if (!StrMatch(keys["Class"].c_str(), baseclass.c_str())) { + else if (StrMatch(keys["Class"].c_str(), baseclass.c_str()) IS ERR::Okay) { if (keys.contains("Icon")) StrCopy(keys["Icon"].c_str(), icon, sizeof(icon)); // Don't break as sub-class would have priority } @@ -2113,16 +2116,16 @@ static ERROR GET_Icon(extFile *Self, CSTRING *Value) if (!icon[0]) { if (link) *Value = Self->prvIcon = StrClone("icons:filetypes/empty_shortcut"); else *Value = Self->prvIcon = StrClone("icons:filetypes/empty"); - return ERR_Okay; + return ERR::Okay; } - if (StrCompare("icons:", icon, 6) != ERR_Okay) { + if (StrCompare("icons:", icon, 6) != ERR::Okay) { CopyMemory(icon, icon+6, sizeof(icon) - 6); for (LONG i=0; i < 6; i++) icon[i] = "icons:"[i]; } *Value = Self->prvIcon = StrClone(icon); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2135,7 +2138,7 @@ folder containing the link will need to be taken into consideration when calcula *********************************************************************************************************************/ -static ERROR GET_Link(extFile *Self, STRING *Value) +static ERR GET_Link(extFile *Self, STRING *Value) { #ifdef __unix__ pf::Log log; @@ -2144,7 +2147,7 @@ static ERROR GET_Link(extFile *Self, STRING *Value) if (Self->prvLink) { // The link has already been read previously, just re-use it *Value = Self->prvLink; - return ERR_Okay; + return ERR::Okay; } *Value = NULL; @@ -2159,24 +2162,24 @@ static ERROR GET_Link(extFile *Self, STRING *Value) } FreeResource(path); - if (*Value) return ERR_Okay; - else return ERR_Failed; + if (*Value) return ERR::Okay; + else return ERR::Failed; } - else return ERR_ResolvePath; + else return ERR::ResolvePath; } - return ERR_Failed; + return ERR::Failed; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } -static ERROR SET_Link(extFile *Self, STRING Value) +static ERR SET_Link(extFile *Self, STRING Value) { #ifdef __unix__ //symlink(). #endif - return ERR_NoSupport; + return ERR::NoSupport; } /********************************************************************************************************************* @@ -2197,23 +2200,23 @@ to traverse the folder hierarchy. *********************************************************************************************************************/ -static ERROR GET_Path(extFile *Self, STRING *Value) +static ERR GET_Path(extFile *Self, STRING *Value) { if (Self->Path) { *Value = Self->Path; - return ERR_Okay; + return ERR::Okay; } else { *Value = NULL; - return ERR_FieldNotSet; + return ERR::FieldNotSet; } } -static ERROR SET_Path(extFile *Self, CSTRING Value) +static ERR SET_Path(extFile *Self, CSTRING Value) { pf::Log log; - if (Self->initialised()) return log.warning(ERR_Immutable); + if (Self->initialised()) return log.warning(ERR::Immutable); if (Self->Stream) { #ifdef __unix__ @@ -2230,13 +2233,13 @@ static ERROR SET_Path(extFile *Self, CSTRING Value) LONG i, j, len; if ((Value) and (*Value)) { - if (StrCompare("string:", Value, 7) != ERR_Okay) { + if (StrCompare("string:", Value, 7) != ERR::Okay) { for (len=0; (Value[len]) and (Value[len] != '|'); len++); } else len = StrLength(Value); // Note: An extra byte is allocated in case the FL::FOLDER flag is set - if (!AllocMemory(len+2, MEM::STRING|MEM::NO_CLEAR, (APTR *)&Self->Path, NULL)) { + if (AllocMemory(len+2, MEM::STRING|MEM::NO_CLEAR, (APTR *)&Self->Path, NULL) IS ERR::Okay) { // If the path is set to ':' then this is the equivalent of asking for a folder list of all volumes in // the system. No further initialisation is necessary in such a case. @@ -2250,7 +2253,7 @@ static ERROR SET_Path(extFile *Self, CSTRING Value) // e.g. "drive1:documents//tutorials/" for (j=0; Value[j] IS ':'; j++); - if (!StrCompare("string:", Value, 7)) { + if (StrCompare("string:", Value, 7) IS ERR::Okay) { i = StrCopy(Value, Self->Path); } else { @@ -2291,11 +2294,11 @@ static ERROR SET_Path(extFile *Self, CSTRING Value) } } } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } if (Self->prvResolvedPath) { FreeResource(Self->prvResolvedPath); Self->prvResolvedPath = NULL; } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2305,7 +2308,7 @@ Lookup: PERMIT -END- *********************************************************************************************************************/ -static ERROR GET_Permissions(extFile *Self, PERMIT *Value) +static ERR GET_Permissions(extFile *Self, PERMIT *Value) { pf::Log log; @@ -2328,45 +2331,45 @@ static ERROR GET_Permissions(extFile *Self, PERMIT *Value) if (fstat64(Self->Handle, &info) != -1) { Self->Permissions |= convert_fs_permissions(info.st_mode); } - else return convert_errno(errno, ERR_SystemCall); + else return convert_errno(errno, ERR::SystemCall); } else if (Self->Stream) { struct stat64 info; if (stat64(path, &info) != -1) Self->Permissions |= convert_fs_permissions(info.st_mode); - else return convert_errno(errno, ERR_SystemCall); + else return convert_errno(errno, ERR::SystemCall); } *Value = Self->Permissions; - return ERR_Okay; + return ERR::Okay; } - else return ERR_ResolvePath; + else return ERR::ResolvePath; #elif _WIN32 CSTRING path; - if (!GET_ResolvedPath(Self, &path)) { + if (GET_ResolvedPath(Self, &path) IS ERR::Okay) { winGetAttrib(path, (LONG *)(Value)); // Supports PERMIT::HIDDEN/ARCHIVE/OFFLINE/READ/WRITE - return ERR_Okay; + return ERR::Okay; } - else return ERR_ResolvePath; + else return ERR::ResolvePath; #endif - return ERR_NoSupport; + return ERR::NoSupport; } -static ERROR SET_Permissions(extFile *Self, PERMIT Value) +static ERR SET_Permissions(extFile *Self, PERMIT Value) { if (!Self->initialised()) { Self->Permissions = Value; - return ERR_Okay; + return ERR::Okay; } else return set_permissions(Self, Value); } //******************************************************************************************************************** -static ERROR set_permissions(extFile *Self, PERMIT Permissions) +static ERR set_permissions(extFile *Self, PERMIT Permissions) { pf::Log log(__FUNCTION__); #ifdef __unix__ @@ -2397,9 +2400,9 @@ static ERROR set_permissions(extFile *Self, PERMIT Permissions) if (err != -1) { Self->Permissions = Permissions; - return ERR_Okay; + return ERR::Okay; } - else return convert_errno(errno, ERR_SystemCall); + else return convert_errno(errno, ERR::SystemCall); } else if (Self->Stream) { // File represents a folder @@ -2424,30 +2427,30 @@ static ERROR set_permissions(extFile *Self, PERMIT Permissions) if (chmod(path, flags) != -1) { Self->Permissions = Permissions; - return ERR_Okay; + return ERR::Okay; } - else return log.warning(convert_errno(errno, ERR_SystemCall)); + else return log.warning(convert_errno(errno, ERR::SystemCall)); } - else return log.warning(ERR_ResolvePath); + else return log.warning(ERR::ResolvePath); } - else return log.warning(ERR_InvalidHandle); + else return log.warning(ERR::InvalidHandle); #elif _WIN32 log.branch("$%.8x", LONG(Permissions)); CSTRING path; - if (!GET_ResolvedPath(Self, &path)) { - ERROR error; - if (winSetAttrib(path, LONG(Permissions))) error = log.warning(ERR_Failed); - else error = ERR_Okay; + if (GET_ResolvedPath(Self, &path) IS ERR::Okay) { + ERR error; + if (winSetAttrib(path, LONG(Permissions))) error = log.warning(ERR::Failed); + else error = ERR::Okay; return error; } - else return log.warning(ERR_ResolvePath); + else return log.warning(ERR::ResolvePath); #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -2463,14 +2466,14 @@ The Position will always remain at zero if the file object represents a folder. *********************************************************************************************************************/ -static ERROR SET_Position(extFile *Self, LARGE Value) +static ERR SET_Position(extFile *Self, LARGE Value) { if (Self->initialised()) { return acSeekStart(Self, Value); } else { Self->Position = Value; - return ERR_Okay; + return ERR::Okay; } } @@ -2483,22 +2486,21 @@ to the host platform. Please refer to the ~ResolvePath() function for further i *********************************************************************************************************************/ -static ERROR GET_ResolvedPath(extFile *Self, CSTRING *Value) +static ERR GET_ResolvedPath(extFile *Self, CSTRING *Value) { - if (!Self->Path) return ERR_FieldNotSet; + if (!Self->Path) return ERR::FieldNotSet; if (!Self->prvResolvedPath) { auto flags = ((Self->Flags & FL::APPROXIMATE) != FL::NIL) ? RSF::APPROXIMATE : RSF::NO_FILE_CHECK; - ERROR error; pf::SwitchContext ctx(Self); - if ((error = ResolvePath(Self->Path, flags, &Self->prvResolvedPath)) != ERR_Okay) { - return ERR_ResolvePath; + if (ResolvePath(Self->Path, flags, &Self->prvResolvedPath) != ERR::Okay) { + return ERR::ResolvePath; } } *Value = Self->prvResolvedPath; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2511,78 +2513,77 @@ position being set to the end of the file. *********************************************************************************************************************/ -static ERROR GET_Size(extFile *Self, LARGE *Size) +static ERR GET_Size(extFile *Self, LARGE *Size) { pf::Log log; if ((Self->Flags & FL::FOLDER) != FL::NIL) { *Size = 0; - return ERR_Okay; + return ERR::Okay; } else if (Self->Handle != -1) { struct stat64 stats; if (!fstat64(Self->Handle, &stats)) { *Size = stats.st_size; - return ERR_Okay; + return ERR::Okay; } - else return convert_errno(errno, ERR_SystemCall); + else return convert_errno(errno, ERR::SystemCall); } else if (Self->Buffer) { *Size = Self->Size; - return ERR_Okay; + return ERR::Okay; } CSTRING path; - ERROR error; - if (!(error = GET_ResolvedPath(Self, &path))) { + if (GET_ResolvedPath(Self, &path) IS ERR::Okay) { struct stat64 stats; if (!stat64(path, &stats)) { *Size = stats.st_size; log.trace("The file size is %" PF64, *Size); - return ERR_Okay; + return ERR::Okay; } - else return convert_errno(errno, ERR_SystemCall); + else return convert_errno(errno, ERR::SystemCall); } - else return log.warning(ERR_ResolvePath); + else return log.warning(ERR::ResolvePath); } -static ERROR SET_Size(extFile *Self, LARGE Size) +static ERR SET_Size(extFile *Self, LARGE Size) { pf::Log log; - if (Size IS Self->Size) return ERR_Okay; - if (Size < 0) return log.warning(ERR_OutOfRange); + if (Size IS Self->Size) return ERR::Okay; + if (Size < 0) return log.warning(ERR::OutOfRange); if (Self->Buffer) { - if (Self->initialised()) return ERR_NoSupport; + if (Self->initialised()) return ERR::NoSupport; else Self->Size = Size; if (Self->Position > Self->Size) acSeekStart(Self, Size); - return ERR_Okay; + return ERR::Okay; } if (!Self->initialised()) { Self->Size = Size; if (Self->Position > Self->Size) acSeekStart(Self, Size); - return ERR_Okay; + return ERR::Okay; } #ifdef _WIN32 CSTRING path; - if (!GET_ResolvedPath(Self, &path)) { + if (GET_ResolvedPath(Self, &path) IS ERR::Okay) { if (winSetEOF(path, Size)) { acSeek(Self, 0.0, SEEK::END); Self->Size = Size; if (Self->Position > Self->Size) acSeekStart(Self, Size); - return ERR_Okay; + return ERR::Okay; } else { log.warning("Failed to set file size to %" PF64, Size); - return ERR_SystemCall; + return ERR::SystemCall; } } - else return log.warning(ERR_ResolvePath); + else return log.warning(ERR::ResolvePath); #elif __unix__ @@ -2594,7 +2595,7 @@ static ERROR SET_Size(extFile *Self, LARGE Size) #endif Self->Size = Size; if (Self->Position > Self->Size) acSeekStart(Self, Size); - return ERR_Okay; + return ERR::Okay; } else { // Some filesystem drivers do not support truncation for the purpose of @@ -2607,7 +2608,7 @@ static ERROR SET_Size(extFile *Self, LARGE Size) // Seek past the file boundary and write a single byte to expand the file. Yes, it's legal and works. - ERROR error; + ERR error; if (!(error = GET_ResolvedPath(Self, &path))) { struct statfs fstat; if (statfs(path, &fstat) != -1) { @@ -2620,23 +2621,23 @@ static ERROR SET_Size(extFile *Self, LARGE Size) lseek64(Self->Handle, Self->Position, SEEK_SET); Self->Size = Size; if (Self->Position > Self->Size) acSeekStart(Self, Size); - return ERR_Okay; + return ERR::Okay; } - else return convert_errno(errno, ERR_SystemCall); + else return convert_errno(errno, ERR::SystemCall); } - else return convert_errno(errno, ERR_SystemCall); + else return convert_errno(errno, ERR::SystemCall); } - else return log.warning(ERR_OutOfSpace); + else return log.warning(ERR::OutOfSpace); } - else return convert_errno(errno, ERR_SystemCall); + else return convert_errno(errno, ERR::SystemCall); } - else return ERR_ResolvePath; + else return ERR::ResolvePath; } - else return ERR_Failed; + else return ERR::Failed; } #else log.trace("No support for truncating file sizes on this platform."); - return log.warning(ERR_NoSupport); + return log.warning(ERR::NoSupport); #endif } @@ -2668,7 +2669,7 @@ for comparison to the time stamps of other files. For a parsed time structure, *********************************************************************************************************************/ -static ERROR GET_TimeStamp(extFile *Self, LARGE *Value) +static ERR GET_TimeStamp(extFile *Self, LARGE *Value) { pf::Log log; @@ -2679,48 +2680,46 @@ static ERROR GET_TimeStamp(extFile *Self, LARGE *Value) if (!fstat64(Self->Handle, &stats)) { // Timestamp has to match that produced by fs_getinfo() - struct tm *local; - if ((local = localtime(&stats.st_mtime))) { - DateTime datetime; - datetime.Year = 1900 + local->tm_year; - datetime.Month = local->tm_mon + 1; - datetime.Day = local->tm_mday; - datetime.Hour = local->tm_hour; - datetime.Minute = local->tm_min; - datetime.Second = local->tm_sec; + if (auto local = localtime(&stats.st_mtime)) { + DateTime datetime = { + .Year = WORD(1900 + local->tm_year), + .Month = BYTE(local->tm_mon + 1), + .Day = BYTE(local->tm_mday), + .Hour = BYTE(local->tm_hour), + .Minute = BYTE(local->tm_min), + .Second = BYTE(local->tm_sec) + }; *Value = calc_timestamp(&datetime); - return ERR_Okay; + return ERR::Okay; } - else return convert_errno(errno, ERR_SystemCall); + else return convert_errno(errno, ERR::SystemCall); } - else return convert_errno(errno, ERR_SystemCall); + else return convert_errno(errno, ERR::SystemCall); } else { CSTRING path; - ERROR error; - if (!(error = GET_ResolvedPath(Self, &path))) { + if (GET_ResolvedPath(Self, &path) IS ERR::Okay) { struct stat64 stats; if (!stat64(path, &stats)) { - - struct tm *local; - if ((local = localtime(&stats.st_mtime))) { - DateTime datetime; - datetime.Year = 1900 + local->tm_year; - datetime.Month = local->tm_mon + 1; - datetime.Day = local->tm_mday; - datetime.Hour = local->tm_hour; - datetime.Minute = local->tm_min; - datetime.Second = local->tm_sec; + if (auto local = localtime(&stats.st_mtime)) { + DateTime datetime = { + .Year = WORD(1900 + local->tm_year), + .Month = BYTE(local->tm_mon + 1), + .Day = BYTE(local->tm_mday), + .Hour = BYTE(local->tm_hour), + .Minute = BYTE(local->tm_min), + .Second = BYTE(local->tm_sec) + }; *Value = calc_timestamp(&datetime); - return ERR_Okay; + return ERR::Okay; } - else return convert_errno(errno, ERR_SystemCall); + else return convert_errno(errno, ERR::SystemCall); } - else return convert_errno(errno, ERR_SystemCall); + else return convert_errno(errno, ERR::SystemCall); } - else return log.warning(ERR_ResolvePath); + else return log.warning(ERR::ResolvePath); } } @@ -2734,38 +2733,38 @@ case the ID has been changed after initialisation of the file object. You can also change the user ID of a file by writing an integer value to this field. This can only be done post-initialisation or an error code will be returned. -If the filesystem does not support user ID's, ERR_NoSupport is returned. +If the filesystem does not support user ID's, ERR::NoSupport is returned. -END- *********************************************************************************************************************/ -static ERROR GET_User(extFile *Self, LONG *Value) +static ERR GET_User(extFile *Self, LONG *Value) { #ifdef __unix__ struct stat64 info; - if (fstat64(Self->Handle, &info) IS -1) return ERR_FileNotFound; + if (fstat64(Self->Handle, &info) IS -1) return ERR::FileNotFound; *Value = info.st_uid; - return ERR_Okay; + return ERR::Okay; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } -static ERROR SET_User(extFile *Self, LONG Value) +static ERR SET_User(extFile *Self, LONG Value) { #ifdef __unix__ pf::Log log; if (Self->initialised()) { log.msg("Changing user to #%d", Value); if (!fchown(Self->Handle, Value, -1)) { - return ERR_Okay; + return ERR::Okay; } - else return log.warning(convert_errno(errno, ERR_Failed)); + else return log.warning(convert_errno(errno, ERR::Failed)); } - else return log.warning(ERR_Failed); + else return log.warning(ERR::Failed); #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -2828,7 +2827,7 @@ static const FieldArray FileFields[] = { //******************************************************************************************************************** -extern "C" ERROR add_file_class(void) +extern "C" ERR add_file_class(void) { glFileClass = extMetaClass::create::global( fl::ClassVersion(VER_FILE), @@ -2840,6 +2839,6 @@ extern "C" ERROR add_file_class(void) fl::Size(sizeof(extFile)), fl::Path("modules:core")); - return glFileClass ? ERR_Okay : ERR_AddClass; + return glFileClass ? ERR::Okay : ERR::AddClass; } diff --git a/src/core/classes/class_metaclass.cpp b/src/core/classes/class_metaclass.cpp index daa6733c1..977ad7d0e 100644 --- a/src/core/classes/class_metaclass.cpp +++ b/src/core/classes/class_metaclass.cpp @@ -27,12 +27,12 @@ complete run-down on class development. #include "../defs.h" -static ERROR OBJECT_GetClass(OBJECTPTR, extMetaClass **); -static ERROR OBJECT_GetClassID(OBJECTPTR, CLASSID *); -static ERROR OBJECT_GetName(OBJECTPTR, STRING *); -static ERROR OBJECT_GetOwner(OBJECTPTR, OBJECTID *); -static ERROR OBJECT_SetOwner(OBJECTPTR, OBJECTID); -static ERROR OBJECT_SetName(OBJECTPTR, CSTRING); +static ERR OBJECT_GetClass(OBJECTPTR, extMetaClass **); +static ERR OBJECT_GetClassID(OBJECTPTR, CLASSID *); +static ERR OBJECT_GetName(OBJECTPTR, STRING *); +static ERR OBJECT_GetOwner(OBJECTPTR, OBJECTID *); +static ERR OBJECT_SetOwner(OBJECTPTR, OBJECTID); +static ERR OBJECT_SetName(OBJECTPTR, CSTRING); static void field_setup(extMetaClass *); static void sort_class_fields(extMetaClass *, std::vector &); @@ -45,30 +45,30 @@ static Field * lookup_id_byclass(extMetaClass *, ULONG, extMetaClass **); // The MetaClass is the focal point of the OO design model. Because classes are treated like objects, they must point // back to a controlling class definition - this it. See NewObject() for the management code for this data. -static ERROR GET_ActionTable(extMetaClass *, ActionEntry **, LONG *); -static ERROR GET_Fields(extMetaClass *, const FieldArray **, LONG *); -static ERROR GET_Location(extMetaClass *, CSTRING *); -static ERROR GET_Methods(extMetaClass *, const MethodEntry **, LONG *); -static ERROR GET_Module(extMetaClass *, CSTRING *); -static ERROR GET_PrivateObjects(extMetaClass *, OBJECTID **, LONG *); -static ERROR GET_RootModule(extMetaClass *, class RootModule **); -static ERROR GET_Dictionary(extMetaClass *, struct Field **, LONG *); -static ERROR GET_SubFields(extMetaClass *, const FieldArray **, LONG *); - -static ERROR SET_Actions(extMetaClass *, const ActionArray *); -static ERROR SET_Fields(extMetaClass *, const FieldArray *, LONG); -static ERROR SET_Methods(extMetaClass *, const MethodEntry *, LONG); - -static ERROR GET_ClassName(extMetaClass *Self, CSTRING *Value) +static ERR GET_ActionTable(extMetaClass *, ActionEntry **, LONG *); +static ERR GET_Fields(extMetaClass *, const FieldArray **, LONG *); +static ERR GET_Location(extMetaClass *, CSTRING *); +static ERR GET_Methods(extMetaClass *, const MethodEntry **, LONG *); +static ERR GET_Module(extMetaClass *, CSTRING *); +static ERR GET_PrivateObjects(extMetaClass *, OBJECTID **, LONG *); +static ERR GET_RootModule(extMetaClass *, class RootModule **); +static ERR GET_Dictionary(extMetaClass *, struct Field **, LONG *); +static ERR GET_SubFields(extMetaClass *, const FieldArray **, LONG *); + +static ERR SET_Actions(extMetaClass *, const ActionArray *); +static ERR SET_Fields(extMetaClass *, const FieldArray *, LONG); +static ERR SET_Methods(extMetaClass *, const MethodEntry *, LONG); + +static ERR GET_ClassName(extMetaClass *Self, CSTRING *Value) { *Value = Self->ClassName; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_ClassName(extMetaClass *Self, CSTRING Value) +static ERR SET_ClassName(extMetaClass *Self, CSTRING Value) { Self->ClassName = Value; - return ERR_Okay; + return ERR::Okay; } static const FieldDef CategoryTable[] = { @@ -85,8 +85,8 @@ static const FieldDef CategoryTable[] = { static const std::vector glMetaFieldsPreset = { // If you adjust this table, remember to adjust the index numbers and the byte offsets into the structure. { 0, NULL, NULL, writeval_default, "ClassVersion", FID_ClassVersion, sizeof(BaseClass), 0, FDF_DOUBLE|FDF_RI }, - { (MAXINT)"FieldArray", (ERROR (*)(APTR, APTR))GET_Fields, (APTR)SET_Fields, writeval_default, "Fields", FID_Fields, sizeof(BaseClass)+8, 1, FDF_ARRAY|FD_STRUCT|FDF_RI }, - { (MAXINT)"Field", (ERROR (*)(APTR, APTR))GET_Dictionary, NULL, writeval_default, "Dictionary", FID_Dictionary, sizeof(BaseClass)+8+(sizeof(APTR)*1), 2, FDF_ARRAY|FD_STRUCT|FDF_R }, + { (MAXINT)"FieldArray", (ERR (*)(APTR, APTR))GET_Fields, (APTR)SET_Fields, writeval_default, "Fields", FID_Fields, sizeof(BaseClass)+8, 1, FDF_ARRAY|FD_STRUCT|FDF_RI }, + { (MAXINT)"Field", (ERR (*)(APTR, APTR))GET_Dictionary, NULL, writeval_default, "Dictionary", FID_Dictionary, sizeof(BaseClass)+8+(sizeof(APTR)*1), 2, FDF_ARRAY|FD_STRUCT|FDF_R }, { 0, NULL, NULL, writeval_default, "ClassName", FID_ClassName, sizeof(BaseClass)+8+(sizeof(APTR)*2), 3, FDF_STRING|FDF_RI }, { 0, NULL, NULL, writeval_default, "FileExtension", FID_FileExtension, sizeof(BaseClass)+8+(sizeof(APTR)*3), 4, FDF_STRING|FDF_RI }, { 0, NULL, NULL, writeval_default, "FileDescription", FID_FileDescription, sizeof(BaseClass)+8+(sizeof(APTR)*4), 5, FDF_STRING|FDF_RI }, @@ -99,15 +99,15 @@ static const std::vector glMetaFieldsPreset = { { 0, NULL, NULL, writeval_default, "OpenCount", FID_OpenCount, sizeof(BaseClass)+24+(sizeof(APTR)*7), 12, FDF_LONG|FDF_R }, { (MAXINT)&CategoryTable, NULL, NULL, writeval_default, "Category", FID_Category, sizeof(BaseClass)+28+(sizeof(APTR)*7), 13, FDF_LONG|FDF_LOOKUP|FDF_RI }, // Virtual fields - { (MAXINT)"MethodEntry", (ERROR (*)(APTR, APTR))GET_Methods, (APTR)SET_Methods, writeval_default, "Methods", FID_Methods, sizeof(BaseClass), 14, FDF_ARRAY|FD_STRUCT|FDF_RI }, + { (MAXINT)"MethodEntry", (ERR (*)(APTR, APTR))GET_Methods, (APTR)SET_Methods, writeval_default, "Methods", FID_Methods, sizeof(BaseClass), 14, FDF_ARRAY|FD_STRUCT|FDF_RI }, { 0, NULL, (APTR)SET_Actions, writeval_default, "Actions", FID_Actions, sizeof(BaseClass), 15, FDF_POINTER|FDF_I }, - { 0, (ERROR (*)(APTR, APTR))GET_ActionTable, 0, writeval_default, "ActionTable", FID_ActionTable, sizeof(BaseClass), 16, FDF_ARRAY|FDF_POINTER|FDF_R }, - { 0, (ERROR (*)(APTR, APTR))GET_Location, 0, writeval_default, "Location", FID_Location, sizeof(BaseClass), 17, FDF_STRING|FDF_R }, - { 0, (ERROR (*)(APTR, APTR))GET_ClassName, (APTR)SET_ClassName, writeval_default, "Name", FID_Name, sizeof(BaseClass), 18, FDF_STRING|FDF_SYSTEM|FDF_RI }, - { 0, (ERROR (*)(APTR, APTR))GET_Module, 0, writeval_default, "Module", FID_Module, sizeof(BaseClass), 19, FDF_STRING|FDF_R }, - { 0, (ERROR (*)(APTR, APTR))GET_PrivateObjects, 0, writeval_default, "PrivateObjects", FID_PrivateObjects, sizeof(BaseClass), 20, FDF_ARRAY|FDF_LONG|FDF_ALLOC|FDF_R }, - { (MAXINT)"FieldArray", (ERROR (*)(APTR, APTR))GET_SubFields, 0, writeval_default, "SubFields", FID_SubFields, sizeof(BaseClass), 21, FDF_ARRAY|FD_STRUCT|FDF_SYSTEM|FDF_R }, - { ID_ROOTMODULE, (ERROR (*)(APTR, APTR))GET_RootModule, 0, writeval_default, "RootModule", FID_RootModule, sizeof(BaseClass), 22, FDF_OBJECT|FDF_R }, + { 0, (ERR (*)(APTR, APTR))GET_ActionTable, 0, writeval_default, "ActionTable", FID_ActionTable, sizeof(BaseClass), 16, FDF_ARRAY|FDF_POINTER|FDF_R }, + { 0, (ERR (*)(APTR, APTR))GET_Location, 0, writeval_default, "Location", FID_Location, sizeof(BaseClass), 17, FDF_STRING|FDF_R }, + { 0, (ERR (*)(APTR, APTR))GET_ClassName, (APTR)SET_ClassName, writeval_default, "Name", FID_Name, sizeof(BaseClass), 18, FDF_STRING|FDF_SYSTEM|FDF_RI }, + { 0, (ERR (*)(APTR, APTR))GET_Module, 0, writeval_default, "Module", FID_Module, sizeof(BaseClass), 19, FDF_STRING|FDF_R }, + { 0, (ERR (*)(APTR, APTR))GET_PrivateObjects, 0, writeval_default, "PrivateObjects", FID_PrivateObjects, sizeof(BaseClass), 20, FDF_ARRAY|FDF_LONG|FDF_ALLOC|FDF_R }, + { (MAXINT)"FieldArray", (ERR (*)(APTR, APTR))GET_SubFields, 0, writeval_default, "SubFields", FID_SubFields, sizeof(BaseClass), 21, FDF_ARRAY|FD_STRUCT|FDF_SYSTEM|FDF_R }, + { ID_ROOTMODULE, (ERR (*)(APTR, APTR))GET_RootModule, 0, writeval_default, "RootModule", FID_RootModule, sizeof(BaseClass), 22, FDF_OBJECT|FDF_R }, { 0, 0, 0, NULL, "", 0, 0, 0, 0 } }; @@ -139,10 +139,10 @@ static const FieldArray glMetaFields[] = { END_FIELD }; -extern "C" ERROR CLASS_FindField(extMetaClass *, struct mcFindField *); -extern "C" ERROR CLASS_Free(extMetaClass *, APTR); -extern "C" ERROR CLASS_Init(extMetaClass *, APTR); -extern "C" ERROR CLASS_NewObject(extMetaClass *, APTR); +extern "C" ERR CLASS_FindField(extMetaClass *, struct mcFindField *); +extern "C" ERR CLASS_Free(extMetaClass *, APTR); +extern "C" ERR CLASS_Init(extMetaClass *, APTR); +extern "C" ERR CLASS_NewObject(extMetaClass *, APTR); FDEF argsFindField[] = { { "ID", FD_LONG }, { "Field:Field", FD_RESULT|FD_PTR|FD_STRUCT }, { "Source", FD_RESULT|FD_OBJECTPTR }, { 0, 0 } }; @@ -151,10 +151,10 @@ extMetaClass glMetaClass; //******************************************************************************************************************** // Standard signal action, applicable to all classes -static ERROR DEFAULT_Signal(OBJECTPTR Object, APTR Void) +static ERR DEFAULT_Signal(OBJECTPTR Object, APTR Void) { Object->Flags |= NF::SIGNALLED; - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -179,9 +179,9 @@ void init_metaclass(void) glMetaClass.Methods.resize(2); glMetaClass.Methods[1] = { -1, (APTR)CLASS_FindField, "FindField", argsFindField, sizeof(struct mcFindField) }; - glMetaClass.ActionTable[AC_Free].PerformAction = (ERROR (*)(OBJECTPTR, APTR))CLASS_Free; - glMetaClass.ActionTable[AC_Init].PerformAction = (ERROR (*)(OBJECTPTR, APTR))CLASS_Init; - glMetaClass.ActionTable[AC_NewObject].PerformAction = (ERROR (*)(OBJECTPTR, APTR))CLASS_NewObject; + glMetaClass.ActionTable[AC_Free].PerformAction = (ERR (*)(OBJECTPTR, APTR))CLASS_Free; + glMetaClass.ActionTable[AC_Init].PerformAction = (ERR (*)(OBJECTPTR, APTR))CLASS_Init; + glMetaClass.ActionTable[AC_NewObject].PerformAction = (ERR (*)(OBJECTPTR, APTR))CLASS_NewObject; glMetaClass.ActionTable[AC_Signal].PerformAction = &DEFAULT_Signal; sort_class_fields(&glMetaClass, glMetaClass.FieldLookup); @@ -214,34 +214,34 @@ Search *********************************************************************************************************************/ -ERROR CLASS_FindField(extMetaClass *Self, struct mcFindField *Args) +ERR CLASS_FindField(extMetaClass *Self, struct mcFindField *Args) { - if ((!Args) or (!Args->ID)) return ERR_NullArgs; + if ((!Args) or (!Args->ID)) return ERR::NullArgs; extMetaClass *src = NULL; Args->Field = lookup_id_byclass(Self, Args->ID, &src); Args->Source = src; - if (Args->Field) return ERR_Okay; - else return ERR_Search; + if (Args->Field) return ERR::Okay; + else return ERR::Search; } //******************************************************************************************************************** -ERROR CLASS_Free(extMetaClass *Self, APTR Void) +ERR CLASS_Free(extMetaClass *Self, APTR Void) { if (Self->ClassID) glClassMap.erase(Self->ClassID); if (Self->Location) { FreeResource(Self->Location); Self->Location = NULL; } Self->~extMetaClass(); - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -ERROR CLASS_Init(extMetaClass *Self, APTR Void) +ERR CLASS_Init(extMetaClass *Self, APTR Void) { pf::Log log; - if (!Self->ClassName) return log.warning(ERR_MissingClassName); + if (!Self->ClassName) return log.warning(ERR::MissingClassName); auto class_hash = StrHash(Self->ClassName, false); @@ -257,7 +257,7 @@ ERROR CLASS_Init(extMetaClass *Self, APTR Void) if (!Self->Size) Self->Size = sizeof(BaseClass); else if (Self->Size < (LONG)sizeof(BaseClass)) { // Object size not specified log.warning("Size of %d is not valid.", Self->Size); - return ERR_FieldNotSet; + return ERR::FieldNotSet; } } else { @@ -301,7 +301,7 @@ ERROR CLASS_Init(extMetaClass *Self, APTR Void) } else { log.warning("A base for class $%.8x is not present!", Self->BaseClassID); - return ERR_Failed; + return ERR::Failed; } } @@ -351,12 +351,12 @@ ERROR CLASS_Init(extMetaClass *Self, APTR Void) if ((!glClassFile) and (!write_attempted)) { write_attempted = true; auto flags = FL::WRITE; - if (AnalysePath(glClassBinPath, NULL) != ERR_Okay) flags |= FL::NEW; + if (AnalysePath(glClassBinPath, NULL) != ERR::Okay) flags |= FL::NEW; auto file = objFile::create::untracked(fl::Name("class_dict_output"), fl::Path(glClassBinPath), fl::Flags(flags), fl::Permissions(PERMIT::USER_READ|PERMIT::USER_WRITE|PERMIT::GROUP_READ|PERMIT::GROUP_WRITE|PERMIT::OTHERS_READ)); - if (!file) return ERR_File; + if (!file) return ERR::File; glClassFile = file; LONG hdr = CLASSDB_HEADER; @@ -368,20 +368,20 @@ ERROR CLASS_Init(extMetaClass *Self, APTR Void) glClassDB[Self->ClassID].write(glClassFile); } } - else return log.warning(ERR_SystemLocked); + else return log.warning(ERR::SystemLocked); } #endif - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -ERROR CLASS_NewObject(extMetaClass *Self, APTR Void) +ERR CLASS_NewObject(extMetaClass *Self, APTR Void) { new (Self) extMetaClass; Self->Integral[0] = 0xff; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -414,20 +414,20 @@ Never define method ID's in an action list - the #Methods field is provided for *********************************************************************************************************************/ -static ERROR SET_Actions(extMetaClass *Self, const ActionArray *Actions) +static ERR SET_Actions(extMetaClass *Self, const ActionArray *Actions) { - if (!Actions) return ERR_Failed; + if (!Actions) return ERR::Failed; Self->ActionTable[AC_Signal].PerformAction = &DEFAULT_Signal; for (auto i=0; Actions[i].ActionCode; i++) { auto code = Actions[i].ActionCode; if ((code < AC_END) and (code > 0)) { - Self->ActionTable[code].PerformAction = (ERROR (*)(OBJECTPTR, APTR))Actions[i].Routine; + Self->ActionTable[code].PerformAction = (ERR (*)(OBJECTPTR, APTR))Actions[i].Routine; } } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -446,11 +446,11 @@ a call, as documented in the Action Support Guide. *********************************************************************************************************************/ -static ERROR GET_ActionTable(extMetaClass *Self, ActionEntry **Value, LONG *Elements) +static ERR GET_ActionTable(extMetaClass *Self, ActionEntry **Value, LONG *Elements) { *Value = Self->ActionTable; *Elements = AC_END; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -499,14 +499,14 @@ linear scanning. *********************************************************************************************************************/ -static ERROR GET_Dictionary(extMetaClass *Self, struct Field **Value, LONG *Elements) +static ERR GET_Dictionary(extMetaClass *Self, struct Field **Value, LONG *Elements) { if (Self->initialised()) { *Value = Self->FieldLookup.data(); *Elements = Self->FieldLookup.size(); - return ERR_Okay; + return ERR::Okay; } - else return ERR_NotInitialised; + else return ERR::NotInitialised; } /********************************************************************************************************************* @@ -522,16 +522,16 @@ information. *********************************************************************************************************************/ -static ERROR GET_Fields(extMetaClass *Self, const FieldArray **Fields, LONG *Elements) +static ERR GET_Fields(extMetaClass *Self, const FieldArray **Fields, LONG *Elements) { *Fields = Self->Fields; *Elements = Self->OriginalFieldTotal; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_Fields(extMetaClass *Self, const FieldArray *Fields, LONG Elements) +static ERR SET_Fields(extMetaClass *Self, const FieldArray *Fields, LONG Elements) { - if (!Fields) return ERR_Failed; + if (!Fields) return ERR::Failed; Self->Fields = Fields; if (Elements > 0) { @@ -544,7 +544,7 @@ static ERROR SET_Fields(extMetaClass *Self, const FieldArray *Fields, LONG Eleme Self->OriginalFieldTotal = i; } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -597,10 +597,10 @@ file extension of the source binary. *********************************************************************************************************************/ -static ERROR GET_Location(extMetaClass *Self, CSTRING *Value) +static ERR GET_Location(extMetaClass *Self, CSTRING *Value) { - if (Self->Path) { *Value = Self->Path; return ERR_Okay; } - if (Self->Location) { *Value = Self->Location; return ERR_Okay; } + if (Self->Path) { *Value = Self->Path; return ERR::Okay; } + if (Self->Location) { *Value = Self->Location; return ERR::Okay; } if (Self->ClassID) { if (glClassDB.contains(Self->ClassID)) { @@ -611,8 +611,8 @@ static ERROR GET_Location(extMetaClass *Self, CSTRING *Value) Self->Location = StrClone(glClassDB[Self->BaseClassID].Path.c_str()); } - if ((*Value = Self->Location)) return ERR_Okay; - else return ERR_Failed; + if ((*Value = Self->Location)) return ERR::Okay; + else return ERR::Failed; } /********************************************************************************************************************* @@ -628,19 +628,19 @@ information. *********************************************************************************************************************/ -static ERROR GET_Methods(extMetaClass *Self, const MethodEntry **Methods, LONG *Elements) +static ERR GET_Methods(extMetaClass *Self, const MethodEntry **Methods, LONG *Elements) { *Methods = Self->Methods.data(); *Elements = Self->Methods.size(); - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_Methods(extMetaClass *Self, const MethodEntry *Methods, LONG Elements) +static ERR SET_Methods(extMetaClass *Self, const MethodEntry *Methods, LONG Elements) { pf::Log log; Self->Methods.clear(); - if (!Methods) return ERR_Okay; + if (!Methods) return ERR::Okay; // Search for the method with the lowest ID number @@ -666,7 +666,7 @@ static ERROR SET_Methods(extMetaClass *Self, const MethodEntry *Methods, LONG El // NOTE: If this is a sub-class, the initialisation process will add the base-class methods to the list. } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -676,17 +676,17 @@ Module: The name of the module binary that initialised the class. *********************************************************************************************************************/ -static ERROR GET_Module(extMetaClass *Self, CSTRING *Value) +static ERR GET_Module(extMetaClass *Self, CSTRING *Value) { - if (!Self->initialised()) return ERR_NotInitialised; + if (!Self->initialised()) return ERR::NotInitialised; if (Self->Root) { *Value = Self->Root->LibraryName; - return ERR_Okay; + return ERR::Okay; } else { *Value = "core"; - return ERR_Okay; + return ERR::Okay; } } @@ -702,7 +702,7 @@ The resulting array must be terminated with ~FreeResource() after use. *********************************************************************************************************************/ -static ERROR GET_PrivateObjects(extMetaClass *Self, OBJECTID **Array, LONG *Elements) +static ERR GET_PrivateObjects(extMetaClass *Self, OBJECTID **Array, LONG *Elements) { pf::Log log; std::list objlist; @@ -717,25 +717,25 @@ static ERROR GET_PrivateObjects(extMetaClass *Self, OBJECTID **Array, LONG *Elem } } } - else return log.warning(ERR_SystemLocked); + else return log.warning(ERR::SystemLocked); if (!objlist.size()) { *Array = NULL; *Elements = 0; - return ERR_Okay; + return ERR::Okay; } objlist.sort([](const OBJECTID &a, const OBJECTID &b) { return (a < b); }); OBJECTID *result; - if (!AllocMemory(sizeof(OBJECTID) * objlist.size(), MEM::NO_CLEAR, (APTR *)&result, NULL)) { + if (AllocMemory(sizeof(OBJECTID) * objlist.size(), MEM::NO_CLEAR, (APTR *)&result, NULL) IS ERR::Okay) { LONG i = 0; for (const auto & id : objlist) result[i++] = id; *Array = result; *Elements = objlist.size(); - return ERR_Okay; + return ERR::Okay; } - else return ERR_AllocMemory; + else return ERR::AllocMemory; } /********************************************************************************************************************* @@ -760,10 +760,10 @@ RootModule: Returns a direct reference to the RootModule object that hosts the c *********************************************************************************************************************/ -static ERROR GET_RootModule(extMetaClass *Self, class RootModule **Value) +static ERR GET_RootModule(extMetaClass *Self, class RootModule **Value) { *Value = Self->Root; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -780,7 +780,7 @@ evaluating the field definitions that have been provided. *********************************************************************************************************************/ -static ERROR GET_SubFields(extMetaClass *Self, const FieldArray **Fields, LONG *Elements) +static ERR GET_SubFields(extMetaClass *Self, const FieldArray **Fields, LONG *Elements) { if (Self->SubFields) { LONG i; @@ -792,7 +792,7 @@ static ERROR GET_SubFields(extMetaClass *Self, const FieldArray **Fields, LONG * *Fields = NULL; *Elements = 0; } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -819,7 +819,7 @@ static void field_setup(extMetaClass *Class) for (unsigned j=0; j < Class->FieldLookup.size(); j++) { if (Class->FieldLookup[j].FieldID IS hash) { if (Class->SubFields[i].GetField) { - Class->FieldLookup[j].GetValue = (ERROR (*)(APTR, APTR))Class->SubFields[i].GetField; + Class->FieldLookup[j].GetValue = (ERR (*)(APTR, APTR))Class->SubFields[i].GetField; Class->FieldLookup[j].Flags |= FDF_R; } @@ -863,7 +863,7 @@ static void field_setup(extMetaClass *Class) if (name_field) { Class->FieldLookup.push_back({ .Arg = 0, - .GetValue = (ERROR (*)(APTR, APTR))&OBJECT_GetName, + .GetValue = (ERR (*)(APTR, APTR))&OBJECT_GetName, .SetValue = (APTR)&OBJECT_SetName, .WriteValue = &writeval_default, .Name = "Name", @@ -877,7 +877,7 @@ static void field_setup(extMetaClass *Class) if (owner_field) { Class->FieldLookup.push_back({ .Arg = 0, - .GetValue = (ERROR (*)(APTR, APTR))&OBJECT_GetOwner, + .GetValue = (ERR (*)(APTR, APTR))&OBJECT_GetOwner, .SetValue = (APTR)&OBJECT_SetOwner, .WriteValue = &writeval_default, .Name = "Owner", @@ -892,7 +892,7 @@ static void field_setup(extMetaClass *Class) Class->FieldLookup.push_back({ .Arg = 0, - .GetValue = (ERROR (*)(APTR, APTR))&OBJECT_GetClass, + .GetValue = (ERR (*)(APTR, APTR))&OBJECT_GetClass, .SetValue = NULL, .WriteValue = &writeval_default, .Name = "Class", @@ -906,7 +906,7 @@ static void field_setup(extMetaClass *Class) Class->FieldLookup.push_back({ .Arg = 0, - .GetValue = (ERROR (*)(APTR, APTR))&OBJECT_GetClassID, + .GetValue = (ERR (*)(APTR, APTR))&OBJECT_GetClassID, .SetValue = NULL, .WriteValue = &writeval_default, .Name = "ClassID", @@ -973,7 +973,7 @@ static void add_field(extMetaClass *Class, std::vector &Fields, const Fie auto &field = Fields.emplace_back( Source.Arg, - (ERROR (*)(APTR, APTR))Source.GetField, + (ERR (*)(APTR, APTR))Source.GetField, Source.SetField, writeval_default, Source.Name, @@ -1029,53 +1029,53 @@ static void sort_class_fields(extMetaClass *Class, std::vector &Fields) //******************************************************************************************************************** // These are pre-defined fields that are applied to each class' object. -static ERROR OBJECT_GetClass(OBJECTPTR Self, extMetaClass **Value) +static ERR OBJECT_GetClass(OBJECTPTR Self, extMetaClass **Value) { *Value = Self->ExtClass; - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR OBJECT_GetClassID(OBJECTPTR Self, CLASSID *Value) +static ERR OBJECT_GetClassID(OBJECTPTR Self, CLASSID *Value) { *Value = Self->Class->ClassID; - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR OBJECT_GetOwner(OBJECTPTR Self, OBJECTID *OwnerID) +static ERR OBJECT_GetOwner(OBJECTPTR Self, OBJECTID *OwnerID) { *OwnerID = Self->ownerID(); - return ERR_Okay; + return ERR::Okay; } -static ERROR OBJECT_SetOwner(OBJECTPTR Self, OBJECTID OwnerID) +static ERR OBJECT_SetOwner(OBJECTPTR Self, OBJECTID OwnerID) { pf::Log log; if (OwnerID) { OBJECTPTR newowner; - if (!AccessObject(OwnerID, 2000, &newowner)) { + if (AccessObject(OwnerID, 2000, &newowner) IS ERR::Okay) { SetOwner(Self, newowner); ReleaseObject(newowner); - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_ExclusiveDenied); + else return log.warning(ERR::ExclusiveDenied); } - else return log.warning(ERR_NullArgs); + else return log.warning(ERR::NullArgs); } //******************************************************************************************************************** -static ERROR OBJECT_GetName(OBJECTPTR Self, STRING *Name) +static ERR OBJECT_GetName(OBJECTPTR Self, STRING *Name) { *Name = Self->Name; - return ERR_Okay; + return ERR::Okay; } -static ERROR OBJECT_SetName(OBJECTPTR Self, CSTRING Name) +static ERR OBJECT_SetName(OBJECTPTR Self, CSTRING Name) { if (!Name) return SetName(Self, ""); else return SetName(Self, Name); @@ -1098,9 +1098,9 @@ void scan_classes(void) DeleteFile(glClassBinPath, NULL); DirInfo *dir; - if (!OpenDir("modules:", RDF::QUALIFY, &dir)) { + if (OpenDir("modules:", RDF::QUALIFY, &dir) IS ERR::Okay) { LONG total = 0; - while (!ScanDir(dir)) { + while (ScanDir(dir) IS ERR::Okay) { FileInfo *list = dir->Info; if ((list->Flags & RDF::FILE) != RDF::NIL) { @@ -1108,7 +1108,7 @@ void scan_classes(void) if (!StrCompare("libshim.", list->Name)) continue; if (!StrCompare("libcore.", list->Name)) continue; #else - if (!StrCompare("core.", list->Name)) continue; + if (StrCompare("core.", list->Name) IS ERR::Okay) continue; #endif auto modules = std::string("modules:") + list->Name; diff --git a/src/core/classes/class_module.cpp b/src/core/classes/class_module.cpp index e1e008571..11aa4b12d 100644 --- a/src/core/classes/class_module.cpp +++ b/src/core/classes/class_module.cpp @@ -96,10 +96,10 @@ static void free_module(MODHANDLE handle); //******************************************************************************************************************** -static ERROR GET_Name(extModule *, CSTRING *); +static ERR GET_Name(extModule *, CSTRING *); -static ERROR SET_Header(extModule *, struct ModHeader *); -static ERROR SET_Name(extModule *, CSTRING); +static ERR SET_Header(extModule *, struct ModHeader *); +static ERR SET_Name(extModule *, CSTRING); static const FieldDef clFlags[] = { { "LinkLibrary", MOF::LINK_LIBRARY }, @@ -118,8 +118,8 @@ static const FieldArray glModuleFields[] = { END_FIELD }; -static ERROR MODULE_Init(extModule *, APTR); -static ERROR MODULE_Free(extModule *, APTR); +static ERR MODULE_Init(extModule *, APTR); +static ERR MODULE_Free(extModule *, APTR); static const ActionArray glModuleActions[] = { { AC_Free, MODULE_Free }, @@ -130,7 +130,7 @@ static const ActionArray glModuleActions[] = { //******************************************************************************************************************** #ifndef PARASOL_STATIC -static ERROR load_mod(extModule *Self, RootModule *Root, struct ModHeader **Table) +static ERR load_mod(extModule *Self, RootModule *Root, struct ModHeader **Table) { pf::Log log(__FUNCTION__); std::string path; @@ -143,13 +143,13 @@ static ERROR load_mod(extModule *Self, RootModule *Root, struct ModHeader **Tabl path.assign(Self->Name); STRING volume; - if (!ResolvePath(path.c_str(), RSF::APPROXIMATE, &volume)) { + if (ResolvePath(path.c_str(), RSF::APPROXIMATE, &volume) IS ERR::Okay) { path.assign(volume); FreeResource(volume); } else { log.warning("Failed to resolve the path of module '%s'", Self->Name); - return ERR_ResolvePath; + return ERR::ResolvePath; } } @@ -225,13 +225,13 @@ static ERROR load_mod(extModule *Self, RootModule *Root, struct ModHeader **Tabl if ((Self->Flags & MOF::LINK_LIBRARY) IS MOF::NIL) { if (!(*Table = (struct ModHeader *)dlsym(Root->LibraryBase, "ModHeader"))) { log.warning("The 'ModHeader' structure is missing from module %s.", path.c_str()); - return ERR_NotFound; + return ERR::NotFound; } } } else { log.warning("%s: %s", Self->Name, (CSTRING)dlerror()); - return ERR_NoSupport; + return ERR::NoSupport; } #elif _WIN32 @@ -241,7 +241,7 @@ static ERROR load_mod(extModule *Self, RootModule *Root, struct ModHeader **Tabl if (!(*Table = (struct ModHeader *)winGetProcAddress(Root->LibraryBase, "ModHeader"))) { if (!(*Table = (struct ModHeader *)winGetProcAddress(Root->LibraryBase, "_ModHeader"))) { log.warning("The 'ModHeader' structure is missing from module %s.", path.c_str()); - return ERR_NotFound; + return ERR::NotFound; } } } @@ -249,20 +249,20 @@ static ERROR load_mod(extModule *Self, RootModule *Root, struct ModHeader **Tabl else { char msg[100]; log.error("Failed to load DLL '%s' (call: winLoadLibrary(): %s).", path.c_str(), winFormatMessage(0, msg, sizeof(msg))); - return ERR_Read; + return ERR::Read; } #else #error This system needs support for the loading of module/exe files. #endif - return ERR_Okay; + return ERR::Okay; } #endif //******************************************************************************************************************** -ERROR ROOTMODULE_Free(RootModule *Self, APTR Void) +ERR ROOTMODULE_Free(RootModule *Self, APTR Void) { if (Self->Table) Self->Table->Root = NULL; // Remove the DLL's reference to the master. @@ -285,13 +285,13 @@ ERROR ROOTMODULE_Free(RootModule *Self, APTR Void) if (Self->Next) Self->Next->Prev = Self->Prev; } - return ERR_Okay; + return ERR::Okay; } -static ERROR ROOTMODULE_GET_Header(RootModule *Self, struct ModHeader **Value) +static ERR ROOTMODULE_GET_Header(RootModule *Self, struct ModHeader **Value) { *Value = Self->Header; - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -299,7 +299,7 @@ static ERROR ROOTMODULE_GET_Header(RootModule *Self, struct ModHeader **Value) // module code will be left resident in memory as it belongs to the RootModule, not the Module. See Expunge() // in the Core for further details. -static ERROR MODULE_Free(extModule *Self, APTR Void) +static ERR MODULE_Free(extModule *Self, APTR Void) { // Call the Module's Close procedure @@ -310,20 +310,20 @@ static ERROR MODULE_Free(extModule *Self, APTR Void) } if (Self->prvMBMemory) { FreeResource(Self->prvMBMemory); Self->prvMBMemory = NULL; } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR MODULE_Init(extModule *Self, APTR Void) +static ERR MODULE_Init(extModule *Self, APTR Void) { pf::Log log; - ERROR error = ERR_Failed; + ERR error = ERR::Failed; LONG i; bool root_mod = false; char name[60]; - if (!Self->Name[0]) return log.warning(ERR_FieldNotSet); + if (!Self->Name[0]) return log.warning(ERR::FieldNotSet); // Check if the module is resident. If not, we need to load and prepare the module for a shared environment. @@ -340,7 +340,7 @@ static ERROR MODULE_Init(extModule *Self, APTR Void) if ((master = check_resident(Self, name))) { Self->Root = master; } - else if (!NewObject(ID_ROOTMODULE, NF::UNTRACKED, (OBJECTPTR *)&master)) { + else if (NewObject(ID_ROOTMODULE, NF::UNTRACKED, (OBJECTPTR *)&master) IS ERR::Okay) { master->Next = glModuleList; // Insert the RootModule at the start of the chain. if (glModuleList) glModuleList->Prev = master; glModuleList = master; @@ -362,11 +362,11 @@ static ERROR MODULE_Init(extModule *Self, APTR Void) if (it != glStaticModules.end()) table = it->second; else { log.warning("Unable to find module '%s' from %d static modules.", Self->Name, LONG(glStaticModules.size())); - error = ERR_NotFound; + error = ERR::NotFound; goto exit; } #else - if ((error = load_mod(Self, master, &table))) goto exit; + if ((error = load_mod(Self, master, &table)) != ERR::Okay) goto exit; #endif } @@ -375,8 +375,8 @@ static ERROR MODULE_Init(extModule *Self, APTR Void) Self->Root = master; if (table) { - if (!table->Init) { log.warning(ERR_ModuleMissingInit); goto exit; } - if (!table->Name) { log.warning(ERR_ModuleMissingName); goto exit; } + if (!table->Init) { log.warning(ERR::ModuleMissingInit); goto exit; } + if (!table->Name) { log.warning(ERR::ModuleMissingName); goto exit; } master->Header = table; master->Table = table; @@ -400,13 +400,13 @@ static ERROR MODULE_Init(extModule *Self, APTR Void) error = master->Init(Self, modkb); } #endif - if (error) goto exit; + if (error != ERR::Okay) goto exit; } else if ((Self->Flags & MOF::LINK_LIBRARY) != MOF::NIL) { log.msg("Loaded link library '%s'", Self->Name); } else { - log.warning(ERR_ModuleMissingInit); + log.warning(ERR::ModuleMissingInit); goto exit; } @@ -414,7 +414,7 @@ static ERROR MODULE_Init(extModule *Self, APTR Void) context = NULL; } else { - error = log.warning(ERR_NewObject); + error = log.warning(ERR::NewObject); goto exit; } @@ -430,8 +430,8 @@ static ERROR MODULE_Init(extModule *Self, APTR Void) if (master->Open) { log.trace("Opening %s module.", Self->Name); - if (master->Open(Self) != ERR_Okay) { - log.warning(ERR_ModuleOpenFailed); + if (master->Open(Self) != ERR::Okay) { + log.warning(ERR::ModuleOpenFailed); goto exit; } } @@ -458,13 +458,13 @@ static ERROR MODULE_Init(extModule *Self, APTR Void) #endif log.trace("Module has been successfully initialised."); - error = ERR_Okay; + error = ERR::Okay; exit: - if (error) { // Free allocations if an error occurred + if (error != ERR::Okay) { // Free allocations if an error occurred - if (!(error & ERF_Notified)) log.msg("\"%s\" failed: %s", Self->Name, GetErrorMsg(error)); - error &= ~(ERF_Notified|ERF_Delay); + if ((error & ERR::Notified) IS ERR::Okay) log.msg("\"%s\" failed: %s", Self->Name, GetErrorMsg(error)); + error &= ~(ERR::Notified); if (root_mod) { if (master->Expunge) master->Expunge(); @@ -483,7 +483,7 @@ static ERROR MODULE_Init(extModule *Self, APTR Void) ResolveSymbol: Resolves the symbol names in loaded link libraries to address pointers. This method will convert symbol names to their respective address pointers. The module code must have been successfully -loaded into memory or an ERR_FieldNotSet error will be returned. If the symbol was not found then ERR_NotFound is +loaded into memory or an ERR::FieldNotSet error will be returned. If the symbol was not found then ERR::NotFound is returned. -INPUT- @@ -499,41 +499,41 @@ NoSupport: The host platform does not support this method. **********************************************************************************************************************/ -static ERROR MODULE_ResolveSymbol(extModule *Self, struct modResolveSymbol *Args) +static ERR MODULE_ResolveSymbol(extModule *Self, struct modResolveSymbol *Args) { pf::Log log; - if ((!Args) or (!Args->Name)) return log.warning(ERR_NullArgs); + if ((!Args) or (!Args->Name)) return log.warning(ERR::NullArgs); #ifdef _WIN32 #ifdef PARASOL_STATIC if ((Args->Address = winGetProcAddress(NULL, Args->Name))) { #else - if ((!Self->Root) or (!Self->Root->LibraryBase)) return ERR_FieldNotSet; + if ((!Self->Root) or (!Self->Root->LibraryBase)) return ERR::FieldNotSet; if ((Args->Address = winGetProcAddress(Self->Root->LibraryBase, Args->Name))) { #endif - return ERR_Okay; + return ERR::Okay; } else { log.msg("Failed to resolve '%s' in %s module.", Args->Name, Self->Root->Name); - return ERR_NotFound; + return ERR::NotFound; } #elif __unix__ #ifdef PARASOL_STATIC if ((Args->Address = dlsym(RTLD_DEFAULT, Args->Name))) { #else - if ((!Self->Root) or (!Self->Root->LibraryBase)) return ERR_FieldNotSet; + if ((!Self->Root) or (!Self->Root->LibraryBase)) return ERR::FieldNotSet; if ((Args->Address = dlsym(Self->Root->LibraryBase, Args->Name))) { #endif - return ERR_Okay; + return ERR::Okay; } else { log.msg("Failed to resolve '%s' in %s module.", Args->Name, Self->Root->Name); - return ERR_NotFound; + return ERR::NotFound; } #else #warning Platform not supported. - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -566,11 +566,11 @@ than on disk. **********************************************************************************************************************/ -static ERROR SET_Header(extModule *Self, struct ModHeader *Value) +static ERR SET_Header(extModule *Self, struct ModHeader *Value) { - if (!Value) return ERR_Failed; + if (!Value) return ERR::Failed; Self->Header = Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -603,15 +603,15 @@ may use a `.dll` extension. **********************************************************************************************************************/ -static ERROR GET_Name(extModule *Self, CSTRING *Value) +static ERR GET_Name(extModule *Self, CSTRING *Value) { *Value = Self->Name; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_Name(extModule *Self, CSTRING Name) +static ERR SET_Name(extModule *Self, CSTRING Name) { - if (!Name) return ERR_Okay; + if (!Name) return ERR::Okay; LONG i; for (i=0; (Name[i]) and ((size_t)i < sizeof(Self->Name)-1); i++) { @@ -620,7 +620,7 @@ static ERROR SET_Name(extModule *Self, CSTRING Name) } Self->Name[i] = 0; - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -639,12 +639,12 @@ APTR build_jump_table(const Function *FList) log.trace("%d functions have been detected in the function list.", size); void **functions; - if (!AllocMemory((size+1) * sizeof(APTR), MEM::NO_CLEAR|MEM::UNTRACKED, (APTR *)&functions, NULL)) { + if (AllocMemory((size+1) * sizeof(APTR), MEM::NO_CLEAR|MEM::UNTRACKED, (APTR *)&functions, NULL) IS ERR::Okay) { for (LONG i=0; i < size; i++) functions[i] = FList[i].Address; functions[size] = NULL; return functions; } - else log.warning(ERR_AllocMemory); + else log.warning(ERR::AllocMemory); return NULL; } #endif @@ -710,7 +710,7 @@ static RootModule * check_resident(extModule *Self, CSTRING ModuleName) log.traceBranch("Module Name: %s", ModuleName); - if (!StrMatch("core", ModuleName)) { + if (StrMatch("core", ModuleName) IS ERR::Okay) { log.msg("Self-reference to the Core detected."); if (!kminit) { kminit = true; @@ -784,7 +784,7 @@ static const ActionArray glRootModuleActions[] = { //******************************************************************************************************************** -extern "C" ERROR add_module_class(void) +extern "C" ERR add_module_class(void) { if (!(glModuleClass = extMetaClass::create::global( fl::BaseClassID(ID_MODULE), @@ -797,7 +797,7 @@ extern "C" ERROR add_module_class(void) fl::Methods(glModuleMethods), fl::Fields(glModuleFields), fl::Size(sizeof(extModule)), - fl::Path("modules:core")))) return ERR_AddClass; + fl::Path("modules:core")))) return ERR::AddClass; if (!(glRootModuleClass = extMetaClass::create::global( fl::BaseClassID(ID_ROOTMODULE), @@ -808,8 +808,8 @@ extern "C" ERROR add_module_class(void) fl::Actions(glRootModuleActions), fl::Fields(glRootModuleFields), fl::Size(sizeof(RootModule)), - fl::Path("modules:core")))) return ERR_AddClass; + fl::Path("modules:core")))) return ERR::AddClass; - return ERR_Okay; + return ERR::Okay; } diff --git a/src/core/classes/class_script.cpp b/src/core/classes/class_script.cpp index d9a83225e..36d3c674f 100644 --- a/src/core/classes/class_script.cpp +++ b/src/core/classes/class_script.cpp @@ -25,18 +25,18 @@ Terminating the script will not remove objects that are outside its resource hie #include "../defs.h" #include -static ERROR GET_Results(objScript *, STRING **, LONG *); +static ERR GET_Results(objScript *, STRING **, LONG *); -static ERROR SET_Procedure(objScript *, CSTRING); -static ERROR SET_Results(objScript *, CSTRING *, LONG); -static ERROR SET_String(objScript *, CSTRING); +static ERR SET_Procedure(objScript *, CSTRING); +static ERR SET_Results(objScript *, CSTRING *, LONG); +static ERR SET_String(objScript *, CSTRING); -INLINE CSTRING check_bom(CSTRING Value) +inline CSTRING check_bom(const unsigned char *Value) { if ((Value[0] IS 0xef) and (Value[1] IS 0xbb) and (Value[2] IS 0xbf)) Value += 3; // UTF-8 BOM else if ((Value[0] IS 0xfe) and (Value[1] IS 0xff)) Value += 2; // UTF-16 BOM big endian else if ((Value[0] IS 0xff) and (Value[1] IS 0xfe)) Value += 2; // UTF-16 BOM little endian - return Value; + return (CSTRING)Value; } /********************************************************************************************************************* @@ -45,9 +45,9 @@ Activate: Executes the script. -END- *********************************************************************************************************************/ -static ERROR SCRIPT_Activate(objScript *Self, APTR Void) +static ERR SCRIPT_Activate(objScript *Self, APTR Void) { - return ERR_NoSupport; + return ERR::NoSupport; } /********************************************************************************************************************* @@ -56,9 +56,9 @@ DataFeed: Script source code can be passed to the object as XML or text via data -END- *********************************************************************************************************************/ -static ERROR SCRIPT_DataFeed(objScript *Self, struct acDataFeed *Args) +static ERR SCRIPT_DataFeed(objScript *Self, struct acDataFeed *Args) { - if (!Args) return ERR_NullArgs; + if (!Args) return ERR::NullArgs; if (Args->Datatype IS DATA::XML) { Self->setStatement((STRING)Args->Buffer); @@ -67,7 +67,7 @@ static ERROR SCRIPT_DataFeed(objScript *Self, struct acDataFeed *Args) Self->setStatement((STRING)Args->Buffer); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -91,10 +91,10 @@ ptr(func) Procedure: The function to be dereferenced. *********************************************************************************************************************/ -static ERROR SCRIPT_DerefProcedure(objScript *Self, struct scDerefProcedure *Args) +static ERR SCRIPT_DerefProcedure(objScript *Self, struct scDerefProcedure *Args) { // It is the responsibility of the sub-class to override this method with something appropriate. - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -108,7 +108,7 @@ Private large ProcedureID: An identifier for the target procedure. cstruct(*ScriptArg) Args: Optional CSV string containing arguments to pass to the procedure. int TotalArgs: The total number of arguments in the Args parameter. -&int Error: The error code returned from the script, if any. +&error Error: The error code returned from the script, if any. -ERRORS- Okay: @@ -118,36 +118,36 @@ int TotalArgs: The total number of arguments in the Args parameter. *********************************************************************************************************************/ -static ERROR SCRIPT_Callback(objScript *Self, struct scCallback *Args) +static ERR SCRIPT_Callback(objScript *Self, struct scCallback *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); - if ((Args->TotalArgs < 0) or (Args->TotalArgs > 1024)) return log.warning(ERR_Args); + if (!Args) return log.warning(ERR::NullArgs); + if ((Args->TotalArgs < 0) or (Args->TotalArgs > 1024)) return log.warning(ERR::Args); - LARGE save_id = Self->ProcedureID; - CSTRING save_name = Self->Procedure; + auto save_id = Self->ProcedureID; + auto save_name = Self->Procedure; Self->ProcedureID = Args->ProcedureID; - Self->Procedure = NULL; + Self->Procedure = NULL; - const ScriptArg *saveargs = Self->ProcArgs; + const ScriptArg *save_args = Self->ProcArgs; Self->ProcArgs = Args->Args; - LONG savetotal = Self->TotalArgs; - Self->TotalArgs = Args->TotalArgs; + auto save_total = Self->TotalArgs; + Self->TotalArgs = Args->TotalArgs; auto saved_error = Self->Error; auto saved_error_msg = Self->ErrorString; Self->ErrorString = NULL; - Self->Error = ERR_Okay; + Self->Error = ERR::Okay; - ERROR error = acActivate(Self); + ERR error = acActivate(Self); Args->Error = Self->Error; Self->Error = saved_error; Self->ProcedureID = save_id; - Self->Procedure = save_name; - Self->ProcArgs = saveargs; - Self->TotalArgs = savetotal; + Self->Procedure = save_name; + Self->ProcArgs = save_args; + Self->TotalArgs = save_total; if (Self->ErrorString) FreeResource(Self->ErrorString); Self->ErrorString = saved_error_msg; @@ -219,37 +219,37 @@ Args: The TotalArgs value is invalid. *********************************************************************************************************************/ -static ERROR SCRIPT_Exec(objScript *Self, struct scExec *Args) +static ERR SCRIPT_Exec(objScript *Self, struct scExec *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); - if ((Args->TotalArgs < 0) or (Args->TotalArgs > 32)) return log.warning(ERR_Args); + if (!Args) return log.warning(ERR::NullArgs); + if ((Args->TotalArgs < 0) or (Args->TotalArgs > 32)) return log.warning(ERR::Args); - LARGE save_id = Self->ProcedureID; + auto save_id = Self->ProcedureID; CSTRING save_name = Self->Procedure; Self->ProcedureID = 0; Self->Procedure = Args->Procedure; - const ScriptArg *saveargs = Self->ProcArgs; + const ScriptArg *save_args = Self->ProcArgs; Self->ProcArgs = Args->Args; - LONG savetotal = Self->TotalArgs; + auto save_total = Self->TotalArgs; Self->TotalArgs = Args->TotalArgs; - ERROR error = acActivate(Self); + ERR error = acActivate(Self); Self->ProcedureID = save_id; - Self->Procedure = save_name; - Self->ProcArgs = saveargs; - Self->TotalArgs = savetotal; + Self->Procedure = save_name; + Self->ProcArgs = save_args; + Self->TotalArgs = save_total; return error; } //******************************************************************************************************************** -static ERROR SCRIPT_Free(objScript *Self, APTR Void) +static ERR SCRIPT_Free(objScript *Self, APTR Void) { if (Self->CacheFile) { FreeResource(Self->CacheFile); Self->CacheFile = NULL; } if (Self->Path) { FreeResource(Self->Path); Self->Path = NULL; } @@ -259,7 +259,7 @@ static ERROR SCRIPT_Free(objScript *Self, APTR Void) if (Self->ErrorString) { FreeResource(Self->ErrorString); Self->ErrorString = NULL; } if (Self->Results) { FreeResource(Self->Results); Self->Results = NULL; } Self->~objScript(); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -290,13 +290,13 @@ NullArgs *********************************************************************************************************************/ -static ERROR SCRIPT_GetProcedureID(objScript *Self, struct scGetProcedureID *Args) +static ERR SCRIPT_GetProcedureID(objScript *Self, struct scGetProcedureID *Args) { pf::Log log; - if ((!Args) or (!Args->Procedure) or (!Args->Procedure[0])) return log.warning(ERR_NullArgs); + if ((!Args) or (!Args->Procedure) or (!Args->Procedure[0])) return log.warning(ERR::NullArgs); Args->ProcedureID = StrHash(Args->Procedure, 0); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -305,43 +305,43 @@ GetVar: Script parameters can be retrieved through this action. -END- *********************************************************************************************************************/ -static ERROR SCRIPT_GetVar(objScript *Self, struct acGetVar *Args) +static ERR SCRIPT_GetVar(objScript *Self, struct acGetVar *Args) { pf::Log log; - if ((!Args) or (!Args->Buffer) or (!Args->Field)) return ERR_NullArgs; - if (Args->Size < 2) return log.warning(ERR_Args); + if ((!Args) or (!Args->Buffer) or (!Args->Field)) return ERR::NullArgs; + if (Args->Size < 2) return log.warning(ERR::Args); auto it = Self->Vars.find(Args->Field); if (it != Self->Vars.end()) { StrCopy(it->second, Args->Buffer, Args->Size); - return ERR_Okay; + return ERR::Okay; } else { Args->Buffer[0] = 0; - return ERR_UnsupportedField; + return ERR::UnsupportedField; } } //******************************************************************************************************************** -static ERROR SCRIPT_Init(objScript *Self, APTR Void) +static ERR SCRIPT_Init(objScript *Self, APTR Void) { pf::Log log; if (!Self->TargetID) { // Define the target if it has not been set already - log.debug("Target not set, defaulting to owner #%d.", Self->ownerID()); + log.detail("Target not set, defaulting to owner #%d.", Self->ownerID()); Self->TargetID = Self->ownerID(); } - if (Self->isSubClass()) return ERR_Okay; // Break here to let the sub-class continue initialisation + if (Self->isSubClass()) return ERR::Okay; // Break here to let the sub-class continue initialisation - return ERR_NoSupport; + return ERR::NoSupport; } //******************************************************************************************************************** -static ERROR SCRIPT_NewObject(objScript *Self, APTR Void) +static ERR SCRIPT_NewObject(objScript *Self, APTR Void) { new (Self) objScript; @@ -356,16 +356,16 @@ static ERROR SCRIPT_NewObject(objScript *Self, APTR Void) StrCopy("lang", Self->LanguageDir, sizeof(Self->LanguageDir)); - return ERR_Okay; + return ERR::Okay; } // If reset, the script will be reloaded from the original file location the next time an activation occurs. All // arguments are also reset. -static ERROR SCRIPT_Reset(objScript *Self, APTR Void) +static ERR SCRIPT_Reset(objScript *Self, APTR Void) { Self->Vars.clear(); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -374,19 +374,19 @@ SetVar: Script parameters can be set through this action. -END- *********************************************************************************************************************/ -static ERROR SCRIPT_SetVar(objScript *Self, struct acSetVar *Args) +static ERR SCRIPT_SetVar(objScript *Self, struct acSetVar *Args) { pf::Log log; // It is acceptable to set zero-length string values (this has its uses in some scripts). - if ((!Args) or (!Args->Field) or (!Args->Value)) return ERR_NullArgs; - if (!Args->Field[0]) return ERR_NullArgs; + if ((!Args) or (!Args->Field) or (!Args->Value)) return ERR::NullArgs; + if (!Args->Field[0]) return ERR::NullArgs; log.trace("%s = %s", Args->Field, Args->Value); Self->Vars[Args->Field] = Args->Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -403,17 +403,17 @@ date stamps on the original and cache files. *********************************************************************************************************************/ -static ERROR GET_CacheFile(objScript *Self, STRING *Value) +static ERR GET_CacheFile(objScript *Self, STRING *Value) { *Value = Self->CacheFile; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_CacheFile(objScript *Self, CSTRING Value) +static ERR SET_CacheFile(objScript *Self, CSTRING Value) { if (Self->CacheFile) { FreeResource(Self->CacheFile); Self->CacheFile = NULL; } if (Value) Self->CacheFile = StrClone(Value); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -430,7 +430,7 @@ will be set to -1. -FIELD- Error: If a script fails during execution, an error code may be readable here. -On execution of a script, the Error value is reset to ERR_Okay and will be updated if the script fails. Be mindful +On execution of a script, the Error value is reset to ERR::Okay and will be updated if the script fails. Be mindful that if a script is likely to be executed recursively then the first thrown error will have priority and be propagated through the call stack. @@ -439,17 +439,17 @@ ErrorString: A human readable error string may be declared here following a scri *********************************************************************************************************************/ -static ERROR GET_ErrorString(objScript *Self, STRING *Value) +static ERR GET_ErrorString(objScript *Self, STRING *Value) { *Value = Self->ErrorString; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_ErrorString(objScript *Self, CSTRING Value) +static ERR SET_ErrorString(objScript *Self, CSTRING Value) { if (Self->ErrorString) { FreeResource(Self->ErrorString); Self->ErrorString = NULL; } if (Value) Self->ErrorString = StrClone(Value); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -466,10 +466,10 @@ code for international English. *********************************************************************************************************************/ -static ERROR GET_Language(objScript *Self, STRING *Value) +static ERR GET_Language(objScript *Self, STRING *Value) { *Value = Self->Language; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -481,16 +481,14 @@ The LineOffset is a value that is added to all line numbers that are referenced primarily intended for internal usage only. -FIELD- -Path: The location of the file that is to be processed as a script. +Path: The location of a script file to be loaded. -Script files can be loaded by a script object by setting the Path field to the path of the source file. The -source must be provided prior to the initialisation process or the script object will fail (as an alternative, the -#Statement field can also be set). +A script file can be loaded by setting the Path to its location. The path must be defined prior to the initialisation +process, or alternatively the client can define the #Statement field. -Special parameters can also be passed to the script when setting the location. The name of an executable procedure -may be passed by following the location with a semicolon, then the name of the procedure to execute. Arguments -can also be passed to the script by following this with a second semicolon, then a sequence of arguments, each -separated with a comma. The following string illustrates the format used: +Optional parameters can also be passed to the script via the Path string. The name of a function is passed first, +surrounded by semicolons. Arguments can be passed to the function by appending them as a CSV list. The following +string illustrates the format used:
    dir:location;procedure;arg1=val1,arg2,arg3=val2
     
    @@ -500,13 +498,13 @@ valid existing object).
     
     *********************************************************************************************************************/
     
    -static ERROR GET_Path(objScript *Self, STRING *Value)
    +static ERR GET_Path(objScript *Self, STRING *Value)
     {
        *Value = Self->Path;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
    -static ERROR SET_Path(objScript *Self, CSTRING Value)
    +static ERR SET_Path(objScript *Self, CSTRING Value)
     {
        if (Self->Path) {
           // If the location has already been set, throw the value to SetVar instead.
    @@ -520,90 +518,93 @@ static ERROR SET_Path(objScript *Self, CSTRING Value)
           if (Self->String)      { FreeResource(Self->String); Self->String = NULL; }
           if (Self->WorkingPath) { FreeResource(Self->WorkingPath); Self->WorkingPath = NULL; }
     
    -      LONG i, j, len;
    +      LONG i, len;
           if ((Value) and (*Value)) {
    -         if (!StrCompare("STRING:", Value, 7)) {
    +         if (StrCompare("STRING:", Value, 7) IS ERR::Okay) {
                 return SET_String(Self, Value + 7);
              }
     
              for (len=0; (Value[len]) and (Value[len] != ';'); len++);
     
    -         if (!AllocMemory(len+1, MEM::STRING|MEM::NO_CLEAR, (APTR *)&Self->Path, NULL)) {
    +         if (AllocMemory(len+1, MEM::STRING|MEM::NO_CLEAR, (APTR *)&Self->Path, NULL) IS ERR::Okay) {
                 for (i=0; i < len; i++) Self->Path[i] = Value[i];
                 Self->Path[i] = 0;
     
                 // If a semi-colon has been used, this indicates that a procedure follows the filename.
     
                 if (Value[i] IS ';') {
    -               char buffer[800], arg[100], argval[400];
    -
                    i++;
    -               while ((Value[i]) and (Value[i] <= 0x20)) i++;
    -               for (j=0; (Value[i]) and (Value[i] > 0x20) and (Value[i] != ';'); j++) buffer[j] = Value[i++];
    -               buffer[j] = 0;
    -               if (buffer[0]) SET_Procedure(Self, buffer);
    +               while ((Value[i]) and (unsigned(Value[i]) <= 0x20)) i++;
    +               auto start = i, end = i;
    +               while ((Value[end]) and (unsigned(Value[end]) > 0x20) and (Value[end] != ';')) end++;
    +               if (end > start) {
    +                  std::string buffer;
    +                  buffer.append(Value, start, end - start);
    +                  SET_Procedure(Self, buffer.c_str());
    +               }
     
    -               // The presence of an opening bracket precedes a series of arguments
    +               // Process optional parameters
     
    -               if (Value[i] IS ';') {
    -                  i++;
    +               if (Value[end] IS ';') {
    +                  char arg[100];
     
    +                  i = end + 1;
                       while (Value[i]) {
    -                     while ((Value[i]) and (Value[i] <= 0x20)) i++;
    +                     while ((Value[i]) and (unsigned(Value[i]) <= 0x20)) i++;
                          while (Value[i] IS ',') {
                             i++;
    -                        while ((Value[i]) and (Value[i] <= 0x20)) i++;
    +                        while ((Value[i]) and (unsigned(Value[i]) <= 0x20)) i++;
                          }
     
                          // Extract arg name
     
    -                     for (j=0; (Value[i] != ',') and (Value[i] != '=') and (Value[i] > 0x20); j++) arg[j] = Value[i++];
    +                     LONG j;
    +                     for (j=0; (Value[i] != ',') and (Value[i] != '=') and (unsigned(Value[i]) > 0x20); j++) arg[j] = Value[i++];
                          arg[j] = 0;
     
                          while ((Value[i]) and (Value[i] <= 0x20)) i++;
     
                          // Extract arg value
     
    -                     argval[0] = '1';
    -                     argval[1] = 0;
    +                     std::string argval("1");
                          if (Value[i] IS '=') {
                             i++;
    -                        while ((Value[i]) and (Value[i] <= 0x20)) i++;
    +                        while ((Value[i]) and (unsigned(Value[i]) <= 0x20)) i++;
                             if (Value[i] IS '"') {
                                i++;
    -                           for (j=0; (Value[i]) and (Value[i] != '"'); j++) argval[j] = Value[i++];
    -                           argval[j] = 0;
    +                           for (j=0; (Value[i+j]) and (Value[i+j] != '"'); j++);
    +                           argval.assign(Value, i, j);
                             }
                             else {
    -                           for (j=0; (Value[i]) and (Value[i] != ','); j++) argval[j] = Value[i++];
    -                           argval[j] = 0;
    +                           for (j=0; (Value[i+j]) and (Value[i+j] != ','); j++);
    +                           argval.assign(Value, i, j);
                             }
                          }
     
    -                     if (!StrMatch("target", arg)) Self->setTarget(StrToInt(argval));
    -                     else acSetVar(Self, arg, argval);
    +                     if (StrMatch("target", arg) IS ERR::Okay) Self->setTarget(StrToInt(argval));
    +                     else acSetVar(Self, arg, argval.c_str());
                       }
                    }
                 }
              }
    -         else return ERR_AllocMemory;
    +         else return ERR::AllocMemory;
           }
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     // Internal: Name
     
    -static ERROR SET_Name(objScript *Self, CSTRING Name)
    +static ERR SET_Name(objScript *Self, CSTRING Name)
     {
        if (Name) {
           SetName(Self, Name);
           struct acSetVar args = { .Field = "Name", .Value = Name };
           return SCRIPT_SetVar(Self, &args);
        }
    -   else return ERR_Okay;
    +   else return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -620,36 +621,36 @@ script activation - something to try when we have the time?
     
     *********************************************************************************************************************/
     
    -static ERROR GET_Owner(objScript *Self, OBJECTID *Value)
    +static ERR GET_Owner(objScript *Self, OBJECTID *Value)
     {
        if (Self->ScriptOwnerID) *Value = Self->ScriptOwnerID;
        else *Value = Self->ownerID();
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
    -static ERROR SET_Owner(objScript *Self, OBJECTID Value)
    +static ERR SET_Owner(objScript *Self, OBJECTID Value)
     {
        pf::Log log;
     
        if (Value) {
           OBJECTPTR newowner;
    -      if (!AccessObject(Value, 2000, &newowner)) {
    +      if (AccessObject(Value, 2000, &newowner) IS ERR::Okay) {
              SetOwner(Self, newowner);
              ReleaseObject(newowner);
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
    -      else return log.warning(ERR_ExclusiveDenied);
    +      else return log.warning(ERR::ExclusiveDenied);
        }
    -   else return log.warning(ERR_Args);
    +   else return log.warning(ERR::Args);
     }
     
     /*********************************************************************************************************************
     
     -FIELD-
    -Procedure: Allows you to specify a procedure to be executed from within a script.
    +Procedure: Specifies a procedure to be executed from within a script.
     
     Sometimes scripts are split into several procedures or functions that can be executed independently from the 'main'
    -area of the script.  If a script that you have loaded contains procedures, you can set the Procedure field to execute a
    +area of the script.  If a loaded script contains procedures, the client can set the Procedure field to execute a
     specific routine whenever the script is activated with the Activate action.
     
     If this field is not set, the first procedure in the script, or the 'main' procedure (as defined by the script type) is
    @@ -657,17 +658,17 @@ executed by default.
     
     *********************************************************************************************************************/
     
    -static ERROR GET_Procedure(objScript *Self, CSTRING *Value)
    +static ERR GET_Procedure(objScript *Self, CSTRING *Value)
     {
        *Value = Self->Procedure;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
    -static ERROR SET_Procedure(objScript *Self, CSTRING Value)
    +static ERR SET_Procedure(objScript *Self, CSTRING Value)
     {
        if (Self->Procedure) { FreeResource(Self->Procedure); Self->Procedure = NULL; }
        if (Value) Self->Procedure = StrClone(Value);
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -682,21 +683,21 @@ For maximum compatibility in type conversion, the results are stored as an array
     
     *********************************************************************************************************************/
     
    -static ERROR GET_Results(objScript *Self, STRING **Value, LONG *Elements)
    +static ERR GET_Results(objScript *Self, STRING **Value, LONG *Elements)
     {
        if (Self->Results) {
           *Value = Self->Results;
           *Elements = Self->ResultsTotal;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
        else {
           *Value = NULL;
           *Elements = 0;
    -      return ERR_FieldNotSet;
    +      return ERR::FieldNotSet;
        }
     }
     
    -static ERROR SET_Results(objScript *Self, CSTRING *Value, LONG Elements)
    +static ERR SET_Results(objScript *Self, CSTRING *Value, LONG Elements)
     {
        pf::Log log;
     
    @@ -707,12 +708,12 @@ static ERROR SET_Results(objScript *Self, CSTRING *Value, LONG Elements)
        if (Value) {
           LONG len = 0;
           for (LONG i=0; i < Elements; i++) {
    -         if (!Value[i]) return log.warning(ERR_InvalidData);
    +         if (!Value[i]) return log.warning(ERR::InvalidData);
              len += StrLength(Value[i]) + 1;
           }
           Self->ResultsTotal = Elements;
     
    -      if (!AllocMemory((sizeof(CSTRING) * (Elements+1)) + len, MEM::STRING|MEM::NO_CLEAR, (APTR *)&Self->Results, NULL)) {
    +      if (AllocMemory((sizeof(CSTRING) * (Elements+1)) + len, MEM::STRING|MEM::NO_CLEAR, (APTR *)&Self->Results, NULL) IS ERR::Okay) {
              STRING str = (STRING)(Self->Results + Elements + 1);
              LONG i;
              for (i=0; Value[i]; i++) {
    @@ -720,11 +721,11 @@ static ERROR SET_Results(objScript *Self, CSTRING *Value, LONG Elements)
                 str += StrCopy(Value[i], str) + 1;
              }
              Self->Results[i] = NULL;
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
    -      else return ERR_AllocMemory;
    +      else return ERR::AllocMemory;
        }
    -   else return ERR_Okay;
    +   else return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -738,19 +739,19 @@ It is also commonly used for executing scripts that have been embedded into prog
     
     *********************************************************************************************************************/
     
    -static ERROR GET_String(objScript *Self, CSTRING *Value)
    +static ERR GET_String(objScript *Self, CSTRING *Value)
     {
        *Value = Self->String;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
    -static ERROR SET_String(objScript *Self, CSTRING Value)
    +static ERR SET_String(objScript *Self, CSTRING Value)
     {
        if (Self->Path) { FreeResource(Self->Path); Self->Path = NULL; } // Path removed when a statement string is being set
        if (Self->String) { FreeResource(Self->String); Self->String = NULL; }
     
    -   if (Value) Self->String = StrClone(check_bom(Value));
    -   return ERR_Okay;
    +   if (Value) Self->String = StrClone(check_bom((const unsigned char *)Value));
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -765,24 +766,24 @@ field is not set, the root-level objects in the script will be initialised to th
     TotalArgs: Reflects the total number of arguments used in a script object.
     
     The total number of arguments that have been set in a script object through the unlisted field mechanism are reflected
    -in the value of this field.  If you have not set any arguments then the field value will be zero.
    +in the value of this field.
     -END-
     *********************************************************************************************************************/
     
    -static ERROR GET_TotalArgs(objScript *Self, LONG *Value)
    +static ERR GET_TotalArgs(objScript *Self, LONG *Value)
     {
        *Value = Self->Vars.size();
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
     PRIVATE: Variables
     *********************************************************************************************************************/
     
    -static ERROR GET_Variables(objScript *Self, std::map **Value)
    +static ERR GET_Variables(objScript *Self, std::map **Value)
     {
        *Value = &Self->Vars;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -796,31 +797,29 @@ loaded, without the file name.  If this cannot be determined then the working pa
     
     The working path is always fully qualified with a slash or colon at the end of the string.
     
    -You can manually change the working path by setting this field with a custom string.
    +A client can manually change the working path by setting this field with a custom string.
     -END-
     
     *********************************************************************************************************************/
     
    -static ERROR GET_WorkingPath(objScript *Self, STRING *Value)
    +static ERR GET_WorkingPath(objScript *Self, STRING *Value)
     {
        pf::Log log;
     
    -   // The working path is determined when the first attempt to read it is made.
    -
        if (!Self->WorkingPath) {
           if (!Self->Path) {
              log.warning("Script has no defined Path.");
    -         return ERR_MissingPath;
    +         return ERR::MissingPath;
           }
     
           // Determine if an absolute path has been indicated
     
    -      UBYTE path = FALSE;
    -      if (Self->Path[0] IS '/') path = TRUE;
    +      bool path = false;
    +      if (Self->Path[0] IS '/') path = true;
           else {
             for (LONG j=0; (Self->Path[j]) and (Self->Path[j] != '/') and (Self->Path[j] != '\\'); j++) {
                 if (Self->Path[j] IS ':') {
    -               path = TRUE;
    +               path = true;
                    break;
                 }
              }
    @@ -832,7 +831,6 @@ static ERROR GET_WorkingPath(objScript *Self, STRING *Value)
              if ((Self->Path[k] IS ':') or (Self->Path[k] IS '/') or (Self->Path[k] IS '\\')) j = k+1;
           }
     
    -      STRING workingpath;
           if (path) { // Extract absolute path
              pf::SwitchContext ctx(Self);
              char save = Self->Path[j];
    @@ -840,36 +838,32 @@ static ERROR GET_WorkingPath(objScript *Self, STRING *Value)
              Self->WorkingPath = StrClone(Self->Path);
              Self->Path[j] = save;
           }
    -      else if ((!CurrentTask()->get(FID_Path, &workingpath)) and (workingpath)) {
    -         char buf[1024];
    -
    -         // Using ResolvePath() can help to determine relative paths such as "../path/file"
    +      else {
    +         STRING working_path;
    +         if ((CurrentTask()->get(FID_Path, &working_path) IS ERR::Okay) and (working_path)) {
    +            // Using ResolvePath() can help to determine relative paths such as "../path/file"
     
    -         if (j > 0) {
    -            char save = Self->Path[j];
    -            Self->Path[j] = 0;
    -            snprintf(buf, sizeof(buf), "%s%s", workingpath, Self->Path);
    -            Self->Path[j] = save;
    -         }
    -         else snprintf(buf, sizeof(buf), "%s", workingpath);
    +            std::string buf = working_path;
    +            if (j > 0) buf.append(Self->Path, 0, j);
     
    -         pf::SwitchContext ctx(Self);
    -         if (ResolvePath(buf, RSF::APPROXIMATE, &Self->WorkingPath) != ERR_Okay) {
    -            Self->WorkingPath = StrClone(workingpath);
    +            pf::SwitchContext ctx(Self);
    +            if (ResolvePath(buf.c_str(), RSF::APPROXIMATE, &Self->WorkingPath) != ERR::Okay) {
    +               Self->WorkingPath = StrClone(working_path);
    +            }
              }
    +         else log.warning("No working path.");
           }
    -      else log.warning("No working path.");
        }
     
        *Value = Self->WorkingPath;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
    -static ERROR SET_WorkingPath(objScript *Self, STRING Value)
    +static ERR SET_WorkingPath(objScript *Self, STRING Value)
     {
        if (Self->WorkingPath) { FreeResource(Self->WorkingPath); Self->WorkingPath = NULL; }
        if (Value) Self->WorkingPath = StrClone(Value);
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
    @@ -903,7 +897,7 @@ static const FieldArray clScriptFields[] = {
     
     //********************************************************************************************************************
     
    -extern "C" ERROR add_script_class(void)
    +extern "C" ERR add_script_class(void)
     {
        glScriptClass = extMetaClass::create::global(
           fl::ClassVersion(VER_SCRIPT),
    @@ -915,5 +909,5 @@ extern "C" ERROR add_script_class(void)
           fl::Size(sizeof(objScript)),
           fl::Path("modules:core"));
     
    -   return glScriptClass ? ERR_Okay : ERR_AddClass;
    +   return glScriptClass ? ERR::Okay : ERR::AddClass;
     }
    diff --git a/src/core/classes/class_script_def.c b/src/core/classes/class_script_def.c
    index b20b14b45..72bf2eb40 100644
    --- a/src/core/classes/class_script_def.c
    +++ b/src/core/classes/class_script_def.c
    @@ -8,7 +8,7 @@ static const struct FieldDef clScriptFlags[] = {
     
     FDEF maExec[] = { { "Procedure", FD_STR }, { "ScriptArg:Args", FD_PTR|FD_STRUCT }, { "TotalArgs", FD_LONG }, { 0, 0 } };
     FDEF maDerefProcedure[] = { { "Procedure", FD_FUNCTIONPTR }, { 0, 0 } };
    -FDEF maCallback[] = { { "ProcedureID", FD_LARGE }, { "ScriptArg:Args", FD_PTR|FD_STRUCT }, { "TotalArgs", FD_LONG }, { "Error", FD_LONG|FD_RESULT }, { 0, 0 } };
    +FDEF maCallback[] = { { "ProcedureID", FD_LARGE }, { "ScriptArg:Args", FD_PTR|FD_STRUCT }, { "TotalArgs", FD_LONG }, { "Error", FD_LONG|FD_ERROR|FD_RESULT }, { 0, 0 } };
     FDEF maGetProcedureID[] = { { "Procedure", FD_STR }, { "ProcedureID", FD_LARGE|FD_RESULT }, { 0, 0 } };
     
     static const struct MethodEntry clScriptMethods[] = {
    diff --git a/src/core/classes/class_storagedevice.cpp b/src/core/classes/class_storagedevice.cpp
    index 4b549126f..ee0a7eaaf 100644
    --- a/src/core/classes/class_storagedevice.cpp
    +++ b/src/core/classes/class_storagedevice.cpp
    @@ -20,24 +20,24 @@ Following initialisation, all meta fields describing the volume are readable for
     #define PRV_FILESYSTEM
     #include "../defs.h"
     
    -static ERROR STORAGE_Free(extStorageDevice *, APTR);
    -static ERROR STORAGE_Init(extStorageDevice *, APTR);
    +static ERR STORAGE_Free(extStorageDevice *, APTR);
    +static ERR STORAGE_Init(extStorageDevice *, APTR);
     
     //********************************************************************************************************************
     
    -static ERROR STORAGE_Free(extStorageDevice *Self, APTR Void)
    +static ERR STORAGE_Free(extStorageDevice *Self, APTR Void)
     {
        if (Self->Volume) { FreeResource(Self->Volume); Self->Volume = NULL; }
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     
    -static ERROR STORAGE_Init(extStorageDevice *Self, APTR Void)
    +static ERR STORAGE_Init(extStorageDevice *Self, APTR Void)
     {
        pf::Log log;
     
    -   if (!Self->Volume) return log.warning(ERR_FieldNotSet);
    +   if (!Self->Volume) return log.warning(ERR::FieldNotSet);
     
        const virtual_drive *vd = get_fs(Self->Volume);
     
    @@ -48,7 +48,7 @@ static ERROR STORAGE_Init(extStorageDevice *Self, APTR Void)
        Self->DeviceSize = -1;
     
        if (vd->GetDeviceInfo) return vd->GetDeviceInfo(Self->Volume, Self);
    -   else return ERR_Okay;
    +   else return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -71,15 +71,15 @@ If a volume expresses a unique device identifier such as a factory serial number
     
     *********************************************************************************************************************/
     
    -static ERROR GET_DeviceID(extStorageDevice *Self, STRING *Value)
    +static ERR GET_DeviceID(extStorageDevice *Self, STRING *Value)
     {
        if (Self->DeviceID) {
           *Value = Self->DeviceID;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
        else {
           *Value = NULL;
    -      return ERR_FieldNotSet;
    +      return ERR::FieldNotSet;
        }
     }
     
    @@ -104,23 +104,23 @@ acceptable.  Any characters following a colon will be stripped automatically wit
     
     *********************************************************************************************************************/
     
    -static ERROR GET_Volume(extStorageDevice *Self, STRING *Value)
    +static ERR GET_Volume(extStorageDevice *Self, STRING *Value)
     {
        if (Self->Volume) {
           *Value = Self->Volume;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
        else {
           *Value = NULL;
    -      return ERR_FieldNotSet;
    +      return ERR::FieldNotSet;
        }
     }
     
    -static ERROR SET_Volume(extStorageDevice *Self, CSTRING Value)
    +static ERR SET_Volume(extStorageDevice *Self, CSTRING Value)
     {
        pf::Log log;
     
    -   if (Self->initialised()) return log.warning(ERR_Immutable);
    +   if (Self->initialised()) return log.warning(ERR::Immutable);
     
        if ((Value) and (*Value)) {
           LONG len;
    @@ -128,15 +128,15 @@ static ERROR SET_Volume(extStorageDevice *Self, CSTRING Value)
     
           if (Self->Volume) FreeResource(Self->Volume);
     
    -      if (!AllocMemory(len+2, MEM::STRING|MEM::NO_CLEAR, (APTR *)&Self->Volume, NULL)) {
    +      if (AllocMemory(len+2, MEM::STRING|MEM::NO_CLEAR, (APTR *)&Self->Volume, NULL) IS ERR::Okay) {
              CopyMemory(Value, Self->Volume, len);
              Self->Volume[len] = ':';
              Self->Volume[len+1] = 0;
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
    -      else return log.warning(ERR_AllocMemory);
    +      else return log.warning(ERR::AllocMemory);
        }
    -   else return ERR_Okay;
    +   else return ERR::Okay;
     }
     
     //********************************************************************************************************************
    @@ -179,7 +179,7 @@ static const ActionArray clActions[] = {
     
     //********************************************************************************************************************
     
    -extern "C" ERROR add_storage_class(void)
    +extern "C" ERR add_storage_class(void)
     {
        glStorageClass = extMetaClass::create::global(
           fl::BaseClassID(ID_STORAGEDEVICE),
    @@ -191,5 +191,5 @@ extern "C" ERROR add_storage_class(void)
           fl::Size(sizeof(extStorageDevice)),
           fl::Path("modules:core"));
     
    -   return glStorageClass ? ERR_Okay : ERR_AddClass;
    +   return glStorageClass ? ERR::Okay : ERR::AddClass;
     }
    diff --git a/src/core/classes/class_task.cpp b/src/core/classes/class_task.cpp
    index 234e75ab9..3db64c329 100644
    --- a/src/core/classes/class_task.cpp
    +++ b/src/core/classes/class_task.cpp
    @@ -15,7 +15,7 @@ To execute a compiled program, set the #Location field to point to the executabl
     task.  Arguments can be passed to the executable by setting the #Parameters field.  Once the task object is
     successfully initialised, use the #Activate() action to run the executable.  If the file executes successfully,
     a new task object is spawned separately to represent the executable (which means it is safe to destroy your task object
    -immediately afterwards).  If the #Activate() action returns with ERR_Okay then the executable program was run
    +immediately afterwards).  If the #Activate() action returns with ERR::Okay then the executable program was run
     successfully.
     
     To find the task object that represents the active process, use the ~CurrentTask() function to quickly retrieve it.
    @@ -94,21 +94,21 @@ extern "C" DLLCALL LONG WINAPI RegSetValueExA(APTR hKey, CSTRING lpValueName, LO
     static LONG glProcessBreak = 0;
     #endif
     
    -static ERROR GET_LaunchPath(extTask *, STRING *);
    +static ERR GET_LaunchPath(extTask *, STRING *);
     
    -static ERROR TASK_Activate(extTask *, APTR);
    -static ERROR TASK_Free(extTask *, APTR);
    -static ERROR TASK_GetEnv(extTask *, struct taskGetEnv *);
    -static ERROR TASK_GetVar(extTask *, struct acGetVar *);
    -static ERROR TASK_Init(extTask *, APTR);
    -static ERROR TASK_NewObject(extTask *, APTR);
    -static ERROR TASK_SetEnv(extTask *, struct taskSetEnv *);
    -static ERROR TASK_SetVar(extTask *, struct acSetVar *);
    -static ERROR TASK_Write(extTask *, struct acWrite *);
    +static ERR TASK_Activate(extTask *, APTR);
    +static ERR TASK_Free(extTask *, APTR);
    +static ERR TASK_GetEnv(extTask *, struct taskGetEnv *);
    +static ERR TASK_GetVar(extTask *, struct acGetVar *);
    +static ERR TASK_Init(extTask *, APTR);
    +static ERR TASK_NewObject(extTask *, APTR);
    +static ERR TASK_SetEnv(extTask *, struct taskSetEnv *);
    +static ERR TASK_SetVar(extTask *, struct acSetVar *);
    +static ERR TASK_Write(extTask *, struct acWrite *);
     
    -static ERROR TASK_AddArgument(extTask *, struct taskAddArgument *);
    -static ERROR TASK_Expunge(extTask *, APTR);
    -static ERROR TASK_Quit(extTask *, APTR);
    +static ERR TASK_AddArgument(extTask *, struct taskAddArgument *);
    +static ERR TASK_Expunge(extTask *, APTR);
    +static ERR TASK_Quit(extTask *, APTR);
     
     static const FieldDef clFlags[] = {
        { "Foreign",    TSF::FOREIGN },
    @@ -143,46 +143,38 @@ static void task_stdinput_callback(HOSTHANDLE FD, void *Task)
     {
        auto Self = (extTask *)Task;
        char buffer[4096];
    -   ERROR error;
    +   ERR error;
     
     #ifdef _WIN32
        LONG bytes_read;
    -   LONG result = winReadStdInput(FD, buffer, sizeof(buffer)-1, &bytes_read);
    -   if (!result) {
    -      error = ERR_Okay;
    -   }
    -   else if (result IS 1) {
    -      return;
    -   }
    +   auto result = winReadStdInput(FD, buffer, sizeof(buffer)-1, &bytes_read);
    +   if (!result) error = ERR::Okay;
    +   else if (result IS 1) return;
        else if (result IS -2) {
    -      error = ERR_Finished;
    +      error = ERR::Finished;
           RegisterFD(winGetStdInput(), RFD::READ|RFD::REMOVE, &task_stdinput_callback, Self);
        }
    -   else {
    -      error = ERR_Failed;
    -      return;
    -   }
    +   else return;
     #else
        LONG bytes_read = read(fileno(stdin), buffer, sizeof(buffer)-1);
    -   if (bytes_read >= 0) error = ERR_Okay;
    -   else error = ERR_Finished;
    +   if (bytes_read >= 0) error = ERR::Okay;
    +   else error = ERR::Finished;
     #endif
     
        buffer[bytes_read] = 0;
     
    -   if (Self->InputCallback.Type IS CALL_STDC) {
    -      auto routine = (void (*)(extTask *, APTR, LONG, ERROR))Self->InputCallback.StdC.Routine;
    -      routine(Self, buffer, bytes_read, error);
    +   if (Self->InputCallback.isC()) {
    +      auto routine = (void (*)(extTask *, APTR, LONG, ERR, APTR))Self->InputCallback.StdC.Routine;
    +      routine(Self, buffer, bytes_read, error, Self->InputCallback.StdC.Meta);
        }
    -   else if (Self->InputCallback.Type IS CALL_SCRIPT) {
    -      auto script = Self->InputCallback.Script.Script;
    +   else if (Self->InputCallback.isScript()) {
           const ScriptArg args[] = {
              { "Task",       Self },
              { "Buffer",     buffer, FD_PTRBUFFER },
              { "BufferSize", bytes_read, FD_LONG|FD_BUFSIZE },
    -         { "Status",     error, FD_ERROR }
    +         { "Status",     LONG(error), FD_ERROR }
           };
    -      scCallback(script, Self->InputCallback.Script.ProcedureID, args, ARRAYSIZE(args), NULL);
    +      scCallback(Self->InputCallback.Script.Script, Self->InputCallback.Script.ProcedureID, args, std::ssize(args), NULL);
        }
     }
     
    @@ -228,20 +220,17 @@ static void task_stdout(HOSTHANDLE FD, APTR Task)
           buffer[len] = 0;
     
           auto task = (extTask *)Task;
    -      if (task->OutputCallback.Type IS CALL_STDC) {
    -         auto routine = (void (*)(extTask *, APTR, LONG))task->OutputCallback.StdC.Routine;
    -         routine(task, buffer, len);
    +      if (task->OutputCallback.isC()) {
    +         auto routine = (void (*)(extTask *, APTR, LONG, APTR))task->OutputCallback.StdC.Routine;
    +         routine(task, buffer, len, task->OutputCallback.StdC.Meta);
           }
    -      else if (task->OutputCallback.Type IS CALL_SCRIPT) {
    -         OBJECTPTR script;
    -         if ((script = task->OutputCallback.Script.Script)) {
    -            const ScriptArg args[] = {
    -               { "Task",       Task,   FD_OBJECTPTR },
    -               { "Buffer",     buffer, FD_PTRBUFFER },
    -               { "BufferSize", len,    FD_LONG|FD_BUFSIZE }
    -            };
    -            scCallback(script, task->OutputCallback.Script.ProcedureID, args, ARRAYSIZE(args), NULL);
    -         }
    +      else if (task->OutputCallback.isScript()) {
    +         const ScriptArg args[] = {
    +            { "Task",       Task,   FD_OBJECTPTR },
    +            { "Buffer",     buffer, FD_PTRBUFFER },
    +            { "BufferSize", len,    FD_LONG|FD_BUFSIZE }
    +         };
    +         scCallback(task->OutputCallback.Script.Script, task->OutputCallback.Script.ProcedureID, args, std::ssize(args), NULL);
           }
        }
        recursive--;
    @@ -261,19 +250,18 @@ static void task_stderr(HOSTHANDLE FD, APTR Task)
     
           auto task = (extTask *)Task;
           if (task->ErrorCallback.Type) {
    -         if (task->ErrorCallback.Type IS CALL_STDC) {
    -            auto routine = (void (*)(extTask *, APTR, LONG))task->ErrorCallback.StdC.Routine;
    -            routine(task, buffer, len);
    +         if (task->ErrorCallback.isC()) {
    +            auto routine = (void (*)(extTask *, APTR, LONG, APTR))task->ErrorCallback.StdC.Routine;
    +            routine(task, buffer, len, task->ErrorCallback.StdC.Meta);
              }
    -         else if (task->ErrorCallback.Type IS CALL_SCRIPT) {
    -            OBJECTPTR script;
    -            if ((script = task->ErrorCallback.Script.Script)) {
    +         else if (task->ErrorCallback.isScript()) {
    +            if (auto script = task->ErrorCallback.Script.Script) {
                    const ScriptArg args[] = {
                       { "Task", Task, FD_OBJECTPTR },
                       { "Data", buffer, FD_PTRBUFFER },
                       { "Size", len, FD_LONG|FD_BUFSIZE }
                    };
    -               scCallback(script, task->ErrorCallback.Script.ProcedureID, args, ARRAYSIZE(args), NULL);
    +               scCallback(script, task->ErrorCallback.Script.ProcedureID, args, std::ssize(args), NULL);
                 }
              }
           }
    @@ -289,18 +277,18 @@ static void task_stderr(HOSTHANDLE FD, APTR Task)
     #ifdef _WIN32
     static void output_callback(extTask *Task, FUNCTION *Callback, APTR Buffer, LONG Size)
     {
    -   if (Callback->Type IS CALL_STDC) {
    -      auto routine = (void (*)(extTask *, APTR, LONG))Callback->StdC.Routine;
    -      routine(Task, Buffer, Size);
    +   if (Callback->isC()) {
    +      auto routine = (void (*)(extTask *, APTR, LONG, APTR))Callback->StdC.Routine;
    +      routine(Task, Buffer, Size, Callback->StdC.Meta);
        }
    -   else if (Callback->Type IS CALL_SCRIPT) {
    +   else if (Callback->isScript()) {
           auto script = Callback->Script.Script;
           const ScriptArg args[] = {
              { "Task", Task, FD_OBJECTPTR },
              { "Data", Buffer, FD_PTRBUFFER },
              { "Size", Size, FD_LONG|FD_BUFSIZE }
           };
    -      scCallback(script, Callback->Script.ProcedureID, args, ARRAYSIZE(args), NULL);
    +      scCallback(script, Callback->Script.ProcedureID, args, std::ssize(args), NULL);
        }
     }
     
    @@ -375,9 +363,9 @@ extern "C" void task_deregister_incoming(WINHANDLE Handle)
     
     //********************************************************************************************************************
     
    -static ERROR msg_waitforobjects(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize)
    +static ERR msg_waitforobjects(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize)
     {
    -   return ERR_Terminate;
    +   return ERR::Terminate;
     }
     
     //********************************************************************************************************************
    @@ -396,14 +384,14 @@ static CSTRING action_id_name(LONG ActionID)
     
     //********************************************************************************************************************
     
    -static ERROR msg_action(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize)
    +static ERR msg_action(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize)
     {
        pf::Log log("ProcessMessages");
        ActionMessage *action;
     
        if (!(action = (ActionMessage *)Message)) {
           log.warning("No data attached to MSGID_ACTION message.");
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
     
        #ifdef DBG_INCOMING
    @@ -412,8 +400,8 @@ static ERROR msg_action(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LON
     
        if ((action->ObjectID) and (action->ActionID)) {
           OBJECTPTR obj;
    -      ERROR error;
    -      if (!(error = AccessObject(action->ObjectID, 5000, &obj))) {
    +      ERR error;
    +      if ((error = AccessObject(action->ObjectID, 5000, &obj)) IS ERR::Okay) {
              if (action->SendArgs IS false) {
                 obj->Flags |= NF::MESSAGE;
                 Action(action->ActionID, obj, NULL);
    @@ -432,7 +420,7 @@ static ERROR msg_action(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LON
                 // Use resolve_args() to process the args structure back into something readable
     
                 if (fields) {
    -               if (!resolve_args(action+1, fields)) {
    +               if (resolve_args(action+1, fields) IS ERR::Okay) {
                       obj->Flags |= NF::MESSAGE;
                       Action(action->ActionID, obj, action+1);
                       obj->Flags = obj->Flags & (~NF::MESSAGE);
    @@ -448,7 +436,7 @@ static ERROR msg_action(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LON
              }
           }
           else {
    -         if ((error != ERR_NoMatchingObject) and (error != ERR_MarkedForDeletion)) {
    +         if ((error != ERR::NoMatchingObject) and (error != ERR::MarkedForDeletion)) {
                 if (action->ActionID > 0) log.warning("Could not gain access to object %d to execute action %s.", action->ObjectID, action_id_name(action->ActionID));
                 else log.warning("Could not gain access to object %d to execute method %d.", action->ObjectID, action->ActionID);
              }
    @@ -456,42 +444,42 @@ static ERROR msg_action(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LON
        }
        else log.warning("Action message %s specifies an object ID of #%d.", action_id_name(action->ActionID), action->ObjectID);
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     
    -static ERROR msg_quit(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize)
    +static ERR msg_quit(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize)
     {
        pf::Log log(__FUNCTION__);
        log.function("Processing quit message");
        glTaskState = TSTATE::STOPPING;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     // Determine whether or not a process is alive
     
    -extern "C" ERROR validate_process(LONG ProcessID)
    +extern "C" ERR validate_process(LONG ProcessID)
     {
        pf::Log log(__FUNCTION__);
        static LONG glValidating = 0;
     
        log.function("PID: %d", ProcessID);
     
    -   if (glValidating) return ERR_Okay;
    +   if (glValidating) return ERR::Okay;
        if (glValidateProcessID IS ProcessID) glValidateProcessID = 0;
    -   if ((ProcessID IS glProcessID) or (!ProcessID)) return ERR_Okay;
    +   if ((ProcessID IS glProcessID) or (!ProcessID)) return ERR::Okay;
     
        #ifdef _WIN32
           // On Windows we don't check if the process is alive because validation can often occur during the final shutdown
           // phase of the other process.
        #elif __unix__
           if ((kill(ProcessID, 0) IS -1) and (errno IS ESRCH));
    -      else return ERR_Okay;
    +      else return ERR::Okay;
        #else
           log.error("This platform does not support validate_process()");
    -      return ERR_Okay;
    +      return ERR::Okay;
        #endif
     
        OBJECTID task_id = 0;
    @@ -503,13 +491,13 @@ extern "C" ERROR validate_process(LONG ProcessID)
           }
        }
     
    -   if (!task_id) return ERR_False;
    +   if (!task_id) return ERR::False;
     
        evTaskRemoved task_removed = { GetEventID(EVG::SYSTEM, "task", "removed"), task_id, ProcessID };
        BroadcastEvent(&task_removed, sizeof(task_removed));
     
        glValidating = 0;
    -   return ERR_False; // Return ERR_False to indicate that the task was not healthy
    +   return ERR::False; // Return ERR::False to indicate that the task was not healthy
     }
     
     //********************************************************************************************************************
    @@ -560,14 +548,14 @@ static void task_process_end(WINHANDLE FD, extTask *Task)
     
        // Call ExitCallback, if specified
     
    -   if (Task->ExitCallback.Type IS CALL_STDC) {
    -      auto routine = (void (*)(extTask *))Task->ExitCallback.StdC.Routine;
    -      routine(Task);
    +   if (Task->ExitCallback.isC()) {
    +      auto routine = (void (*)(extTask *, APTR))Task->ExitCallback.StdC.Routine;
    +      routine(Task, Task->ExitCallback.StdC.Meta);
        }
    -   else if (Task->ExitCallback.Type IS CALL_SCRIPT) {
    +   else if (Task->ExitCallback.isScript()) {
           auto script = Task->ExitCallback.Script.Script;
           const ScriptArg args[] = { { "Task", Task, FD_OBJECTPTR } };
    -      scCallback(script, Task->ExitCallback.Script.ProcedureID, args, ARRAYSIZE(args), NULL);      
    +      scCallback(script, Task->ExitCallback.Script.ProcedureID, args, std::ssize(args), NULL);
        }
     
        // Post an event for the task's closure
    @@ -632,13 +620,13 @@ TimeOut:     Can be returned if the WAIT flag is used.  Indicates that the proce
     
     *********************************************************************************************************************/
     
    -static ERROR TASK_Activate(extTask *Self, APTR Void)
    +static ERR TASK_Activate(extTask *Self, APTR Void)
     {
        pf::Log log;
        LONG i, j, k;
        char buffer[1000];
        STRING path;
    -   ERROR error;
    +   ERR error;
        #ifdef _WIN32
           char launchdir[500];
           STRING redirect_stdout, redirect_stderr;
    @@ -654,11 +642,11 @@ static ERROR TASK_Activate(extTask *Self, APTR Void)
     
        if ((Self->Flags & TSF::FOREIGN) != TSF::NIL) Self->Flags |= TSF::SHELL;
     
    -   if (!Self->Location) return log.warning(ERR_MissingPath);
    +   if (!Self->Location) return log.warning(ERR::MissingPath);
     
        if (!glJanitorActive) {
           pf::SwitchContext ctx(glCurrentTask);
    -      auto call = make_function_stdc(process_janitor);
    +      auto call = FUNCTION(process_janitor);
           SubscribeTimer(60, &call, &glProcessJanitor);
           glJanitorActive = true;
        }
    @@ -667,8 +655,8 @@ static ERROR TASK_Activate(extTask *Self, APTR Void)
        // Determine the launch folder
     
        launchdir[0] = 0;
    -   if ((!GET_LaunchPath(Self, &path)) and (path)) {
    -      if (!ResolvePath(path, RSF::APPROXIMATE|RSF::PATH, &path)) {
    +   if ((GET_LaunchPath(Self, &path) IS ERR::Okay) and (path)) {
    +      if (ResolvePath(path, RSF::APPROXIMATE|RSF::PATH, &path) IS ERR::Okay) {
              for (i=0; (path[i]) and ((size_t)i < sizeof(launchdir)-1); i++) launchdir[i] = path[i];
              launchdir[i] = 0;
              FreeResource(path);
    @@ -679,7 +667,7 @@ static ERROR TASK_Activate(extTask *Self, APTR Void)
           }
        }
        else if ((Self->Flags & TSF::RESET_PATH) != TSF::NIL) {
    -      if (!ResolvePath(Self->Location, RSF::APPROXIMATE|RSF::PATH, &path)) {
    +      if (ResolvePath(Self->Location, RSF::APPROXIMATE|RSF::PATH, &path) IS ERR::Okay) {
              for (i=0; (path[i]) and ((size_t)i < sizeof(launchdir)-1); i++) launchdir[i] = path[i];
              FreeResource(path);
           }
    @@ -693,7 +681,7 @@ static ERROR TASK_Activate(extTask *Self, APTR Void)
     
        i = 0;
        buffer[i++] = '"';
    -   if (!ResolvePath(Self->Location, RSF::APPROXIMATE|RSF::PATH, &path)) {
    +   if (ResolvePath(Self->Location, RSF::APPROXIMATE|RSF::PATH, &path) IS ERR::Okay) {
           for (j=0; (path[j]) and ((size_t)i < sizeof(buffer)-1); i++,j++) {
              if (path[j] IS '/') buffer[i] = '\\';
              else buffer[i] = path[j];
    @@ -718,7 +706,7 @@ static ERROR TASK_Activate(extTask *Self, APTR Void)
           if (param[0] IS '>') {
              // Redirection argument detected
     
    -         if (!ResolvePath(param.c_str() + 1, RSF::NO_FILE_CHECK, &redirect_stdout)) {
    +         if (ResolvePath(param.c_str() + 1, RSF::NO_FILE_CHECK, &redirect_stdout) IS ERR::Okay) {
                 redirect_stderr = redirect_stdout;
              }
     
    @@ -813,7 +801,7 @@ static ERROR TASK_Activate(extTask *Self, APTR Void)
        if (!(winerror = winLaunchProcess(Self, buffer, (launchdir[0] != 0) ? launchdir : 0, group,
              internal_redirect, &Self->Platform, hide_output, redirect_stdout, redirect_stderr, &Self->ProcessID))) {
     
    -      error = ERR_Okay;
    +      error = ERR::Okay;
           if (((Self->Flags & TSF::WAIT) != TSF::NIL) and (Self->TimeOut > 0)) {
              log.msg("Waiting for process to exit.  TimeOut: %.2f sec", Self->TimeOut);
     
    @@ -830,7 +818,7 @@ static ERROR TASK_Activate(extTask *Self, APTR Void)
           char msg[300];
           winFormatMessage(winerror, msg, sizeof(msg));
           log.warning("Launch Error: %s", msg);
    -      error = ERR_Failed;
    +      error = ERR::Failed;
        }
     
        if (redirect_stderr IS redirect_stdout) redirect_stderr = NULL;
    @@ -950,7 +938,7 @@ static ERROR TASK_Activate(extTask *Self, APTR Void)
              log.warning("Failed to create pipe: %s", strerror(errno));
              if (input_fd != -1) close(input_fd);
              if (out_fd != -1)   close(out_fd);
    -         return ERR_Failed;
    +         return ERR::Failed;
           }
        }
     
    @@ -969,7 +957,7 @@ static ERROR TASK_Activate(extTask *Self, APTR Void)
              log.warning("Failed to create pipe: %s", strerror(errno));
              if (input_fd != -1) close(input_fd);
              if (out_fd != -1)   close(out_fd);
    -         return ERR_Failed;
    +         return ERR::Failed;
           }
        }
     
    @@ -991,7 +979,7 @@ static ERROR TASK_Activate(extTask *Self, APTR Void)
           if (in_fd != -1)     close(in_fd);
           if (in_errfd != -1)  close(in_errfd);
           log.warning("Failed in an attempt to fork().");
    -      return ERR_Failed;
    +      return ERR::Failed;
        }
     
        if (pid) {
    @@ -1022,7 +1010,7 @@ static ERROR TASK_Activate(extTask *Self, APTR Void)
              input_fd = -1;
           }
     
    -      error = ERR_Okay;
    +      error = ERR::Okay;
           if ((Self->Flags & TSF::WAIT) != TSF::NIL) {
              log.branch("Waiting for process to turn into a zombie in %.2fs.", Self->TimeOut);
     
    @@ -1036,7 +1024,7 @@ static ERROR TASK_Activate(extTask *Self, APTR Void)
     
                 auto remaining = ticks - PreciseTime();
                 if (remaining <= 0) {
    -               error = log.warning(ERR_TimeOut);
    +               error = log.warning(ERR::TimeOut);
                    break;
                 }
              }
    @@ -1130,9 +1118,9 @@ NullArgs
     
     *********************************************************************************************************************/
     
    -static ERROR TASK_AddArgument(extTask *Self, struct taskAddArgument *Args)
    +static ERR TASK_AddArgument(extTask *Self, struct taskAddArgument *Args)
     {
    -   if ((!Args) or (!Args->Argument) or (!*Args->Argument)) return ERR_NullArgs;
    +   if ((!Args) or (!Args->Argument) or (!*Args->Argument)) return ERR::NullArgs;
     
        auto src = Args->Argument;
        if ((*src IS '"') or (*src IS '\'')) {
    @@ -1143,7 +1131,7 @@ static ERROR TASK_AddArgument(extTask *Self, struct taskAddArgument *Args)
        }
        else Self->Parameters.emplace_back(Args->Argument);
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -1158,15 +1146,15 @@ Okay
     
     *********************************************************************************************************************/
     
    -static ERROR TASK_Expunge(extTask *Self, APTR Void)
    +static ERR TASK_Expunge(extTask *Self, APTR Void)
     {
        Expunge(false);
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     
    -static ERROR TASK_Free(extTask *Self, APTR Void)
    +static ERR TASK_Free(extTask *Self, APTR Void)
     {
        pf::Log log;
     
    @@ -1212,7 +1200,7 @@ static ERROR TASK_Free(extTask *Self, APTR Void)
        if (Self->MsgThreadAction)   { FreeResource(Self->MsgThreadAction);   Self->MsgThreadAction    = NULL; }
     
        Self->~extTask();
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -1221,7 +1209,7 @@ static ERROR TASK_Free(extTask *Self, APTR Void)
     GetEnv: Retrieves environment variables for the active process.
     
     On platforms that support environment variables, GetEnv() returns the value of the environment variable matching the
    -Name string.  If there is no matching variable, `ERR_DoesNotExist` is returned.
    +Name string.  If there is no matching variable, `ERR::DoesNotExist` is returned.
     
     In Windows, it is possible to look up registry keys if the string starts with one of the following (in all other
     cases, the system's environment variables are queried):
    @@ -1251,11 +1239,11 @@ NoSupport: The platform does not support environment variables.
     
     *********************************************************************************************************************/
     
    -static ERROR TASK_GetEnv(extTask *Self, struct taskGetEnv *Args)
    +static ERR TASK_GetEnv(extTask *Self, struct taskGetEnv *Args)
     {
        pf::Log log;
     
    -   if ((!Args) or (!Args->Name)) return log.warning(ERR_NullArgs);
    +   if ((!Args) or (!Args->Name)) return log.warning(ERR::NullArgs);
     
     #ifdef _WIN32
     
    @@ -1264,11 +1252,11 @@ static ERROR TASK_GetEnv(extTask *Self, struct taskGetEnv *Args)
     
        Args->Value = NULL;
     
    -   if (glCurrentTask != Self) return ERR_Failed;
    +   if (glCurrentTask != Self) return ERR::Failed;
     
        if (!Self->Env) {
    -      if (AllocMemory(ENV_SIZE, MEM::STRING|MEM::NO_CLEAR, (APTR *)&Self->Env, NULL) != ERR_Okay) {
    -         return ERR_AllocMemory;
    +      if (AllocMemory(ENV_SIZE, MEM::STRING|MEM::NO_CLEAR, (APTR *)&Self->Env, NULL) != ERR::Okay) {
    +         return ERR::AllocMemory;
           }
        }
     
    @@ -1284,8 +1272,8 @@ static ERROR TASK_GetEnv(extTask *Self, struct taskGetEnv *Args)
              { 0, 0 }
           };
     
    -      for (LONG ki=0; ki < ARRAYSIZE(keys); ki++) {
    -         if (!StrCompare(keys[ki].HKey, Args->Name)) {
    +      for (LONG ki=0; ki < std::ssize(keys); ki++) {
    +         if (StrCompare(keys[ki].HKey, Args->Name) IS ERR::Okay) {
                 CSTRING str = Args->Name + StrLength(keys[ki].HKey); // str = Parasol\Something
                 len = StrLength(str); // End of string
     
    @@ -1327,29 +1315,29 @@ static ERROR TASK_GetEnv(extTask *Self, struct taskGetEnv *Args)
                       winCloseHandle(keyhandle);
                    }
     
    -               if (Args->Value) return ERR_Okay;
    -               else return ERR_DoesNotExist;
    +               if (Args->Value) return ERR::Okay;
    +               else return ERR::DoesNotExist;
                 }
    -            else return log.warning(ERR_Syntax);
    +            else return log.warning(ERR::Syntax);
              }
           }
        }
     
        len = winGetEnv(Args->Name, Self->Env, ENV_SIZE);
    -   if (!len) return ERR_DoesNotExist;
    -   if (len >= ENV_SIZE) return log.warning(ERR_BufferOverflow);
    +   if (!len) return ERR::DoesNotExist;
    +   if (len >= ENV_SIZE) return log.warning(ERR::BufferOverflow);
     
        Args->Value = Self->Env;
    -   return ERR_Okay;
    +   return ERR::Okay;
     
     #elif __unix__
        if ((Args->Value = getenv(Args->Name))) {
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return ERR_DoesNotExist;
    +   else return ERR::DoesNotExist;
     #else
        #warn Write support for GetEnv()
    -   return ERR_NoSupport;
    +   return ERR::NoSupport;
     #endif
     }
     
    @@ -1359,30 +1347,30 @@ GetVar: Retrieves variable field values.
     -END-
     *********************************************************************************************************************/
     
    -static ERROR TASK_GetVar(extTask *Self, struct acGetVar *Args)
    +static ERR TASK_GetVar(extTask *Self, struct acGetVar *Args)
     {
        pf::Log log;
        LONG j;
     
    -   if ((!Args) or (!Args->Buffer) or (Args->Size <= 0)) return log.warning(ERR_NullArgs);
    +   if ((!Args) or (!Args->Buffer) or (Args->Size <= 0)) return log.warning(ERR::NullArgs);
     
        auto it = Self->Fields.find(Args->Field);
        if (it != Self->Fields.end()) {
           for (j=0; (it->second[j]) and (j < Args->Size-1); j++) Args->Buffer[j] = it->second[j];
           Args->Buffer[j++] = 0;
     
    -      if (j >= Args->Size) return ERR_BufferOverflow;
    -      else return ERR_Okay;
    +      if (j >= Args->Size) return ERR::BufferOverflow;
    +      else return ERR::Okay;
        }
     
        log.warning("The variable \"%s\" does not exist.", Args->Field);
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     
    -static ERROR TASK_Init(extTask *Self, APTR Void)
    +static ERR TASK_Init(extTask *Self, APTR Void)
     {
        pf::Log log;
        LONG len;
    @@ -1398,7 +1386,7 @@ static ERROR TASK_Init(extTask *Self, APTR Void)
           if (winGetExeDirectory(sizeof(buffer), buffer)) {
              LONG len = StrLength(buffer);
              while ((len > 1) and (buffer[len-1] != '/') and (buffer[len-1] != '\\') and (buffer[len-1] != ':')) len--;
    -         if (!AllocMemory(len+1, MEM::STRING|MEM::NO_CLEAR, (void **)&Self->ProcessPath, NULL)) {
    +         if (AllocMemory(len+1, MEM::STRING|MEM::NO_CLEAR, (void **)&Self->ProcessPath, NULL) IS ERR::Okay) {
                 for (i=0; i < len; i++) Self->ProcessPath[i] = buffer[i];
                 Self->ProcessPath[i] = 0;
              }
    @@ -1406,7 +1394,7 @@ static ERROR TASK_Init(extTask *Self, APTR Void)
     
           if ((len = winGetCurrentDirectory(sizeof(buffer), buffer))) {
              if (Self->Path) { FreeResource(Self->Path); Self->Path = NULL; }
    -         if (!AllocMemory(len+2, MEM::STRING|MEM::NO_CLEAR, (void **)&Self->Path, NULL)) {
    +         if (AllocMemory(len+2, MEM::STRING|MEM::NO_CLEAR, (void **)&Self->Path, NULL) IS ERR::Okay) {
                 for (i=0; i < len; i++) Self->Path[i] = buffer[i];
                 if (Self->Path[i-1] != '\\') Self->Path[i++] = '\\';
                 Self->Path[i] = 0;
    @@ -1484,12 +1472,12 @@ static ERROR TASK_Init(extTask *Self, APTR Void)
        }
        else if (Self->ProcessID) Self->Flags |= TSF::FOREIGN;
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     
    -static ERROR TASK_NewObject(extTask *Self, APTR Void)
    +static ERR TASK_NewObject(extTask *Self, APTR Void)
     {
        new (Self) extTask;
     #ifdef __unix__
    @@ -1497,7 +1485,7 @@ static ERROR TASK_NewObject(extTask *Self, APTR Void)
        Self->ErrFD = -1;
     #endif
        Self->TimeOut = 60 * 60 * 24;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -1516,7 +1504,7 @@ Okay
     
     *********************************************************************************************************************/
     
    -static ERROR TASK_Quit(extTask *Self, APTR Void)
    +static ERR TASK_Quit(extTask *Self, APTR Void)
     {
        pf::Log log;
     
    @@ -1536,7 +1524,7 @@ static ERROR TASK_Quit(extTask *Self, APTR Void)
           SendMessage(MSGID_QUIT, MSF::NIL, NULL, 0);
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -1573,11 +1561,11 @@ NoSupport: The platform does not support environment variables.
     
     *********************************************************************************************************************/
     
    -static ERROR TASK_SetEnv(extTask *Self, struct taskSetEnv *Args)
    +static ERR TASK_SetEnv(extTask *Self, struct taskSetEnv *Args)
     {
        pf::Log log;
     
    -   if ((!Args) or (!Args->Name)) return log.warning(ERR_NullArgs);
    +   if ((!Args) or (!Args->Name)) return log.warning(ERR::NullArgs);
     
     #ifdef _WIN32
     
    @@ -1597,7 +1585,7 @@ static ERROR TASK_SetEnv(extTask *Self, struct taskSetEnv *Args)
           log.msg("Registry: %s = %s", Args->Name, Args->Value);
     
           for (ki=0; ki < ARRAYSIZE(keys); ki++) {
    -         if (!StrCompare(keys[ki].HKey, Args->Name)) {
    +         if (StrCompare(keys[ki].HKey, Args->Name) IS ERR::Okay) {
                 CSTRING str = Args->Name + StrLength(keys[ki].HKey); // str = Parasol\Something
     
                 for (len=StrLength(str); (len > 0) and (str[len] != '\\'); len--);
    @@ -1633,29 +1621,29 @@ static ERROR TASK_SetEnv(extTask *Self, struct taskSetEnv *Args)
                       winCloseHandle(keyhandle);
                    }
     
    -               return ERR_Okay;
    +               return ERR::Okay;
                 }
    -            else return log.warning(ERR_Syntax);
    +            else return log.warning(ERR::Syntax);
              }
           }
     
    -      return log.warning(ERR_Failed);
    +      return log.warning(ERR::Failed);
        }
        else {
           winSetEnv(Args->Name, Args->Value);
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
     
     #elif __unix__
     
        if (Args->Value) setenv(Args->Name, Args->Value, 1);
        else unsetenv(Args->Name);
    -   return ERR_Okay;
    +   return ERR::Okay;
     
     #else
     
        #warn Write support for SetEnv()
    -   return ERR_NoSupport;
    +   return ERR::NoSupport;
     
     #endif
     }
    @@ -1666,12 +1654,12 @@ SetVar: Variable fields are supported for the general storage of program variabl
     -END-
     *********************************************************************************************************************/
     
    -static ERROR TASK_SetVar(extTask *Self, struct acSetVar *Args)
    +static ERR TASK_SetVar(extTask *Self, struct acSetVar *Args)
     {
    -   if ((!Args) or (!Args->Field) or (!Args->Value)) return ERR_NullArgs;
    +   if ((!Args) or (!Args->Field) or (!Args->Value)) return ERR::NullArgs;
     
        Self->Fields[Args->Field] = Args->Value;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -1685,23 +1673,22 @@ process that no more data is incoming).
     
     *********************************************************************************************************************/
     
    -static ERROR TASK_Write(extTask *Task, struct acWrite *Args)
    +static ERR TASK_Write(extTask *Task, struct acWrite *Args)
     {
        pf::Log log;
     
    -   if (!Args) return log.warning(ERR_NullArgs);
    +   if (!Args) return log.warning(ERR::NullArgs);
     
     #ifdef _WIN32
    -   LONG winerror;
        if (Task->Platform) {
    -      if (!(winerror = winWriteStd(Task->Platform, Args->Buffer, Args->Length))) {
    -         return ERR_Okay;
    +      if (auto winerror = winWriteStd(Task->Platform, Args->Buffer, Args->Length); !winerror) {
    +         return ERR::Okay;
           }
    -      else return log.warning(ERR_Write);
    +      else return log.warning(ERR::Write);
        }
    -   else return log.warning(ERR_Failed);
    +   else return log.warning(ERR::Failed);
     #else
    -   return log.warning(ERR_NoSupport);
    +   return log.warning(ERR::NoSupport);
     #endif
     }
     
    @@ -1728,10 +1715,10 @@ if (!AccessObject(CurrentTask(), 5000, &task)) {
     
     *********************************************************************************************************************/
     
    -static ERROR GET_Actions(extTask *Self, struct ActionEntry **Value)
    +static ERR GET_Actions(extTask *Self, struct ActionEntry **Value)
     {
        *Value = Self->Actions;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -1746,9 +1733,9 @@ If an argument needs to include whitespace, use double-quotes to encapsulate the
     
     *********************************************************************************************************************/
     
    -static ERROR SET_Args(extTask *Self, CSTRING Value)
    +static ERR SET_Args(extTask *Self, CSTRING Value)
     {
    -   if ((!Value) or (!*Value)) return ERR_Okay;
    +   if ((!Value) or (!*Value)) return ERR::Okay;
     
        while (*Value) {
           while (*Value <= 0x20) Value++; // Skip whitespace
    @@ -1775,7 +1762,7 @@ static ERROR SET_Args(extTask *Self, CSTRING Value)
           }
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -1791,20 +1778,20 @@ called on termination because the Task object no longer exists for the control o
     
     *********************************************************************************************************************/
     
    -static ERROR GET_ExitCallback(extTask *Self, FUNCTION **Value)
    +static ERR GET_ExitCallback(extTask *Self, FUNCTION **Value)
     {
    -   if (Self->ExitCallback.Type != CALL_NONE) {
    +   if (Self->ExitCallback.defined()) {
           *Value = &Self->ExitCallback;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return ERR_FieldNotSet;
    +   else return ERR::FieldNotSet;
     }
     
    -static ERROR SET_ExitCallback(extTask *Self, FUNCTION *Value)
    +static ERR SET_ExitCallback(extTask *Self, FUNCTION *Value)
     {
        if (Value) Self->ExitCallback = *Value;
    -   else Self->ExitCallback.Type = CALL_NONE;
    -   return ERR_Okay;
    +   else Self->ExitCallback.clear();
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -1820,20 +1807,20 @@ indicated by the Size.  The data pointer is temporary and will be invalid once t
     
     *********************************************************************************************************************/
     
    -static ERROR GET_ErrorCallback(extTask *Self, FUNCTION **Value)
    +static ERR GET_ErrorCallback(extTask *Self, FUNCTION **Value)
     {
    -   if (Self->ErrorCallback.Type != CALL_NONE) {
    +   if (Self->ErrorCallback.defined()) {
           *Value = &Self->ErrorCallback;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return ERR_FieldNotSet;
    +   else return ERR::FieldNotSet;
     }
     
    -static ERROR SET_ErrorCallback(extTask *Self, FUNCTION *Value)
    +static ERR SET_ErrorCallback(extTask *Self, FUNCTION *Value)
     {
        if (Value) Self->ErrorCallback = *Value;
    -   else Self->ErrorCallback.Type = CALL_NONE;
    -   return ERR_Okay;
    +   else Self->ErrorCallback.clear();
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -1843,35 +1830,34 @@ InputCallback: This callback returns incoming data from STDIN.
     
     The InputCallback field is available for use only when the Task object represents the current process.
     The referenced function will be called when process receives data from STDIN.  The callback must follow the
    -synopsis `Function(*Task, APTR Data, LONG Size, ERROR Status)`
    +synopsis `Function(*Task, APTR Data, LONG Size, ERR Status)`
     
     The information read from STDOUT will be returned in the Data pointer and the byte-length of the data will be indicated
     by the Size.  The data buffer is temporary and will be invalid once the callback function has returned.
     
    -A status of ERR_Finished is sent if the stdinput handle has been closed.
    +A status of ERR::Finished is sent if the stdinput handle has been closed.
     
     *********************************************************************************************************************/
     
    -static ERROR GET_InputCallback(extTask *Self, FUNCTION **Value)
    +static ERR GET_InputCallback(extTask *Self, FUNCTION **Value)
     {
    -   if (Self->InputCallback.Type != CALL_NONE) {
    +   if (Self->InputCallback.defined()) {
           *Value = &Self->InputCallback;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return ERR_FieldNotSet;
    +   else return ERR::FieldNotSet;
     }
     
    -static ERROR SET_InputCallback(extTask *Self, FUNCTION *Value)
    +static ERR SET_InputCallback(extTask *Self, FUNCTION *Value)
     {
    -   if (Self != glCurrentTask) return ERR_Failed;
    +   if (Self != glCurrentTask) return ERR::Failed;
     
        if (Value) {
    -      ERROR error;
           #ifdef __unix__
           fcntl(fileno(stdin), F_SETFL, fcntl(fileno(stdin), F_GETFL) | O_NONBLOCK);
    -      if (!(error = RegisterFD(fileno(stdin), RFD::READ, &task_stdinput_callback, Self))) {
    +      if (auto error = RegisterFD(fileno(stdin), RFD::READ, &task_stdinput_callback, Self); error IS ERR::Okay) {
           #elif _WIN32
    -      if (!(error = RegisterFD(winGetStdInput(), RFD::READ, &task_stdinput_callback, Self))) {
    +      if (auto error = RegisterFD(winGetStdInput(), RFD::READ, &task_stdinput_callback, Self); error IS ERR::Okay) {
           #endif
              Self->InputCallback = *Value;
           }
    @@ -1883,10 +1869,10 @@ static ERROR SET_InputCallback(extTask *Self, FUNCTION *Value)
           #else
           if (Self->InputCallback.Type) RegisterFD(fileno(stdin), RFD::READ|RFD::REMOVE, &task_stdinput_callback, Self);
           #endif
    -      Self->InputCallback.Type = CALL_NONE;
    +      Self->InputCallback.clear();
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -1902,20 +1888,20 @@ by the Size.  The data pointer is temporary and will be invalid once the callbac
     
     *********************************************************************************************************************/
     
    -static ERROR GET_OutputCallback(extTask *Self, FUNCTION **Value)
    +static ERR GET_OutputCallback(extTask *Self, FUNCTION **Value)
     {
    -   if (Self->OutputCallback.Type != CALL_NONE) {
    +   if (Self->OutputCallback.defined()) {
           *Value = &Self->OutputCallback;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return ERR_FieldNotSet;
    +   else return ERR::FieldNotSet;
     }
     
    -static ERROR SET_OutputCallback(extTask *Self, FUNCTION *Value)
    +static ERR SET_OutputCallback(extTask *Self, FUNCTION *Value)
     {
        if (Value) Self->OutputCallback = *Value;
    -   else Self->OutputCallback.Type = CALL_NONE;
    -   return ERR_Okay;
    +   else Self->OutputCallback.clear();
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -1932,13 +1918,13 @@ activated.  This will override all other path options, such as the RESET_PATH fl
     
     *********************************************************************************************************************/
     
    -static ERROR GET_LaunchPath(extTask *Self, STRING *Value)
    +static ERR GET_LaunchPath(extTask *Self, STRING *Value)
     {
        *Value = Self->LaunchPath;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
    -static ERROR SET_LaunchPath(extTask *Self, CSTRING Value)
    +static ERR SET_LaunchPath(extTask *Self, CSTRING Value)
     {
        pf::Log log;
     
    @@ -1947,12 +1933,12 @@ static ERROR SET_LaunchPath(extTask *Self, CSTRING Value)
        if ((Value) and (*Value)) {
           LONG i;
           for (i=0; Value[i]; i++);
    -      if (!AllocMemory(i+1, MEM::STRING|MEM::NO_CLEAR, (void **)&Self->LaunchPath, NULL)) {
    +      if (AllocMemory(i+1, MEM::STRING|MEM::NO_CLEAR, (void **)&Self->LaunchPath, NULL) IS ERR::Okay) {
              CopyMemory(Value, Self->LaunchPath, i+1);
           }
    -      else return log.warning(ERR_AllocMemory);
    +      else return log.warning(ERR::AllocMemory);
        }
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -1969,13 +1955,13 @@ only the quoted portion of the string will be used as the source path.
     
     *********************************************************************************************************************/
     
    -static ERROR GET_Location(extTask *Self, STRING *Value)
    +static ERR GET_Location(extTask *Self, STRING *Value)
     {
        *Value = Self->Location;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
    -static ERROR SET_Location(extTask *Self, CSTRING Value)
    +static ERR SET_Location(extTask *Self, CSTRING Value)
     {
        pf::Log log;
     
    @@ -1984,7 +1970,7 @@ static ERROR SET_Location(extTask *Self, CSTRING Value)
        if ((Value) and (*Value)) {
           LONG i;
           for (i=0; Value[i]; i++);
    -      if (!AllocMemory(i+1, MEM::STRING|MEM::NO_CLEAR, (void **)&Self->Location, NULL)) {
    +      if (AllocMemory(i+1, MEM::STRING|MEM::NO_CLEAR, (void **)&Self->Location, NULL) IS ERR::Okay) {
              while ((*Value) and (*Value <= 0x20)) Value++;
              if (*Value IS '"') {
                 Value++;
    @@ -1994,9 +1980,9 @@ static ERROR SET_Location(extTask *Self, CSTRING Value)
              else for (i=0; *Value; i++) Self->Location[i] = *Value++;
              Self->Location[i] = 0;
           }
    -      else return log.warning(ERR_AllocMemory);
    +      else return log.warning(ERR::AllocMemory);
        }
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -2010,16 +1996,16 @@ assign a randomly generated name.
     
     *********************************************************************************************************************/
     
    -static ERROR GET_Name(extTask *Self, STRING *Value)
    +static ERR GET_Name(extTask *Self, STRING *Value)
     {
        *Value = Self->Name;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
    -static ERROR SET_Name(extTask *Self, CSTRING Value)
    +static ERR SET_Name(extTask *Self, CSTRING Value)
     {
        StrCopy(Value, Self->Name, sizeof(Self->Name));
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -2045,18 +2031,18 @@ pf::vector<std::string> Args = {
     
     *********************************************************************************************************************/
     
    -static ERROR GET_Parameters(extTask *Self, pf::vector **Value, LONG *Elements)
    +static ERR GET_Parameters(extTask *Self, pf::vector **Value, LONG *Elements)
     {
        *Value = &Self->Parameters;
        *Elements = Self->Parameters.size();
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
    -static ERROR SET_Parameters(extTask *Self, const pf::vector *Value, LONG Elements)
    +static ERR SET_Parameters(extTask *Self, const pf::vector *Value, LONG Elements)
     {
        if (Value) Self->Parameters = Value[0];
        else Self->Parameters.clear();
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -2079,13 +2065,13 @@ new folder fails for any reason, the working folder will remain unchanged and th
     
     *********************************************************************************************************************/
     
    -static ERROR GET_Path(extTask *Self, STRING *Value)
    +static ERR GET_Path(extTask *Self, STRING *Value)
     {
        *Value = Self->Path;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
    -static ERROR SET_Path(extTask *Self, CSTRING Value)
    +static ERR SET_Path(extTask *Self, CSTRING Value)
     {
        STRING new_path = NULL;
     
    @@ -2093,11 +2079,11 @@ static ERROR SET_Path(extTask *Self, CSTRING Value)
     
        log.trace("ChDir: %s", Value);
     
    -   ERROR error = ERR_Okay;
    +   ERR error = ERR::Okay;
        if ((Value) and (*Value)) {
           LONG len = StrLength(Value);
           while ((len > 1) and (Value[len-1] != '/') and (Value[len-1] != '\\') and (Value[len-1] != ':')) len--;
    -      if (!AllocMemory(len+1, MEM::STRING|MEM::NO_CLEAR, (void **)&new_path, NULL)) {
    +      if (AllocMemory(len+1, MEM::STRING|MEM::NO_CLEAR, (void **)&new_path, NULL) IS ERR::Okay) {
              CopyMemory(Value, new_path, len);
              new_path[len] = 0;
     
    @@ -2105,31 +2091,31 @@ static ERROR SET_Path(extTask *Self, CSTRING Value)
              STRING path;
              if (!ResolvePath(new_path, RSF::NO_FILE_CHECK, &path)) {
                 if (chdir(path)) {
    -               error = ERR_InvalidPath;
    +               error = ERR::InvalidPath;
                    log.msg("Failed to switch current path to: %s", path);
                 }
                 FreeResource(path);
              }
    -         else error = log.warning(ERR_ResolvePath);
    +         else error = log.warning(ERR::ResolvePath);
     #elif _WIN32
              STRING path;
    -         if (!ResolvePath(new_path, RSF::NO_FILE_CHECK|RSF::PATH, &path)) {
    +         if (ResolvePath(new_path, RSF::NO_FILE_CHECK|RSF::PATH, &path) IS ERR::Okay) {
                 if (chdir(path)) {
    -               error = ERR_InvalidPath;
    +               error = ERR::InvalidPath;
                    log.msg("Failed to switch current path to: %s", path);
                 }
                 FreeResource(path);
              }
    -         else error = log.warning(ERR_ResolvePath);
    +         else error = log.warning(ERR::ResolvePath);
     #else
     #warn Support required for changing the current path.
     #endif
           }
    -      else error = log.warning(ERR_AllocMemory);
    +      else error = log.warning(ERR::AllocMemory);
        }
    -   else error = ERR_EmptyString;
    +   else error = ERR::EmptyString;
     
    -   if (!error) {
    +   if (error IS ERR::Okay) {
           if (Self->Path) { FreeResource(Self->Path); Self->Path = NULL; }
           Self->Path = new_path;
        }
    @@ -2151,10 +2137,10 @@ ProcessPath is set to the working folder in use at the time the process was laun
     
     *********************************************************************************************************************/
     
    -static ERROR GET_ProcessPath(extTask *Self, CSTRING *Value)
    +static ERR GET_ProcessPath(extTask *Self, CSTRING *Value)
     {
        *Value = Self->ProcessPath;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -2172,14 +2158,14 @@ effect of prioritisation.
     
     *********************************************************************************************************************/
     
    -static ERROR SET_Priority(extTask *Self, LONG Value)
    +static ERR SET_Priority(extTask *Self, LONG Value)
     {
     #ifdef __unix__
        LONG priority, unused;
        priority = -getpriority(PRIO_PROCESS, 0);
        unused = nice(-(Value - priority));
     #endif
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -2188,7 +2174,7 @@ static ERROR SET_Priority(extTask *Self, LONG Value)
     ReturnCode: The task's return code can be retrieved following execution.
     
     Once a process has completed execution then its return code can be read from this field.  If process is still running,
    -the error code ERR_TaskStillExists will be returned.
    +the error code ERR::TaskStillExists will be returned.
     
     -ERRORS-
     Okay
    @@ -2197,18 +2183,18 @@ DoesNotExist: The task is yet to be successfully launched with the Activate acti
     
     *********************************************************************************************************************/
     
    -static ERROR GET_ReturnCode(extTask *Self, LONG *Value)
    +static ERR GET_ReturnCode(extTask *Self, LONG *Value)
     {
        pf::Log log;
     
        if (Self->ReturnCodeSet) {
           *Value = Self->ReturnCode;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
     
        if (!Self->ProcessID) {
           log.msg("Task hasn't been launched yet.");
    -      return ERR_DoesNotExist;
    +      return ERR::DoesNotExist;
        }
     
     #ifdef __unix__
    @@ -2228,32 +2214,32 @@ static ERROR GET_ReturnCode(extTask *Self, LONG *Value)
           }
     
           *Value = Self->ReturnCode;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return ERR_TaskStillExists;
    +   else return ERR::TaskStillExists;
     
     #elif _WIN32
     
        winGetExitCodeProcess(Self->Platform, &Self->ReturnCode);
    -   if (Self->ReturnCode IS 259) return ERR_TaskStillExists;
    +   if (Self->ReturnCode IS 259) return ERR::TaskStillExists;
        else {
           Self->ReturnCodeSet = true;
           *Value = Self->ReturnCode;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
     
     #else
     
    -   return ERR_NoSupport;
    +   return ERR::NoSupport;
     
     #endif
     }
     
    -static ERROR SET_ReturnCode(extTask *Self, LONG Value)
    +static ERR SET_ReturnCode(extTask *Self, LONG Value)
     {
        Self->ReturnCodeSet = true;
        Self->ReturnCode = Value;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -2292,7 +2278,7 @@ static const FieldArray clFields[] = {
     
     //********************************************************************************************************************
     
    -extern "C" ERROR add_task_class(void)
    +extern "C" ERR add_task_class(void)
     {
        glTaskClass = objMetaClass::create::global(
           fl::ClassVersion(VER_TASK),
    @@ -2307,5 +2293,5 @@ extern "C" ERROR add_task_class(void)
           fl::Size(sizeof(extTask)),
           fl::Path("modules:core"));
     
    -   return glTaskClass ? ERR_Okay : ERR_AddClass;
    +   return glTaskClass ? ERR::Okay : ERR::AddClass;
     }
    diff --git a/src/core/classes/class_thread.cpp b/src/core/classes/class_thread.cpp
    index 4c9936c5a..a910d7d60 100644
    --- a/src/core/classes/class_thread.cpp
    +++ b/src/core/classes/class_thread.cpp
    @@ -14,8 +14,8 @@ The following code illustrates how to create a temporary thread that is automati
     thread_entry() function has completed:
     
     
    -static ERROR thread_entry(objThread *Thread) {
    -   return ERR_Okay;
    +static ERR thread_entry(objThread *Thread) {
    +   return ERR::Okay;
     }
     
     objThread::create thread = { fl::Routine(thread_entry), fl::Flags(THF::AUTO_FREE) };
    @@ -90,7 +90,7 @@ LONG get_thread_id(void)
     //********************************************************************************************************************
     // Retrieve a thread object from the thread pool.
     
    -ERROR threadpool_get(extThread **Result)
    +ERR threadpool_get(extThread **Result)
     {
        pf::Log log;
     
    @@ -103,7 +103,7 @@ ERROR threadpool_get(extThread **Result)
                 at.InUse = true;
                 *Result = at.Thread;
                 glmThreadPool.unlock();
    -            return ERR_Okay;
    +            return ERR::Okay;
              }
           }
     
    @@ -117,9 +117,9 @@ ERROR threadpool_get(extThread **Result)
           }
           *Result = thread;
           glmThreadPool.unlock();
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return log.warning(ERR_CreateObject);
    +   else return log.warning(ERR::CreateObject);
     }
     
     //********************************************************************************************************************
    @@ -164,36 +164,36 @@ void remove_threadpool(void)
     // Called whenever a MSGID_THREAD_ACTION message is caught by ProcessMessages().  See thread_action() in lib_actions.c
     // for usage.
     
    -ERROR msg_threadaction(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize)
    +ERR msg_threadaction(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize)
     {
        auto msg = (ThreadActionMessage *)Message;
    -   if (!msg) return ERR_Okay;
    +   if (!msg) return ERR::Okay;
     
    -   if (msg->Callback.Type IS CALL_STDC) {
    -      auto routine = (void (*)(ACTIONID, OBJECTPTR, ERROR, LONG))msg->Callback.StdC.Routine;
    -      routine(msg->ActionID, msg->Object, msg->Error, msg->Key);
    +   if (msg->Callback.isC()) {
    +      auto routine = (void (*)(ACTIONID, OBJECTPTR, ERR, LONG, APTR))msg->Callback.StdC.Routine;
    +      routine(msg->ActionID, msg->Object, msg->Error, msg->Key, msg->Callback.StdC.Meta);
        }
    -   else if (msg->Callback.Type IS CALL_SCRIPT) {
    +   else if (msg->Callback.isScript()) {
           auto script = msg->Callback.Script.Script;
    -      if (!LockObject(script, 5000)) {
    +      if (LockObject(script, 5000) IS ERR::Okay) {
              const ScriptArg args[] = {
                 { "ActionID", msg->ActionID },
                 { "Object",   msg->Object, FD_OBJECTPTR },
    -            { "Error",    msg->Error },
    +            { "Error",    LONG(msg->Error) },
                 { "Key",      msg->Key }
              };
    -         scCallback(script, msg->Callback.Script.ProcedureID, args, ARRAYSIZE(args), NULL);
    +         scCallback(script, msg->Callback.Script.ProcedureID, args, std::ssize(args), NULL);
              ReleaseObject(script);
           }
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     // Called whenever a MSGID_THREAD_CALLBACK message is caught by ProcessMessages().  See thread_entry() for usage.
     
    -ERROR msg_threadcallback(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize)
    +ERR msg_threadcallback(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize)
     {
        pf::Log log;
     
    @@ -202,15 +202,15 @@ ERROR msg_threadcallback(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LO
     
        log.branch("Executing completion callback for thread #%d", uid);
     
    -   if (msg->Callback.Type IS CALL_STDC) {
    -      auto callback = (void (*)(OBJECTID))msg->Callback.StdC.Routine;
    -      callback(uid);
    +   if (msg->Callback.isC()) {
    +      auto callback = (void (*)(OBJECTID, APTR))msg->Callback.StdC.Routine;
    +      callback(uid, msg->Callback.StdC.Meta);
        }
    -   else if (msg->Callback.Type IS CALL_SCRIPT) {
    +   else if (msg->Callback.isScript()) {
           if (auto script = msg->Callback.Script.Script) {
    -         if (!LockObject(script, 5000)) {
    +         if (LockObject(script, 5000) IS ERR::Okay) {
                 const ScriptArg args[] = { { "Thread", uid, FD_OBJECTID } };
    -            scCallback(script, msg->Callback.Script.ProcedureID, args, ARRAYSIZE(args), NULL);
    +            scCallback(script, msg->Callback.Script.ProcedureID, args, std::ssize(args), NULL);
                 ReleaseObject(script);
              }
           }
    @@ -228,9 +228,9 @@ ERROR msg_threadcallback(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LO
           }
           else acSignal(*thread); // Convenience for the client
        }
    -   else log.warning(ERR_AccessObject);
    +   else log.warning(ERR::AccessObject);
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
    @@ -265,15 +265,15 @@ static void * thread_entry(extThread *Self)
           // Replace the default dummy context with one that pertains to the thread
           ObjectContext thread_ctx(Self, 0);
     
    -      if (Self->Routine.Type IS CALL_STDC) {
    -         auto routine = (ERROR (*)(extThread *))Self->Routine.StdC.Routine;
    -         Self->Error = routine(Self);
    +      if (Self->Routine.isC()) {
    +         auto routine = (ERR (*)(extThread *, APTR))Self->Routine.StdC.Routine;
    +         Self->Error = routine(Self, Self->Routine.StdC.Meta);
           }
    -      else if (Self->Routine.Type IS CALL_SCRIPT) {
    +      else if (Self->Routine.isScript()) {
              ScopedObjectLock script(Self->Routine.Script.Script, 5000);
              if (script.granted()) {
                 const ScriptArg args[] = { { "Thread", Self, FD_OBJECTPTR } };
    -            scCallback(*script, Self->Routine.Script.ProcedureID, args, ARRAYSIZE(args), NULL);
    +            scCallback(*script, Self->Routine.Script.ProcedureID, args, std::ssize(args), NULL);
              }
           }
        }
    @@ -315,16 +315,16 @@ Activate: Spawn a new thread that calls the function referenced in the #Routine
     -END-
     *********************************************************************************************************************/
     
    -static ERROR THREAD_Activate(extThread *Self, APTR Void)
    +static ERR THREAD_Activate(extThread *Self, APTR Void)
     {
        pf::Log log;
     
    -   if (Self->Active) return ERR_ThreadAlreadyActive;
    +   if (Self->Active) return ERR::ThreadAlreadyActive;
     
        // Thread objects MUST be locked prior to activation.  There is otherwise a genuine risk that the object
        // could be terminated by code operating outside of the thread space while it is active.
     
    -   if (Self->Queue.load() < 1) return log.warning(ERR_ThreadNotLocked);
    +   if (Self->Queue.load() < 1) return log.warning(ERR::ThreadNotLocked);
     
        Self->Active = true; // Indicate that the thread is running
     
    @@ -336,7 +336,7 @@ static ERROR THREAD_Activate(extThread *Self, APTR Void)
        //pthread_attr_setstacksize(&attr, Self->StackSize);
        if (!pthread_create(&Self->PThread, &attr, (APTR (*)(APTR))&thread_entry, Self)) {
           pthread_attr_destroy(&attr);
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
        else {
           char errstr[80];
    @@ -344,17 +344,17 @@ static ERROR THREAD_Activate(extThread *Self, APTR Void)
           log.warning("pthread_create() failed with error: %s.", errstr);
           pthread_attr_destroy(&attr);
           Self->Active = false;
    -      return log.warning(ERR_SystemCall);
    +      return log.warning(ERR::SystemCall);
        }
     
     #elif _WIN32
     
        if ((Self->Handle = winCreateThread((APTR)&thread_entry, Self, Self->StackSize, &Self->ThreadID))) {
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
        else {
           Self->Active = false;
    -      return log.warning(ERR_SystemCall);
    +      return log.warning(ERR::SystemCall);
        }
     
     #else
    @@ -371,11 +371,11 @@ could result in an unstable application.
     -END-
     *********************************************************************************************************************/
     
    -static ERROR THREAD_Deactivate(extThread *Self, APTR Void)
    +static ERR THREAD_Deactivate(extThread *Self, APTR Void)
     {
        if (Self->Active) {
           #ifdef __ANDROID__
    -         return ERR_NoSupport;
    +         return ERR::NoSupport;
           #elif __unix__
              pthread_cancel(Self->PThread);
           #elif _WIN32
    @@ -387,7 +387,7 @@ static ERROR THREAD_Deactivate(extThread *Self, APTR Void)
           Self->Active = false;
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -399,7 +399,7 @@ an active thread is made then it will be marked for termination so as to avoid t
     -END-
     *********************************************************************************************************************/
     
    -static ERROR THREAD_Free(extThread *Self, APTR Void)
    +static ERR THREAD_Free(extThread *Self, APTR Void)
     {
        if ((Self->Data) and (Self->DataSize > 0)) {
           FreeResource(Self->Data);
    @@ -416,37 +416,37 @@ static ERROR THREAD_Free(extThread *Self, APTR Void)
        #endif
     
        Self->~extThread();
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     
    -static ERROR THREAD_FreeWarning(extThread *Self, APTR Void)
    +static ERR THREAD_FreeWarning(extThread *Self, APTR Void)
     {
    -   if (!Self->Active) return ERR_Okay;
    +   if (!Self->Active) return ERR::Okay;
        else {
           pf::Log log;
    -      log.debug("Thread is still running, marking for auto termination.");
    +      log.detail("Thread is still running, marking for auto termination.");
           Self->Flags |= THF::AUTO_FREE;
    -      return ERR_InUse;
    +      return ERR::InUse;
        }
     }
     
     //********************************************************************************************************************
     
    -static ERROR THREAD_Init(extThread *Self, APTR Void)
    +static ERR THREAD_Init(extThread *Self, APTR Void)
     {
        pf::Log log;
     
        if (Self->StackSize < 1024) Self->StackSize = 1024;
    -   else if (Self->StackSize > 1024 * 1024) return log.warning(ERR_OutOfRange);
    +   else if (Self->StackSize > 1024 * 1024) return log.warning(ERR::OutOfRange);
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     
    -static ERROR THREAD_NewObject(extThread *Self, APTR Void)
    +static ERR THREAD_NewObject(extThread *Self, APTR Void)
     {
        new (Self) extThread;
        Self->StackSize = 16384;
    @@ -454,7 +454,7 @@ static ERROR THREAD_NewObject(extThread *Self, APTR Void)
           Self->Msgs[0] = -1;
           Self->Msgs[1] = -1;
        #endif
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -482,12 +482,12 @@ AllocMemory
     
     *********************************************************************************************************************/
     
    -static ERROR THREAD_SetData(extThread *Self, struct thSetData *Args)
    +static ERR THREAD_SetData(extThread *Self, struct thSetData *Args)
     {
        pf::Log log;
     
    -   if ((!Args) or (!Args->Data)) return log.warning(ERR_NullArgs);
    -   if (Args->Size < 0) return log.warning(ERR_Args);
    +   if ((!Args) or (!Args->Data)) return log.warning(ERR::NullArgs);
    +   if (Args->Size < 0) return log.warning(ERR::Args);
     
        if (Self->Data) {
           FreeResource(Self->Data);
    @@ -497,14 +497,14 @@ static ERROR THREAD_SetData(extThread *Self, struct thSetData *Args)
     
        if (!Args->Size) { // If no size is provided, we simply copy the provided pointer.
           Self->Data = Args->Data;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else if (!AllocMemory(Args->Size, MEM::DATA, &Self->Data, NULL)) {
    +   else if (AllocMemory(Args->Size, MEM::DATA, &Self->Data, NULL) IS ERR::Okay) {
           Self->DataSize = Args->Size;
           CopyMemory(Args->Data, Self->Data, Args->Size);
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return log.warning(ERR_AllocMemory);
    +   else return log.warning(ERR::AllocMemory);
     }
     
     /*********************************************************************************************************************
    @@ -519,20 +519,20 @@ The synopsis for the callback routine is `void Callback(objThread *Thread)`.
     
     *********************************************************************************************************************/
     
    -static ERROR GET_Callback(extThread *Self, FUNCTION **Value)
    +static ERR GET_Callback(extThread *Self, FUNCTION **Value)
     {
    -   if (Self->Callback.Type != CALL_NONE) {
    +   if (Self->Callback.defined()) {
           *Value = &Self->Callback;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return ERR_FieldNotSet;
    +   else return ERR::FieldNotSet;
     }
     
    -static ERROR SET_Callback(extThread *Self, FUNCTION *Value)
    +static ERR SET_Callback(extThread *Self, FUNCTION *Value)
     {
        if (Value) Self->Callback = *Value;
    -   else Self->Callback.Type = CALL_NONE;
    -   return ERR_Okay;
    +   else Self->Callback.clear();
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -545,11 +545,11 @@ the thread object.  It is paired with the #DataSize field, which reflects the si
     
     *********************************************************************************************************************/
     
    -static ERROR GET_Data(extThread *Self, APTR *Value, LONG *Elements)
    +static ERR GET_Data(extThread *Self, APTR *Value, LONG *Elements)
     {
        *Value = Self->Data;
        *Elements = Self->DataSize;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -568,27 +568,27 @@ Lookup: THF
     Routine: A function reference that will be called when the thread is started.
     
     The routine that will be executed when the thread is activated must be specified here.  The function synopsis is
    -`ERROR routine(objThread *Thread)`.
    +`ERR routine(objThread *Thread)`.
     
     When the routine is called, a reference to the thread object is passed as a parameter.  Once the routine has
     finished processing, the resulting error code will be stored in the thread object's #Error field.
     
     *********************************************************************************************************************/
     
    -static ERROR GET_Routine(extThread *Self, FUNCTION **Value)
    +static ERR GET_Routine(extThread *Self, FUNCTION **Value)
     {
    -   if (Self->Routine.Type != CALL_NONE) {
    +   if (Self->Routine.defined()) {
           *Value = &Self->Routine;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return ERR_FieldNotSet;
    +   else return ERR::FieldNotSet;
     }
     
    -static ERROR SET_Routine(extThread *Self, FUNCTION *Value)
    +static ERR SET_Routine(extThread *Self, FUNCTION *Value)
     {
        if (Value) Self->Routine = *Value;
    -   else Self->Routine.Type = CALL_NONE;
    -   return ERR_Okay;
    +   else Self->Routine.clear();
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -618,7 +618,7 @@ static const FieldArray clFields[] = {
     
     //********************************************************************************************************************
     
    -extern "C" ERROR add_thread_class(void)
    +extern "C" ERR add_thread_class(void)
     {
        glThreadClass = objMetaClass::create::global(
           fl::ClassVersion(VER_THREAD),
    @@ -630,5 +630,5 @@ extern "C" ERROR add_thread_class(void)
           fl::Size(sizeof(extThread)),
           fl::Path("modules:core"));
     
    -   return glThreadClass ? ERR_Okay : ERR_AddClass;
    +   return glThreadClass ? ERR::Okay : ERR::AddClass;
     }
    diff --git a/src/core/classes/class_time.cpp b/src/core/classes/class_time.cpp
    index 55a847d81..eebf7b81e 100644
    --- a/src/core/classes/class_time.cpp
    +++ b/src/core/classes/class_time.cpp
    @@ -8,11 +8,7 @@ that is distributed with this package.  Please refer to it for further informati
     -CLASS-
     Time: Simplifies the management of date/time information.
     
    -The Time class is available for programs that require time and date recording.  In future, support will also be
    -provided for the addition and subtraction of date values.
    -
    -Please note that the Time class uses strict metric interpretations of "millisecond" and "microsecond" terminology. That
    -is, a millisecond is 1/1000th (one thousandth) of a second, a microsecond is 1/1000000th (one millionth) of a second.
    +The Time class is available for programs that require time and date management in a multi-platform manner.
     
     To get the current system time, use the #Query() action.
     -END-
    @@ -33,10 +29,10 @@ To get the current system time, use the #Query() action.
     #include 
     #endif
     
    -static ERROR GET_TimeStamp(objTime *, LARGE *);
    +static ERR GET_TimeStamp(objTime *, LARGE *);
     
    -static ERROR TIME_Query(objTime *, APTR);
    -static ERROR TIME_SetTime(objTime *, APTR);
    +static ERR TIME_Query(objTime *, APTR);
    +static ERR TIME_SetTime(objTime *, APTR);
     
     /*********************************************************************************************************************
     -ACTION-
    @@ -44,7 +40,7 @@ Query: Updates the values in a time object with the current system date and time
     -END-
     *********************************************************************************************************************/
     
    -static ERROR TIME_Query(objTime *Self, APTR Void)
    +static ERR TIME_Query(objTime *Self, APTR Void)
     {
        #ifdef __unix__
     
    @@ -92,7 +88,7 @@ static ERROR TIME_Query(objTime *Self, APTR Void)
        LONG m = Self->Month + 12 * a - 2;
        Self->DayOfWeek = (Self->Day + y + (y / 4) - (y / 100) + (y / 400) + (31 * m) / 12) % 7;
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -106,7 +102,7 @@ work if the user is logged in as the administrator.
     
     *********************************************************************************************************************/
     
    -static ERROR TIME_SetTime(objTime *Self, APTR Void)
    +static ERR TIME_SetTime(objTime *Self, APTR Void)
     {
     #ifdef __unix__
        pf::Log log;
    @@ -157,9 +153,9 @@ static ERROR TIME_SetTime(objTime *Self, APTR Void)
        }
        else log.warning("mktime() failed [%d/%d/%d, %d:%d:%d]", Self->Day, Self->Month, Self->Year, Self->Hour, Self->Minute, Self->Second);
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     #else
    -   return ERR_NoSupport;
    +   return ERR::NoSupport;
     #endif
     }
     
    @@ -175,10 +171,10 @@ DayOfWeek: Day of week (0 - 6) starting from Sunday.
     Hour: Hour (0 - 23)
     
     -FIELD-
    -MicroSecond: Microsecond (0 - 999999)
    +MicroSecond: A microsecond is one millionth of a second (0 - 999999)
     
     -FIELD-
    -MilliSecond: Millisecond (0 - 999)
    +MilliSecond: A millisecond is one thousandth of a second (0 - 999)
     
     -FIELD-
     Minute: Minute (0 - 59)
    @@ -206,24 +202,24 @@ The TimeStamp field is a 64-bit integer that represents the time object as an ap
     milliseconds represented in the time object (approximately the total amount of time passed since Zero-AD).  This is
     convenient for summarising a time value for comparison with other time stamps, or for storing time in a 64-bit space.
     
    -The TimeStamp is dynamically calculated when you read this field.
    +The TimeStamp value is dynamically calculated when reading this field.
     
     *********************************************************************************************************************/
     
    -static ERROR GET_TimeStamp(objTime *Self, LARGE *Value)
    +static ERR GET_TimeStamp(objTime *Self, LARGE *Value)
     {
        *Value = Self->Second +
    -            ((LARGE)Self->Minute * 60) +
    -            ((LARGE)Self->Hour * 60 * 60) +
    -            ((LARGE)Self->Day * 60 * 60 * 24) +
    -            ((LARGE)Self->Month * 60 * 60 * 24 * 31) +
    -            ((LARGE)Self->Year * 60 * 60 * 24 * 12);
    +            (LARGE(Self->Minute) * 60) +
    +            (LARGE(Self->Hour) * 60 * 60) +
    +            (LARGE(Self->Day) * 60 * 60 * 24) +
    +            (LARGE(Self->Month) * 60 * 60 * 24 * 31) +
    +            (LARGE(Self->Year) * 60 * 60 * 24 * 31 * 12);
     
        *Value = *Value * 1000000LL;
     
        *Value += Self->MilliSecond;
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -262,7 +258,7 @@ static const MethodEntry clMethods[] = {
     
     //********************************************************************************************************************
     
    -extern "C" ERROR add_time_class(void)
    +extern "C" ERR add_time_class(void)
     {
        glTimeClass = objMetaClass::create::global(
           fl::BaseClassID(ID_TIME),
    @@ -275,5 +271,5 @@ extern "C" ERROR add_time_class(void)
           fl::Size(sizeof(objTime)),
           fl::Path("modules:core"));
     
    -   return glTimeClass ? ERR_Okay : ERR_AddClass;
    +   return glTimeClass ? ERR::Okay : ERR::AddClass;
     }
    diff --git a/src/core/compression/class_archive.cpp b/src/core/compression/class_archive.cpp
    index 0f1eb22a3..bd9f656f4 100644
    --- a/src/core/compression/class_archive.cpp
    +++ b/src/core/compression/class_archive.cpp
    @@ -53,11 +53,11 @@ struct ArchiveDriver {
     
     static std::unordered_map glArchives;
     
    -static ERROR close_folder(DirInfo *);
    -static ERROR open_folder(DirInfo *);
    -static ERROR get_info(CSTRING, FileInfo *, LONG);
    -static ERROR scan_folder(DirInfo *);
    -static ERROR test_path(STRING, RSF, LOC *);
    +static ERR close_folder(DirInfo *);
    +static ERR open_folder(DirInfo *);
    +static ERR get_info(CSTRING, FileInfo *, LONG);
    +static ERR scan_folder(DirInfo *);
    +static ERR test_path(STRING, RSF, LOC *);
     
     //********************************************************************************************************************
     
    @@ -74,10 +74,10 @@ static void reset_state(extFile *Self)
     
     //********************************************************************************************************************
     
    -static ERROR seek_to_item(extFile *Self)
    +static ERR seek_to_item(extFile *Self)
     {
        auto prv = (prvFileArchive *)Self->ChildPrivate;
    -   if (prv->InvalidState) return ERR_InvalidState;
    +   if (prv->InvalidState) return ERR::InvalidState;
     
        auto &item = prv->Info;
     
    @@ -85,29 +85,29 @@ static ERROR seek_to_item(extFile *Self)
        prv->ReadPtr = NULL;
     
        UWORD extra_len;
    -   if (flReadLE(prv->FileStream, &extra_len)) return ERR_Read;
    +   if (flReadLE(prv->FileStream, &extra_len) != ERR::Okay) return ERR::Read;
        ULONG stream_start = item.Offset + HEAD_LENGTH + item.NameLen + extra_len;
    -   if (acSeekStart(prv->FileStream, stream_start) != ERR_Okay) return ERR_Seek;
    +   if (acSeekStart(prv->FileStream, stream_start) != ERR::Okay) return ERR::Seek;
     
        if (item.CompressedSize > 0) {
           Self->Flags |= FL::FILE;
     
           if (item.DeflateMethod IS 0) { // The file is stored rather than compressed
              Self->Size = item.CompressedSize;
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
           else if ((item.DeflateMethod IS 8) and (!inflateInit2(&prv->Stream, -MAX_WBITS))) {
              prv->Inflating = true;
              Self->Size = item.OriginalSize;
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
    -      else return ERR_Failed;
    +      else return ERR::Failed;
        }
        else { // Folder or empty file
           if (item.IsFolder) Self->Flags |= FL::FOLDER;
           else Self->Flags |= FL::FILE;
           Self->Size = 0;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
     }
     
    @@ -157,15 +157,15 @@ extern extCompression * find_archive(CSTRING Path, std::string &FilePath)
     
     //********************************************************************************************************************
     
    -static ERROR ARCHIVE_Activate(extFile *Self, APTR Void)
    +static ERR ARCHIVE_Activate(extFile *Self, APTR Void)
     {
        Log log;
     
        auto prv = (prvFileArchive *)Self->ChildPrivate;
     
    -   if (!prv->Archive) return log.warning(ERR_SystemCorrupt);
    +   if (!prv->Archive) return log.warning(ERR::SystemCorrupt);
     
    -   if (prv->FileStream) return ERR_Okay; // Already activated
    +   if (prv->FileStream) return ERR::Okay; // Already activated
     
        log.msg("Allocating file stream for item %s", prv->Info.Name.c_str());
     
    @@ -174,16 +174,16 @@ static ERROR ARCHIVE_Activate(extFile *Self, APTR Void)
           fl::Path(prv->Archive->Path),
           fl::Flags(FL::READ)))) {
     
    -      ERROR error = seek_to_item(Self);
    -      if (error) log.warning(error);
    +      ERR error = seek_to_item(Self);
    +      if (error != ERR::Okay) log.warning(error);
           return error;
        }
    -   else return ERR_File;
    +   else return ERR::File;
     }
     
     //********************************************************************************************************************
     
    -static ERROR ARCHIVE_Free(extFile *Self, APTR Void)
    +static ERR ARCHIVE_Free(extFile *Self, APTR Void)
     {
        auto prv = (prvFileArchive *)Self->ChildPrivate;
     
    @@ -193,28 +193,28 @@ static ERROR ARCHIVE_Free(extFile *Self, APTR Void)
           prv->~prvFileArchive();
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     
    -static ERROR ARCHIVE_Init(extFile *Self, APTR Void)
    +static ERR ARCHIVE_Init(extFile *Self, APTR Void)
     {
        Log log;
     
    -   if (!Self->Path) return ERR_FieldNotSet;
    +   if (!Self->Path) return ERR::FieldNotSet;
     
    -   if (StrCompare("archive:", Self->Path, LEN_ARCHIVE) != ERR_Okay) return ERR_NoSupport;
    +   if (StrCompare("archive:", Self->Path, LEN_ARCHIVE) != ERR::Okay) return ERR::NoSupport;
     
    -   if ((Self->Flags & (FL::NEW|FL::WRITE)) != FL::NIL) return log.warning(ERR_ReadOnly);
    +   if ((Self->Flags & (FL::NEW|FL::WRITE)) != FL::NIL) return log.warning(ERR::ReadOnly);
     
    -   ERROR error = ERR_Search;
    -   if (!AllocMemory(sizeof(prvFileArchive), MEM::DATA, &Self->ChildPrivate, NULL)) {
    +   ERR error = ERR::Search;
    +   if (AllocMemory(sizeof(prvFileArchive), MEM::DATA, &Self->ChildPrivate, NULL) IS ERR::Okay) {
           auto prv = (prvFileArchive *)Self->ChildPrivate;
           new (prv) prvFileArchive;
     
           if (Self->Path[StrLength(Self->Path)-1] IS ':') { // Nothing is referenced
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
           else {
              std::string file_path;
    @@ -227,48 +227,48 @@ static ERROR ARCHIVE_Init(extFile *Self, APTR Void)
     
                 auto it = prv->Archive->Files.begin();
                 for (; it != prv->Archive->Files.end(); it++) {
    -               if (!StrCompare(file_path, it->Name, 0, STR::CASE|STR::MATCH_LEN)) break;
    +               if (StrCompare(file_path, it->Name, 0, STR::CASE|STR::MATCH_LEN) IS ERR::Okay) break;
                 }
     
                 if ((it IS prv->Archive->Files.end()) and ((Self->Flags & FL::APPROXIMATE) != FL::NIL)) {
                    file_path.append(".*");
                    for (it = prv->Archive->Files.begin(); it != prv->Archive->Files.end(); it++) {
    -                  if (!StrCompare(file_path, it->Name, 0, STR::WILDCARD)) break;
    +                  if (StrCompare(file_path, it->Name, 0, STR::WILDCARD) IS ERR::Okay) break;
                    }
                 }
     
                 if (it != prv->Archive->Files.end()) {
                    prv->Info = *it;
    -               if (!(error = Self->activate())) {
    +               if ((error = Self->activate()) IS ERR::Okay) {
                       error = Self->query();
                    }
                 }
              }
           }
     
    -      if (error) {
    +      if (error != ERR::Okay) {
              prv->~prvFileArchive();
              FreeResource(Self->ChildPrivate);
              Self->ChildPrivate = NULL;
           }
        }
    -   else error = ERR_AllocMemory;
    +   else error = ERR::AllocMemory;
     
        return error;
     }
     
     //********************************************************************************************************************
     
    -static ERROR ARCHIVE_Query(extFile *Self, APTR Void)
    +static ERR ARCHIVE_Query(extFile *Self, APTR Void)
     {
        auto prv = (prvFileArchive *)(Self->ChildPrivate);
     
        // Activate the source if this hasn't been done already.
     
    -   ERROR error;
    +   ERR error;
        if (!prv->FileStream) {
           error = Self->activate();
    -      if (error) return error;
    +      if (error != ERR::Okay) return error;
        }
     
        // If security flags are present, convert them to file system permissions.
    @@ -291,26 +291,26 @@ static ERROR ARCHIVE_Query(extFile *Self, APTR Void)
           Self->Permissions = permissions;
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     
    -static ERROR ARCHIVE_Read(extFile *Self, struct acRead *Args)
    +static ERR ARCHIVE_Read(extFile *Self, struct acRead *Args)
     {
        Log log;
     
    -   if ((!Args) or (!Args->Buffer)) return log.warning(ERR_NullArgs);
    -   else if (Args->Length == 0) return ERR_Okay;
    -   else if (Args->Length < 0) return ERR_OutOfRange;
    +   if ((!Args) or (!Args->Buffer)) return log.warning(ERR::NullArgs);
    +   else if (Args->Length == 0) return ERR::Okay;
    +   else if (Args->Length < 0) return ERR::OutOfRange;
     
        auto prv = (prvFileArchive *)Self->ChildPrivate;
     
    -   if (prv->InvalidState) return ERR_InvalidState;
    +   if (prv->InvalidState) return ERR::InvalidState;
     
        if (prv->Info.DeflateMethod IS 0) {
    -      ERROR error = acRead(prv->FileStream, Args->Buffer, Args->Length, &Args->Result);
    -      if (!error) Self->Position += Args->Result;
    +      ERR error = acRead(prv->FileStream, Args->Buffer, Args->Length, &Args->Result);
    +      if (error IS ERR::Okay) Self->Position += Args->Result;
           return error;
        }
        else {
    @@ -326,8 +326,8 @@ static ERROR ARCHIVE_Read(extFile *Self, struct acRead *Args)
                 .Length = (zf.CompressedSize < SIZE_COMPRESSION_BUFFER) ? (LONG)zf.CompressedSize : SIZE_COMPRESSION_BUFFER
              };
     
    -         if (Action(AC_Read, prv->FileStream, &read)) return ERR_Read;
    -         if (read.Result <= 0) return ERR_Read;
    +         if (Action(AC_Read, prv->FileStream, &read) != ERR::Okay) return ERR::Read;
    +         if (read.Result <= 0) return ERR::Read;
     
              prv->ReadPtr          = prv->OutputBuffer;
              prv->InputLength      = zf.CompressedSize - read.Result;
    @@ -351,8 +351,8 @@ static ERROR ARCHIVE_Read(extFile *Self, struct acRead *Args)
              // Stop if necessary
     
              if (prv->Stream.total_out IS zf.OriginalSize) break; // All data decompressed
    -         if (Args->Result >= Args->Length) return ERR_Okay;
    -         if (!prv->Inflating) return ERR_Okay;
    +         if (Args->Result >= Args->Length) return ERR::Okay;
    +         if (!prv->Inflating) return ERR::Okay;
     
              // Reset the output buffer and decompress more data
     
    @@ -376,8 +376,8 @@ static ERROR ARCHIVE_Read(extFile *Self, struct acRead *Args)
                 if (prv->InputLength < SIZE_COMPRESSION_BUFFER) read.Length = prv->InputLength;
                 else read.Length = SIZE_COMPRESSION_BUFFER;
     
    -            if (Action(AC_Read, prv->FileStream, &read)) return ERR_Read;
    -            if (read.Result <= 0) return ERR_Read;
    +            if (Action(AC_Read, prv->FileStream, &read) != ERR::Okay) return ERR::Read;
    +            if (read.Result <= 0) return ERR::Read;
     
                 prv->InputLength -= read.Result;
                 prv->Stream.next_in  = prv->InputBuffer;
    @@ -390,13 +390,13 @@ static ERROR ARCHIVE_Read(extFile *Self, struct acRead *Args)
              prv->Inflating = false;
           }
     
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
     }
     
     //********************************************************************************************************************
     
    -static ERROR ARCHIVE_Seek(extFile *Self, struct acSeek *Args)
    +static ERR ARCHIVE_Seek(extFile *Self, struct acSeek *Args)
     {
        Log log;
        LARGE pos;
    @@ -406,64 +406,64 @@ static ERROR ARCHIVE_Seek(extFile *Self, struct acSeek *Args)
        if (Args->Position IS SEEK::START) pos = F2T(Args->Offset);
        else if (Args->Position IS SEEK::END) pos = Self->Size - F2T(Args->Offset);
        else if (Args->Position IS SEEK::CURRENT) pos = Self->Position + F2T(Args->Offset);
    -   else return log.warning(ERR_Args);
    +   else return log.warning(ERR::Args);
     
    -   if (pos < 0) return log.warning(ERR_OutOfRange);
    +   if (pos < 0) return log.warning(ERR::OutOfRange);
     
        if (pos < Self->Position) { // The position must be reset to zero if we need to backtrack
           reset_state(Self);
     
    -      ERROR error = seek_to_item(Self);
    -      if (error) return log.warning(error);
    +      ERR error = seek_to_item(Self);
    +      if (error != ERR::Okay) return log.warning(error);
        }
     
        UBYTE buffer[2048];
        while (Self->Position < pos) {
           struct acRead read = { .Buffer = buffer, .Length = (LONG)(pos - Self->Position) };
           if ((size_t)read.Length > sizeof(buffer)) read.Length = sizeof(buffer);
    -      if (Action(AC_Read, Self, &read)) return ERR_Decompression;
    +      if (Action(AC_Read, Self, &read) != ERR::Okay) return ERR::Decompression;
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     
    -static ERROR ARCHIVE_Write(extFile *Self, struct acWrite *Args)
    +static ERR ARCHIVE_Write(extFile *Self, struct acWrite *Args)
     {
        Log log;
    -   return log.warning(ERR_NoSupport);
    +   return log.warning(ERR::NoSupport);
     }
     
     //********************************************************************************************************************
     
    -static ERROR ARCHIVE_GET_Size(extFile *Self, LARGE *Value)
    +static ERR ARCHIVE_GET_Size(extFile *Self, LARGE *Value)
     {
        auto prv = (prvFileArchive *)Self->ChildPrivate;
        if (prv) {
           *Value = prv->Info.OriginalSize;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return ERR_NotInitialised;
    +   else return ERR::NotInitialised;
     }
     
     //********************************************************************************************************************
     // Open the archive: volume for scanning.
     
    -static ERROR open_folder(DirInfo *Dir)
    +static ERR open_folder(DirInfo *Dir)
     {
        std::string file_path;
        Dir->prvIndex = 0;
        Dir->prvTotal = 0;
        Dir->prvHandle = find_archive(Dir->prvResolvedPath, file_path);
    -   if (!Dir->prvHandle) return ERR_DoesNotExist;
    -   return ERR_Okay;
    +   if (!Dir->prvHandle) return ERR::DoesNotExist;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     // Scan the next entry in the folder.
     
    -static ERROR scan_folder(DirInfo *Dir)
    +static ERR scan_folder(DirInfo *Dir)
     {
        Log log(__FUNCTION__);
     
    @@ -489,7 +489,7 @@ static ERROR scan_folder(DirInfo *Dir)
           ZipFile &zf = *it;
     
           if (!path.empty()) {
    -         if (StrCompare(path, zf.Name) != ERR_Okay) continue;
    +         if (StrCompare(path, zf.Name) != ERR::Okay) continue;
           }
     
           // Single folders will appear as 'ABCDEF/'
    @@ -534,7 +534,7 @@ static ERROR scan_folder(DirInfo *Dir)
     
              ((ArchiveDriver *)Dir->Driver)->Index = it;
              Dir->prvTotal++;
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
     
           if (((Dir->prvFlags & RDF::FOLDER) != RDF::NIL) and (zf.IsFolder)) {
    @@ -556,37 +556,37 @@ static ERROR scan_folder(DirInfo *Dir)
     
              ((ArchiveDriver *)Dir->Driver)->Index = it;
              Dir->prvTotal++;
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
        }
     
    -   return ERR_DirEmpty;
    +   return ERR::DirEmpty;
     }
     
     //********************************************************************************************************************
     
    -static ERROR close_folder(DirInfo *Dir)
    +static ERR close_folder(DirInfo *Dir)
     {
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     
    -static ERROR get_info(CSTRING Path, FileInfo *Info, LONG InfoSize)
    +static ERR get_info(CSTRING Path, FileInfo *Info, LONG InfoSize)
     {
        Log log(__FUNCTION__);
        CompressedItem *item;
        std::string file_path;
    -   ERROR error;
    +   ERR error;
     
        log.traceBranch("%s", Path);
     
        if (auto cmp = find_archive(Path, file_path)) {
           struct cmpFind find = { .Path=file_path.c_str(), .Flags=STR::CASE|STR::MATCH_LEN };
    -      if ((error = Action(MT_CmpFind, cmp, &find))) return error;
    +      if ((error = Action(MT_CmpFind, cmp, &find)) != ERR::Okay) return error;
           item = find.Item;
        }
    -   else return ERR_DoesNotExist;
    +   else return ERR::DoesNotExist;
     
        Info->Size     = item->OriginalSize;
        Info->Flags    = RDF::NIL;
    @@ -616,13 +616,13 @@ static ERROR get_info(CSTRING Path, FileInfo *Info, LONG InfoSize)
        Info->UserID      = item->UserID;
        Info->GroupID     = item->GroupID;
        Info->Tags        = NULL;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     // Test an archive: location.
     
    -static ERROR test_path(STRING Path, RSF Flags, LOC *Type)
    +static ERR test_path(STRING Path, RSF Flags, LOC *Type)
     {
        Log log(__FUNCTION__);
     
    @@ -630,19 +630,19 @@ static ERROR test_path(STRING Path, RSF Flags, LOC *Type)
     
        std::string file_path;
        extCompression *cmp;
    -   if (!(cmp = find_archive(Path, file_path))) return ERR_DoesNotExist;
    +   if (!(cmp = find_archive(Path, file_path))) return ERR::DoesNotExist;
     
        if (file_path.empty()) {
           *Type = LOC::VOLUME;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
     
        CompressedItem *item;
    -   ERROR error = cmpFind(cmp, file_path.c_str(), STR::CASE|STR::MATCH_LEN, &item);
    +   ERR error = cmpFind(cmp, file_path.c_str(), STR::CASE|STR::MATCH_LEN, &item);
     
    -   if ((error) and ((Flags & RSF::APPROXIMATE) != RSF::NIL)) {
    +   if ((error != ERR::Okay) and ((Flags & RSF::APPROXIMATE) != RSF::NIL)) {
           file_path.append(".*");
    -      if (!(error = cmpFind(cmp, file_path.c_str(), STR::CASE|STR::WILDCARD, &item))) {
    +      if ((error = cmpFind(cmp, file_path.c_str(), STR::CASE|STR::WILDCARD, &item)) IS ERR::Okay) {
              // Point the path to the discovered item
              LONG i;
              for (i=0; (Path[i] != '/') and (Path[i]); i++);
    @@ -650,17 +650,17 @@ static ERROR test_path(STRING Path, RSF Flags, LOC *Type)
           }
        }
     
    -   if (error) {
    +   if (error != ERR::Okay) {
           log.trace("cmpFind() did not find %s, %s", file_path.c_str(), GetErrorMsg(error));
     
    -      if (error IS ERR_Search) return ERR_DoesNotExist;
    +      if (error IS ERR::Search) return ERR::DoesNotExist;
           else return error;
        }
     
        if ((item->Flags & FL::FOLDER) != FL::NIL) *Type = LOC::FOLDER;
        else *Type = LOC::FILE;
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
    @@ -687,7 +687,7 @@ static const struct FieldArray clArchiveFields[] = {
     
     //********************************************************************************************************************
     
    -extern "C" ERROR add_archive_class(void)
    +extern "C" ERR add_archive_class(void)
     {
        glArchiveClass = extMetaClass::create::global(
           fl::BaseClassID(ID_FILE),
    @@ -698,12 +698,12 @@ extern "C" ERROR add_archive_class(void)
           fl::Fields(clArchiveFields),
           fl::Path("modules:core"));
     
    -   return glArchiveClass ? ERR_Okay : ERR_AddClass;
    +   return glArchiveClass ? ERR::Okay : ERR::AddClass;
     }
     
     //********************************************************************************************************************
     
    -extern "C" ERROR create_archive_volume(void)
    +extern "C" ERR create_archive_volume(void)
     {
        return VirtualVolume("archive",
           VAS::DRIVER_SIZE, sizeof(ArchiveDriver),
    diff --git a/src/core/compression/class_compressed_stream.cpp b/src/core/compression/class_compressed_stream.cpp
    index 4f9140b85..0203c344d 100644
    --- a/src/core/compression/class_compressed_stream.cpp
    +++ b/src/core/compression/class_compressed_stream.cpp
    @@ -35,37 +35,37 @@ class extCompressedStream : public objCompressedStream {
        gz_header Header;
     };
     
    -static ERROR CSTREAM_Reset(extCompressedStream *, APTR);
    +static ERR CSTREAM_Reset(extCompressedStream *, APTR);
     
     //********************************************************************************************************************
     
    -static ERROR CSTREAM_Free(extCompressedStream *Self, APTR Void)
    +static ERR CSTREAM_Free(extCompressedStream *Self, APTR Void)
     {
        CSTREAM_Reset(Self, NULL);
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     
    -static ERROR CSTREAM_Init(extCompressedStream *Self, APTR Void)
    +static ERR CSTREAM_Init(extCompressedStream *Self, APTR Void)
     {
        pf::Log log;
     
    -   if ((!Self->Input) and (!Self->Output)) return log.warning(ERR_FieldNotSet);
    +   if ((!Self->Input) and (!Self->Output)) return log.warning(ERR::FieldNotSet);
     
        if ((Self->Input) and (Self->Output)) {
           log.warning("A CompressedStream can operate in either read or write mode, not both.");
    -      return ERR_Failed;
    +      return ERR::Failed;
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     
    -static ERROR CSTREAM_NewObject(extCompressedStream *Self, APTR Void) {
    +static ERR CSTREAM_NewObject(extCompressedStream *Self, APTR Void) {
        Self->Format = CF::GZIP;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -76,41 +76,41 @@ Read: Decompress data from the input stream and write it to the supplied buffer.
     
     #define MIN_OUTPUT_SIZE ((32 * 1024) + 2048)
     
    -static ERROR CSTREAM_Read(extCompressedStream *Self, struct acRead *Args)
    +static ERR CSTREAM_Read(extCompressedStream *Self, struct acRead *Args)
     {
        pf::Log log;
     
    -   if ((!Args) or (!Args->Buffer)) return log.warning(ERR_NullArgs);
    -   if (!Self->initialised()) return log.warning(ERR_NotInitialised);
    +   if ((!Args) or (!Args->Buffer)) return log.warning(ERR::NullArgs);
    +   if (!Self->initialised()) return log.warning(ERR::NotInitialised);
     
        Args->Result = 0;
    -   if (Args->Length <= 0) return ERR_Okay;
    +   if (Args->Length <= 0) return ERR::Okay;
     
        UBYTE inputstream[2048];
        LONG length;
     
    -   if (acRead(Self->Input, inputstream, sizeof(inputstream), &length)) return ERR_Read;
    +   if (acRead(Self->Input, inputstream, sizeof(inputstream), &length) != ERR::Okay) return ERR::Read;
     
    -   if (length <= 0) return ERR_Okay;
    +   if (length <= 0) return ERR::Okay;
     
        if (!Self->Inflating) {
           log.trace("Initialising decompression of the stream.");
           ClearMemory(&Self->Stream, sizeof(Self->Stream));
           switch (Self->Format) {
              case CF::ZLIB:
    -            if (inflateInit2(&Self->Stream, MAX_WBITS) != ERR_Okay) return log.warning(ERR_Decompression);
    +            if (inflateInit2(&Self->Stream, MAX_WBITS) != Z_OK) return log.warning(ERR::Decompression);
                 break;
     
              case CF::DEFLATE:
    -            if (inflateInit2(&Self->Stream, -MAX_WBITS) != ERR_Okay) return log.warning(ERR_Decompression);
    +            if (inflateInit2(&Self->Stream, -MAX_WBITS) != Z_OK) return log.warning(ERR::Decompression);
                 break;
     
              case CF::GZIP:
              default:
    -            if (inflateInit2(&Self->Stream, 15 + 32) != ERR_Okay) return log.warning(ERR_Decompression);
    +            if (inflateInit2(&Self->Stream, 15 + 32) != Z_OK) return log.warning(ERR::Decompression);
                 // Read the uncompressed size from the gzip header
                 if (inflateGetHeader(&Self->Stream, &Self->Header) != Z_OK) {
    -               return log.warning(ERR_InvalidData);
    +               return log.warning(ERR::InvalidData);
                 }
           }
     
    @@ -123,7 +123,7 @@ static ERROR CSTREAM_Read(extCompressedStream *Self, struct acRead *Args)
           // An internal buffer will need to be allocated if the one supplied to Read() is not large enough.
           outputsize = MIN_OUTPUT_SIZE;
           if (!(output = Self->OutputBuffer)) {
    -         if (AllocMemory(MIN_OUTPUT_SIZE, MEM::DATA|MEM::NO_CLEAR, (APTR *)&Self->OutputBuffer, NULL)) return ERR_AllocMemory;
    +         if (AllocMemory(MIN_OUTPUT_SIZE, MEM::DATA|MEM::NO_CLEAR, (APTR *)&Self->OutputBuffer, NULL) != ERR::Okay) return ERR::AllocMemory;
              output = Self->OutputBuffer;
           }
        }
    @@ -131,7 +131,7 @@ static ERROR CSTREAM_Read(extCompressedStream *Self, struct acRead *Args)
        Self->Stream.next_in  = inputstream;
        Self->Stream.avail_in = length;
     
    -   ERROR error = ERR_Okay;
    +   ERR error = ERR::Okay;
        LONG result = Z_OK;
        while ((result IS Z_OK) and (Self->Stream.avail_in > 0) and (outputsize > 0)) {
           Self->Stream.next_out  = (Bytef *)output;
    @@ -143,7 +143,7 @@ static ERROR CSTREAM_Read(extCompressedStream *Self, struct acRead *Args)
              break;
           }
     
    -      if (error) break;
    +      if (error != ERR::Okay) break;
     
           Args->Result += outputsize - Self->Stream.avail_out;
           output = (Bytef *)output + outputsize - Self->Stream.avail_out;
    @@ -151,7 +151,7 @@ static ERROR CSTREAM_Read(extCompressedStream *Self, struct acRead *Args)
           if (result IS Z_STREAM_END) { // Decompression is complete
              Self->Inflating = FALSE;
              Self->TotalOutput = Self->Stream.total_out;
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
        }
     
    @@ -168,7 +168,7 @@ referenced objects separately.
     
     *********************************************************************************************************************/
     
    -static ERROR CSTREAM_Reset(extCompressedStream *Self, APTR Void)
    +static ERR CSTREAM_Reset(extCompressedStream *Self, APTR Void)
     {
        Self->TotalOutput = 0;
     
    @@ -184,7 +184,7 @@ static ERROR CSTREAM_Reset(extCompressedStream *Self, APTR Void)
     
        if (Self->OutputBuffer) { FreeResource(Self->OutputBuffer); Self->OutputBuffer = NULL; }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -193,17 +193,17 @@ Seek: For use in decompressing streams only.  Seeks to a position within the str
     -END-
     *********************************************************************************************************************/
     
    -static ERROR CSTREAM_Seek(extCompressedStream *Self, struct acSeek *Args)
    +static ERR CSTREAM_Seek(extCompressedStream *Self, struct acSeek *Args)
     {
        pf::Log log;
     
    -   if (!Args) return ERR_NullArgs;
    +   if (!Args) return ERR::NullArgs;
     
        if (Self->Output) { // Seeking in write mode isn't possible (violates the streaming process).
    -      return log.warning(ERR_NoSupport);
    +      return log.warning(ERR::NoSupport);
        }
     
    -   if (!Self->Input) return log.warning(ERR_FieldNotSet);
    +   if (!Self->Input) return log.warning(ERR::FieldNotSet);
     
        // Seeking results in a reset of the compression object's state.  It then needs to decompress the stream up to the
        // position requested by the client.
    @@ -213,19 +213,19 @@ static ERROR CSTREAM_Seek(extCompressedStream *Self, struct acSeek *Args)
        LARGE pos = 0;
        if (Args->Position IS SEEK::START) pos = F2T(Args->Offset);
        else if (Args->Position IS SEEK::CURRENT) pos = Self->TotalOutput + F2T(Args->Offset);
    -   else return log.warning(ERR_Args);
    +   else return log.warning(ERR::Args);
     
    -   if (pos < 0) return log.warning(ERR_OutOfRange);
    +   if (pos < 0) return log.warning(ERR::OutOfRange);
     
        UBYTE buffer[1024];
        while (pos > 0) {
           struct acRead read = { .Buffer = buffer, .Length = (LONG)pos };
           if ((size_t)read.Length > sizeof(buffer)) read.Length = sizeof(buffer);
    -      if (Action(AC_Read, Self, &read)) return ERR_Decompression;
    +      if (Action(AC_Read, Self, &read) != ERR::Okay) return ERR::Decompression;
           pos -= read.Result;
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -234,12 +234,12 @@ Write: Compress raw data in a buffer and write it to the Output object.
     -END-
     *********************************************************************************************************************/
     
    -static ERROR CSTREAM_Write(extCompressedStream *Self, struct acWrite *Args)
    +static ERR CSTREAM_Write(extCompressedStream *Self, struct acWrite *Args)
     {
        pf::Log log;
     
    -   if ((!Args) or (!Args->Buffer)) return log.warning(ERR_NullArgs);
    -   if (!Self->initialised()) return log.warning(ERR_NotInitialised);
    +   if ((!Args) or (!Args->Buffer)) return log.warning(ERR::NullArgs);
    +   if (!Self->initialised()) return log.warning(ERR::NotInitialised);
     
        if (!Self->Deflating) {
           ClearMemory(&Self->Stream, sizeof(Self->Stream));
    @@ -247,20 +247,20 @@ static ERROR CSTREAM_Write(extCompressedStream *Self, struct acWrite *Args)
           switch (Self->Format) {
              case CF::ZLIB:
                 if (deflateInit2(&Self->Stream, 9, Z_DEFLATED, MAX_WBITS, ZLIB_MEM_LEVEL, Z_DEFAULT_STRATEGY)) {
    -               return log.warning(ERR_Compression);
    +               return log.warning(ERR::Compression);
                 }
                 break;
     
              case CF::DEFLATE:
                 if (deflateInit2(&Self->Stream, 9, Z_DEFLATED, -MAX_WBITS, ZLIB_MEM_LEVEL, Z_DEFAULT_STRATEGY)) {
    -               return log.warning(ERR_Compression);
    +               return log.warning(ERR::Compression);
                 }
                 break;
     
              case CF::GZIP:
              default:
                 if (deflateInit2(&Self->Stream, 9, Z_DEFLATED, 15 + 32, ZLIB_MEM_LEVEL, Z_DEFAULT_STRATEGY)) {
    -               return log.warning(ERR_Compression);
    +               return log.warning(ERR::Compression);
                 }
           }
     
    @@ -269,7 +269,7 @@ static ERROR CSTREAM_Write(extCompressedStream *Self, struct acWrite *Args)
        }
     
        if (!Self->OutputBuffer) {
    -      if (AllocMemory(MIN_OUTPUT_SIZE, MEM::DATA|MEM::NO_CLEAR, (APTR *)&Self->OutputBuffer, NULL)) return ERR_AllocMemory;
    +      if (AllocMemory(MIN_OUTPUT_SIZE, MEM::DATA|MEM::NO_CLEAR, (APTR *)&Self->OutputBuffer, NULL) != ERR::Okay) return ERR::AllocMemory;
        }
     
        Args->Result = 0;
    @@ -296,7 +296,7 @@ static ERROR CSTREAM_Write(extCompressedStream *Self, struct acWrite *Args)
           if ((deflate(&Self->Stream, mode))) {
              deflateEnd(&Self->Stream);
              Self->Deflating = FALSE;
    -         return ERR_BufferOverflow;
    +         return ERR::BufferOverflow;
           }
     
           const LONG len = MIN_OUTPUT_SIZE - Self->Stream.avail_out; // Get number of compressed bytes that were output
    @@ -307,7 +307,7 @@ static ERROR CSTREAM_Write(extCompressedStream *Self, struct acWrite *Args)
              acWrite(Self->Output, Self->OutputBuffer, len, NULL);
           }
           else {
    -         // deflate() may not output anything if it needs more data to fill up a compression frame.  Return ERR_Okay
    +         // deflate() may not output anything if it needs more data to fill up a compression frame.  Return ERR::Okay
              // and wait for more data, or for the developer to end the stream.
     
              //log.trace("No data output on this cycle.");
    @@ -320,7 +320,7 @@ static ERROR CSTREAM_Write(extCompressedStream *Self, struct acWrite *Args)
           Self->Deflating = FALSE;
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -356,7 +356,7 @@ If the size is unknown, a value of -1 is returned.
     
     *********************************************************************************************************************/
     
    -static ERROR CSTREAM_GET_Size(extCompressedStream *Self, LARGE *Value)
    +static ERR CSTREAM_GET_Size(extCompressedStream *Self, LARGE *Value)
     {
        *Value = -1;
        if (Self->Input) {
    @@ -364,9 +364,9 @@ static ERROR CSTREAM_GET_Size(extCompressedStream *Self, LARGE *Value)
              if (Self->Header.extra) *Value = Self->Header.extra_len;
           }
     
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return ERR_Failed;
    +   else return ERR::Failed;
     }
     
     /*********************************************************************************************************************
    @@ -400,7 +400,7 @@ static const ActionArray clStreamActions[] = {
        { 0, NULL }
     };
     
    -extern "C" ERROR add_compressed_stream_class(void)
    +extern "C" ERR add_compressed_stream_class(void)
     {
        glCompressedStreamClass = extMetaClass::create::global(
           fl::BaseClassID(ID_COMPRESSEDSTREAM),
    @@ -413,5 +413,5 @@ extern "C" ERROR add_compressed_stream_class(void)
           fl::Size(sizeof(extCompressedStream)),
           fl::Path("modules:core"));
     
    -   return glCompressedStreamClass ? ERR_Okay : ERR_AddClass;
    +   return glCompressedStreamClass ? ERR::Okay : ERR::AddClass;
     }
    diff --git a/src/core/compression/class_compression.cpp b/src/core/compression/class_compression.cpp
    index 084bb60d3..45f0ea793 100644
    --- a/src/core/compression/class_compression.cpp
    +++ b/src/core/compression/class_compression.cpp
    @@ -206,18 +206,18 @@ class extCompression : public objCompression {
        bool   Inflating;
     };
     
    -static ERROR compress_folder(extCompression *, std::string, std::string);
    -static ERROR compress_file(extCompression *, std::string, std::string, bool);
    +static ERR compress_folder(extCompression *, std::string, std::string);
    +static ERR compress_file(extCompression *, std::string, std::string, bool);
     static void print(extCompression *, CSTRING);
     static void print(extCompression *, std::string);
    -static ERROR remove_file(extCompression *, std::list::iterator &);
    -static ERROR scan_zip(extCompression *);
    -static ERROR fast_scan_zip(extCompression *);
    -static ERROR send_feedback(extCompression *, CompressionFeedback *);
    +static ERR remove_file(extCompression *, std::list::iterator &);
    +static ERR scan_zip(extCompression *);
    +static ERR fast_scan_zip(extCompression *);
    +static ERR send_feedback(extCompression *, CompressionFeedback *);
     static void write_eof(extCompression *);
     void zipfile_to_item(ZipFile &, CompressedItem &);
     
    -static ERROR GET_Size(extCompression *, LARGE *);
    +static ERR GET_Size(extCompression *, LARGE *);
     
     //********************************************************************************************************************
     // Special definitions.
    @@ -271,18 +271,18 @@ static const UBYTE glTail[TAIL_LENGTH] = {
     
     //********************************************************************************************************************
     
    -ERROR convert_zip_error(struct z_stream_s *Stream, LONG Result)
    +ERR convert_zip_error(struct z_stream_s *Stream, LONG Result)
     {
        pf::Log log;
     
    -   ERROR error;
    +   ERR error;
        switch(Result) {
    -      case Z_STREAM_ERROR:  error = ERR_Failed;
    -      case Z_DATA_ERROR:    error = ERR_InvalidData;
    -      case Z_MEM_ERROR:     error = ERR_Memory;
    -      case Z_BUF_ERROR:     error = ERR_BufferOverflow;
    -      case Z_VERSION_ERROR: error = ERR_WrongVersion;
    -      default:              error = ERR_Failed;
    +      case Z_STREAM_ERROR:  error = ERR::Failed;
    +      case Z_DATA_ERROR:    error = ERR::InvalidData;
    +      case Z_MEM_ERROR:     error = ERR::Memory;
    +      case Z_BUF_ERROR:     error = ERR::BufferOverflow;
    +      case Z_VERSION_ERROR: error = ERR::WrongVersion;
    +      default:              error = ERR::Failed;
        }
     
        if (Stream->msg) log.warning("%s", Stream->msg);
    @@ -293,10 +293,10 @@ ERROR convert_zip_error(struct z_stream_s *Stream, LONG Result)
     
     //********************************************************************************************************************
     
    -static void notify_free_feedback(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, APTR Args)
    +static void notify_free_feedback(OBJECTPTR Object, ACTIONID ActionID, ERR Result, APTR Args)
     {
        auto Self = (extCompression *)CurrentContext();
    -   Self->Feedback.Type = CALL_NONE;
    +   Self->Feedback.clear();
     }
     
     /*********************************************************************************************************************
    @@ -307,7 +307,7 @@ CompressBuffer: Compresses a plain memory area into an empty buffer.
     This method provides a simple way of compressing a memory area into a buffer.  It requires a reference to the
     source data and a buffer large enough to accept the compressed information.  Generally the destination buffer should
     be no smaller than 75% of the size of the source data.  If the destination buffer is not large enough, an error of
    -`ERR_BufferOverflow` will be returned.  The size of the compressed data will be returned in the Result parameter.
    +`ERR::BufferOverflow` will be returned.  The size of the compressed data will be returned in the Result parameter.
     
     To decompress the data that is output by this function, use the #DecompressBuffer() method.
     
    @@ -331,12 +331,12 @@ BufferOverflow: The output buffer is not large enough.
     
     *********************************************************************************************************************/
     
    -static ERROR COMPRESSION_CompressBuffer(extCompression *Self, struct cmpCompressBuffer *Args)
    +static ERR COMPRESSION_CompressBuffer(extCompression *Self, struct cmpCompressBuffer *Args)
     {
        pf::Log log;
     
        if ((!Args) or (!Args->Input) or (Args->InputSize <= 0) or (!Args->Output) or (Args->OutputSize <= 8)) {
    -      return log.warning(ERR_Args);
    +      return log.warning(ERR::Args);
        }
     
        Self->Zip.next_in   = (Bytef *)Args->Input;
    @@ -348,7 +348,7 @@ static ERROR COMPRESSION_CompressBuffer(extCompression *Self, struct cmpCompress
        if (level < 0) level = 0;
        else if (level > 9) level = 9;
     
    -   if (deflateInit2(&Self->Zip, level, Z_DEFLATED, Self->WindowBits, ZLIB_MEM_LEVEL, Z_DEFAULT_STRATEGY) IS ERR_Okay) {
    +   if (deflateInit2(&Self->Zip, level, Z_DEFLATED, Self->WindowBits, ZLIB_MEM_LEVEL, Z_DEFAULT_STRATEGY) IS Z_OK) {
           if (deflate(&Self->Zip, Z_FINISH) IS Z_STREAM_END) {
              Args->Result = Self->Zip.total_out + 8;
              deflateEnd(&Self->Zip);
    @@ -358,14 +358,14 @@ static ERROR COMPRESSION_CompressBuffer(extCompression *Self, struct cmpCompress
              ((char *)Args->Output)[2] = 'I';
              ((char *)Args->Output)[3] = 'B';
              ((LONG *)Args->Output)[1] = Self->Zip.total_out;
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
           else {
              deflateEnd(&Self->Zip);
    -         return log.warning(ERR_BufferOverflow);
    +         return log.warning(ERR::BufferOverflow);
           }
        }
    -   else return log.warning(ERR_Failed);
    +   else return log.warning(ERR::Failed);
     }
     
     /*********************************************************************************************************************
    @@ -381,7 +381,7 @@ Failed: Failed to initialise the decompression process.
     
     *********************************************************************************************************************/
     
    -static ERROR COMPRESSION_CompressStreamStart(extCompression *Self, APTR Void)
    +static ERR COMPRESSION_CompressStreamStart(extCompression *Self, APTR Void)
     {
        pf::Log log;
     
    @@ -397,13 +397,12 @@ static ERROR COMPRESSION_CompressStreamStart(extCompression *Self, APTR Void)
        ClearMemory(&Self->DeflateStream, sizeof(Self->DeflateStream));
     
        Self->TotalOutput = 0;
    -   LONG err;
    -   if ((err = deflateInit2(&Self->DeflateStream, level, Z_DEFLATED, Self->WindowBits, ZLIB_MEM_LEVEL, Z_DEFAULT_STRATEGY)) IS ERR_Okay) {
    +   if (auto err = deflateInit2(&Self->DeflateStream, level, Z_DEFLATED, Self->WindowBits, ZLIB_MEM_LEVEL, Z_DEFAULT_STRATEGY); err IS Z_OK) {
           log.trace("Compression stream initialised.");
           Self->Deflating = true;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return log.warning(ERR_Failed);
    +   else return log.warning(ERR::Failed);
     }
     
     /*********************************************************************************************************************
    @@ -426,7 +425,7 @@ the stream.  We recommend that the compression object's sub-class ID is stored f
     The following C code illustrates a simple means of compressing a file to another file using a stream:
     
     
    -ERROR error = mtCompressStreamStart(compress);
    +ERR error = mtCompressStreamStart(compress);
     
     if (!error) {
        LONG len;
    @@ -477,13 +476,13 @@ Retry: Please recall the method using a larger output buffer.
     
     *********************************************************************************************************************/
     
    -static ERROR COMPRESSION_CompressStream(extCompression *Self, struct cmpCompressStream *Args)
    +static ERR COMPRESSION_CompressStream(extCompression *Self, struct cmpCompressStream *Args)
     {
        pf::Log log;
     
    -   if ((!Args) or (!Args->Input) or (!Args->Callback)) return log.warning(ERR_NullArgs);
    +   if ((!Args) or (!Args->Input) or (!Args->Callback)) return log.warning(ERR::NullArgs);
     
    -   if (!Self->Deflating) return log.warning(ERR_Failed);
    +   if (!Self->Deflating) return log.warning(ERR::Failed);
     
        Self->DeflateStream.next_in   = (Bytef *)Args->Input;
        Self->DeflateStream.avail_in  = Args->Length;
    @@ -494,7 +493,7 @@ static ERROR COMPRESSION_CompressStream(extCompression *Self, struct cmpCompress
           outputsize = Args->OutputSize;
           if (outputsize < Self->MinOutputSize) {
              log.warning("OutputSize (%d) < MinOutputSize (%d)", outputsize, Self->MinOutputSize);
    -         return ERR_BufferOverflow;
    +         return ERR::BufferOverflow;
           }
        }
        else if ((output = Self->OutputBuffer)) {
    @@ -502,8 +501,8 @@ static ERROR COMPRESSION_CompressStream(extCompression *Self, struct cmpCompress
        }
        else {
           Self->OutputSize = 32 * 1024;
    -      if (AllocMemory(Self->OutputSize, MEM::DATA|MEM::NO_CLEAR, (APTR *)&Self->OutputBuffer, NULL) != ERR_Okay) {
    -         return ERR_AllocMemory;
    +      if (AllocMemory(Self->OutputSize, MEM::DATA|MEM::NO_CLEAR, (APTR *)&Self->OutputBuffer, NULL) != ERR::Okay) {
    +         return ERR::AllocMemory;
           }
           output = Self->OutputBuffer;
           outputsize = Self->OutputSize;
    @@ -514,17 +513,17 @@ static ERROR COMPRESSION_CompressStream(extCompression *Self, struct cmpCompress
        // If zlib succeeds but sets avail_out to zero, this means that data was written to the output buffer, but the
        // output buffer is not large enough (so keep calling until avail_out > 0).
     
    -   ERROR error;
    +   ERR error;
        Self->DeflateStream.avail_out = 0;
        while (Self->DeflateStream.avail_out IS 0) {
           Self->DeflateStream.next_out  = (Bytef *)output;
           Self->DeflateStream.avail_out = outputsize;
           if ((err = deflate(&Self->DeflateStream, Z_NO_FLUSH))) {
              deflateEnd(&Self->DeflateStream);
    -         error = ERR_BufferOverflow;
    +         error = ERR::BufferOverflow;
              break;
           }
    -      else error = ERR_Okay;
    +      else error = ERR::Okay;
     
           auto len = outputsize - Self->DeflateStream.avail_out; // Get number of compressed bytes that were output
     
    @@ -533,19 +532,19 @@ static ERROR COMPRESSION_CompressStream(extCompression *Self, struct cmpCompress
     
              log.trace("%d bytes (total %" PF64 ") were compressed.", len, Self->TotalOutput);
     
    -         if (Args->Callback->Type IS CALL_STDC) {
    +         if (Args->Callback->isC()) {
                 pf::SwitchContext context(Args->Callback->StdC.Context);
    -            auto routine = (ERROR (*)(extCompression *, APTR, LONG))Args->Callback->StdC.Routine;
    -            error = routine(Self, output, len);
    +            auto routine = (ERR (*)(extCompression *, APTR, LONG, APTR))Args->Callback->StdC.Routine;
    +            error = routine(Self, output, len, Args->Callback->StdC.Meta);
              }
    -         else if (Args->Callback->Type IS CALL_SCRIPT) {
    +         else if (Args->Callback->isScript()) {
                 const ScriptArg args[] = {
    -               { "Compression",  Self,   FD_OBJECTPTR },
    -               { "Output",       output, FD_BUFFER },
    -               { "OutputLength", LONG(len), FD_LONG|FD_BUFSIZE }
    +               ScriptArg("Compression",  Self, FD_OBJECTPTR),
    +               ScriptArg("Output",       output, FD_BUFFER),
    +               ScriptArg("OutputLength", LONG(len), FD_LONG|FD_BUFSIZE)
                 };
                 auto script = Args->Callback->Script.Script;
    -            if (scCallback(script, Args->Callback->Script.ProcedureID, args, ARRAYSIZE(args), &error)) error = ERR_Failed;
    +            if (scCallback(script, Args->Callback->Script.ProcedureID, args, std::ssize(args), &error) != ERR::Okay) error = ERR::Failed;
              }
              else {
                 log.warning("Callback function structure does not specify a recognised Type.");
    @@ -553,7 +552,7 @@ static ERROR COMPRESSION_CompressStream(extCompression *Self, struct cmpCompress
              }
           }
           else {
    -         // deflate() may not output anything if it needs more data to fill up a compression frame.  Return ERR_Okay
    +         // deflate() may not output anything if it needs more data to fill up a compression frame.  Return ERR::Okay
              // and wait for more data, or for the developer to call CompressStreamEnd().
     
              //log.trace("No data output on this cycle.");
    @@ -561,7 +560,7 @@ static ERROR COMPRESSION_CompressStream(extCompression *Self, struct cmpCompress
           }
        }
     
    -   if (error) log.warning(error);
    +   if (error != ERR::Okay) log.warning(error);
        return error;
     }
     
    @@ -587,24 +586,24 @@ BufferOverflow: The supplied Output buffer is not large enough (check the MinOut
     
     *********************************************************************************************************************/
     
    -static ERROR COMPRESSION_CompressStreamEnd(extCompression *Self, struct cmpCompressStreamEnd *Args)
    +static ERR COMPRESSION_CompressStreamEnd(extCompression *Self, struct cmpCompressStreamEnd *Args)
     {
        pf::Log log;
     
    -   if ((!Args) or (!Args->Callback)) return log.warning(ERR_NullArgs);
    -   if (!Self->Deflating) return ERR_Okay;
    +   if ((!Args) or (!Args->Callback)) return log.warning(ERR::NullArgs);
    +   if (!Self->Deflating) return ERR::Okay;
     
        APTR output;
        LONG outputsize;
     
        if ((output = Args->Output)) {
           outputsize = Args->OutputSize;
    -      if (outputsize < Self->MinOutputSize) return log.warning(ERR_BufferOverflow);
    +      if (outputsize < Self->MinOutputSize) return log.warning(ERR::BufferOverflow);
        }
        else if ((output = Self->OutputBuffer)) {
           outputsize = Self->OutputSize;
        }
    -   else return log.warning(ERR_FieldNotSet);
    +   else return log.warning(ERR::FieldNotSet);
     
        log.trace("Output Size: %d", outputsize);
     
    @@ -612,33 +611,33 @@ static ERROR COMPRESSION_CompressStreamEnd(extCompression *Self, struct cmpCompr
        Self->DeflateStream.avail_in  = 0;
        Self->DeflateStream.avail_out = 0;
     
    -   ERROR error;
    +   ERR error;
        LONG err = Z_OK;
        while ((Self->DeflateStream.avail_out IS 0) and (err IS Z_OK)) {
           Self->DeflateStream.next_out  = (Bytef *)output;
           Self->DeflateStream.avail_out = outputsize;
           if ((err = deflate(&Self->DeflateStream, Z_FINISH)) and (err != Z_STREAM_END)) {
    -         error = log.warning(ERR_BufferOverflow);
    +         error = log.warning(ERR::BufferOverflow);
              break;
           }
     
           Self->TotalOutput += outputsize - Self->DeflateStream.avail_out;
     
    -      if (Args->Callback->Type IS CALL_STDC) {
    +      if (Args->Callback->isC()) {
              pf::SwitchContext context(Args->Callback->StdC.Context);
    -         auto routine = (ERROR (*)(extCompression *, APTR, LONG))Args->Callback->StdC.Routine;
    -         error = routine(Self, output, outputsize - Self->DeflateStream.avail_out);
    +         auto routine = (ERR (*)(extCompression *, APTR, LONG, APTR Meta))Args->Callback->StdC.Routine;
    +         error = routine(Self, output, outputsize - Self->DeflateStream.avail_out, Args->Callback->StdC.Meta);
           }
    -      else if (Args->Callback->Type IS CALL_SCRIPT) {
    +      else if (Args->Callback->isScript()) {
              const ScriptArg args[] = {
                 { "Compression",  Self,   FD_OBJECTPTR },
                 { "Output",       output, FD_BUFFER },
                 { "OutputLength", LONG(outputsize - Self->DeflateStream.avail_out), FD_LONG|FD_BUFSIZE }
              };
              auto script = Args->Callback->Script.Script;
    -         if (scCallback(script, Args->Callback->Script.ProcedureID, args, ARRAYSIZE(args), &error)) error = ERR_Failed;
    +         if (scCallback(script, Args->Callback->Script.ProcedureID, args, std::ssize(args), &error) != ERR::Okay) error = ERR::Failed;
           }
    -      else error = ERR_Okay;
    +      else error = ERR::Okay;
        }
     
        // Free the output buffer if it is quite large
    @@ -674,7 +673,7 @@ Failed: Failed to initialise the decompression process.
     
     *********************************************************************************************************************/
     
    -static ERROR COMPRESSION_DecompressStreamStart(extCompression *Self, APTR Void)
    +static ERR COMPRESSION_DecompressStreamStart(extCompression *Self, APTR Void)
     {
        pf::Log log;
     
    @@ -684,13 +683,12 @@ static ERROR COMPRESSION_DecompressStreamStart(extCompression *Self, APTR Void)
     
        Self->TotalOutput = 0;
     
    -   LONG err;
    -   if ((err = inflateInit2(&Self->InflateStream, Self->WindowBits)) IS ERR_Okay) {
    +   if (auto err = inflateInit2(&Self->InflateStream, Self->WindowBits); err IS Z_OK) {
           log.trace("Decompression stream initialised.");
           Self->Inflating = true;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return log.warning(ERR_Failed);
    +   else return log.warning(ERR::Failed);
     }
     
     /*********************************************************************************************************************
    @@ -702,7 +700,7 @@ Call DecompressStream repeatedly to decompress a data stream and process the res
     will need to provide a pointer to the data in the Input parameter and indicate its size in Length.  The decompression
     routine will call the routine that was specified in Callback for each block that is decompressed.
     
    -The format of the Callback routine is `ERROR Function(*Compression, APTR Buffer, LONG Length)`
    +The format of the Callback routine is `ERR Function(*Compression, APTR Buffer, LONG Length)`
     
     The Buffer will refer to the start of the decompressed data and its size will be indicated in Length.  If the Callback
     routine returns an error of any kind, the decompression process will be stopped and the error code will be immediately
    @@ -729,27 +727,27 @@ BufferOverflow: The output buffer is not large enough.
     
     *********************************************************************************************************************/
     
    -static ERROR COMPRESSION_DecompressStream(extCompression *Self, struct cmpDecompressStream *Args)
    +static ERR COMPRESSION_DecompressStream(extCompression *Self, struct cmpDecompressStream *Args)
     {
        pf::Log log;
     
    -   if ((!Args) or (!Args->Input) or (!Args->Callback)) return log.warning(ERR_NullArgs);
    -   if (!Self->Inflating) return ERR_Okay; // Decompression is complete
    +   if ((!Args) or (!Args->Input) or (!Args->Callback)) return log.warning(ERR::NullArgs);
    +   if (!Self->Inflating) return ERR::Okay; // Decompression is complete
     
        APTR output;
        LONG outputsize;
     
        if ((output = Args->Output)) {
           outputsize = Args->OutputSize;
    -      if (outputsize < Self->MinOutputSize) return log.warning(ERR_BufferOverflow);
    +      if (outputsize < Self->MinOutputSize) return log.warning(ERR::BufferOverflow);
        }
        else if ((output = Self->OutputBuffer)) {
           outputsize = Self->OutputSize;
        }
        else {
           Self->OutputSize = 32 * 1024;
    -      if (AllocMemory(Self->OutputSize, MEM::DATA|MEM::NO_CLEAR, (APTR *)&Self->OutputBuffer, NULL) != ERR_Okay) {
    -         return ERR_AllocMemory;
    +      if (AllocMemory(Self->OutputSize, MEM::DATA|MEM::NO_CLEAR, (APTR *)&Self->OutputBuffer, NULL) != ERR::Okay) {
    +         return ERR::AllocMemory;
           }
           output = Self->OutputBuffer;
           outputsize = Self->OutputSize;
    @@ -760,7 +758,7 @@ static ERROR COMPRESSION_DecompressStream(extCompression *Self, struct cmpDecomp
     
        // Keep looping until Z_STREAM_END or an error is returned
     
    -   ERROR error = ERR_Okay;
    +   ERR error = ERR::Okay;
        LONG result = Z_OK;
        while ((result IS Z_OK) and (Self->InflateStream.avail_in > 0)) {
           Self->InflateStream.next_out  = (Bytef *)output;
    @@ -772,25 +770,25 @@ static ERROR COMPRESSION_DecompressStream(extCompression *Self, struct cmpDecomp
              break;
           }
     
    -      if (error) break;
    +      if (error != ERR::Okay) break;
     
           // Write out the decompressed data
     
           LONG len = outputsize - Self->InflateStream.avail_out;
           if (len > 0) {
    -         if (Args->Callback->Type IS CALL_STDC) {
    +         if (Args->Callback->isC()) {
                 pf::SwitchContext context(Args->Callback->StdC.Context);
    -            auto routine = (ERROR (*)(extCompression *, APTR, LONG))Args->Callback->StdC.Routine;
    -            error = routine(Self, output, len);
    +            auto routine = (ERR (*)(extCompression *, APTR, LONG, APTR))Args->Callback->StdC.Routine;
    +            error = routine(Self, output, len, Args->Callback->StdC.Meta);
              }
    -         else if (Args->Callback->Type IS CALL_SCRIPT) {
    +         else if (Args->Callback->isScript()) {
                 const ScriptArg args[] = {
                    { "Compression",  Self,   FD_OBJECTPTR },
                    { "Output",       output, FD_BUFFER },
                    { "OutputLength", len,    FD_LONG|FD_BUFSIZE }
                 };
                 auto script = Args->Callback->Script.Script;
    -            if (scCallback(script, Args->Callback->Script.ProcedureID, args, ARRAYSIZE(args), &error)) error = ERR_Failed;
    +            if (scCallback(script, Args->Callback->Script.ProcedureID, args, std::ssize(args), &error) != ERR::Okay) error = ERR::Failed;
              }
              else {
                 log.warning("Callback function structure does not specify a recognised Type.");
    @@ -798,7 +796,7 @@ static ERROR COMPRESSION_DecompressStream(extCompression *Self, struct cmpDecomp
              }
           }
     
    -      if (error) break;
    +      if (error != ERR::Okay) break;
     
           if (result IS Z_STREAM_END) { // Decompression is complete, auto-perform DecompressStreamEnd()
              inflateEnd(&Self->InflateStream);
    @@ -808,7 +806,7 @@ static ERROR COMPRESSION_DecompressStream(extCompression *Self, struct cmpDecomp
           }
        }
     
    -   if (error) log.warning(error);
    +   if (error != ERR::Okay) log.warning(error);
        return error;
     }
     
    @@ -829,18 +827,18 @@ NullArgs
     
     *********************************************************************************************************************/
     
    -static ERROR COMPRESSION_DecompressStreamEnd(extCompression *Self, struct cmpDecompressStreamEnd *Args)
    +static ERR COMPRESSION_DecompressStreamEnd(extCompression *Self, struct cmpDecompressStreamEnd *Args)
     {
        pf::Log log;
     
    -   if (!Self->Inflating) return ERR_Okay; // If not inflating, not a problem
    +   if (!Self->Inflating) return ERR::Okay; // If not inflating, not a problem
     
    -   if ((!Args) or (!Args->Callback)) return log.warning(ERR_NullArgs);
    +   if ((!Args) or (!Args->Callback)) return log.warning(ERR::NullArgs);
     
        Self->TotalOutput = Self->InflateStream.total_out;
        inflateEnd(&Self->InflateStream);
        Self->Inflating = false;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -873,16 +871,16 @@ NoSupport: The sub-class does not support this method.
     
     *********************************************************************************************************************/
     
    -static ERROR COMPRESSION_CompressFile(extCompression *Self, struct cmpCompressFile *Args)
    +static ERR COMPRESSION_CompressFile(extCompression *Self, struct cmpCompressFile *Args)
     {
        pf::Log log;
     
    -   if ((!Args) or (!Args->Location) or (!*Args->Location)) return log.warning(ERR_NullArgs);
    -   if (!Self->FileIO) return log.warning(ERR_MissingPath);
    +   if ((!Args) or (!Args->Location) or (!*Args->Location)) return log.warning(ERR::NullArgs);
    +   if (!Self->FileIO) return log.warning(ERR::MissingPath);
     
    -   if ((Self->Flags & CMF::READ_ONLY) != CMF::NIL) return log.warning(ERR_NoPermission);
    +   if ((Self->Flags & CMF::READ_ONLY) != CMF::NIL) return log.warning(ERR::NoPermission);
     
    -   if (Self->isSubClass()) return log.warning(ERR_NoSupport);
    +   if (Self->isSubClass()) return log.warning(ERR::NoSupport);
     
        if (Self->OutputID) {
           std::ostringstream out;
    @@ -946,7 +944,7 @@ static ERROR COMPRESSION_CompressFile(extCompression *Self, struct cmpCompressFi
           return compress_folder(Self, src, path);
        }
     
    -   ERROR error = ERR_Okay;
    +   ERR error = ERR::Okay;
     
        // Check the location string for wildcards, * and ?
     
    @@ -967,10 +965,10 @@ static ERROR COMPRESSION_CompressFile(extCompression *Self, struct cmpCompressFi
           std::string srcfolder(src, pathlen); // Extract the path without the file name
     
           DirInfo *dir;
    -      if (!OpenDir(srcfolder.c_str(), RDF::FILE, &dir)) {
    -         while (!ScanDir(dir)) {
    +      if (OpenDir(srcfolder.c_str(), RDF::FILE, &dir) IS ERR::Okay) {
    +         while (ScanDir(dir) IS ERR::Okay) {
                 FileInfo *scan = dir->Info;
    -            if (!StrCompare(filename, scan->Name, 0, STR::WILDCARD)) {
    +            if (StrCompare(filename, scan->Name, 0, STR::WILDCARD) IS ERR::Okay) {
                    auto folder = src.substr(0, pathlen);
                    folder.append(scan->Name);
                    error = compress_file(Self, folder, path, FALSE);
    @@ -1000,7 +998,7 @@ DecompressBuffer: Decompresses data originating from the CompressBuffer method.
     This method is used to decompress data that has been packed using the #CompressBuffer() method.  A pointer to the
     compressed data and an output buffer large enough to contain the decompressed data are required.  If the output buffer
     is not large enough to contain the data, the method will write out as much information as it can and then return with
    -an error code of `ERR_BufferOverflow`.
    +an error code of `ERR::BufferOverflow`.
     
     -INPUT-
     buf(ptr) Input: Pointer to the compressed data.
    @@ -1015,12 +1013,12 @@ BufferOverflow: The output buffer is not large enough to hold the decompressed i
     
     *********************************************************************************************************************/
     
    -static ERROR COMPRESSION_DecompressBuffer(extCompression *Self, struct cmpDecompressBuffer *Args)
    +static ERR COMPRESSION_DecompressBuffer(extCompression *Self, struct cmpDecompressBuffer *Args)
     {
        pf::Log log;
     
        if ((!Args) or (!Args->Input) or (!Args->Output) or (Args->OutputSize <= 0)) {
    -      return log.warning(ERR_NullArgs);
    +      return log.warning(ERR::NullArgs);
        }
     
        Self->Zip.next_in   = (Bytef *)Args->Input + 8;
    @@ -1028,21 +1026,21 @@ static ERROR COMPRESSION_DecompressBuffer(extCompression *Self, struct cmpDecomp
        Self->Zip.next_out  = (Bytef *)Args->Output;
        Self->Zip.avail_out = Args->OutputSize;
     
    -   if (inflateInit2(&Self->Zip, Self->WindowBits) IS ERR_Okay) {
    +   if (inflateInit2(&Self->Zip, Self->WindowBits) IS Z_OK) {
           LONG err;
           if ((err = inflate(&Self->Zip, Z_FINISH)) IS Z_STREAM_END) {
              Args->Result = Self->Zip.total_out;
              inflateEnd(&Self->Zip);
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
           else {
              inflateEnd(&Self->Zip);
              if (Self->Zip.msg) log.warning("%s", Self->Zip.msg);
    -         else log.warning(ERR_BufferOverflow);
    -         return ERR_BufferOverflow;
    +         else log.warning(ERR::BufferOverflow);
    +         return ERR::BufferOverflow;
           }
        }
    -   else return log.warning(ERR_Failed);
    +   else return log.warning(ERR::Failed);
     }
     
     /*********************************************************************************************************************
    @@ -1080,41 +1078,41 @@ Failed
     
     *********************************************************************************************************************/
     
    -static ERROR COMPRESSION_DecompressFile(extCompression *Self, struct cmpDecompressFile *Args)
    +static ERR COMPRESSION_DecompressFile(extCompression *Self, struct cmpDecompressFile *Args)
     {
        pf::Log log;
     
    -   if (Self->Files.empty()) return ERR_NoData;
    +   if (Self->Files.empty()) return ERR::NoData;
     
        // Validate arguments
     
        if ((!Args) or (!Args->Path)) {
           if (Self->OutputID) print(Self, "Please supply a Path setting that refers to a compressed file archive.\n");
     
    -      return log.warning(ERR_NullArgs);
    +      return log.warning(ERR::NullArgs);
        }
     
        if (!Args->Dest) {
           if (Self->OutputID) print(Self, "Please supply a Destination that refers to a folder for decompression.\n");
     
    -      return log.warning(ERR_NullArgs);
    +      return log.warning(ERR::NullArgs);
        }
     
        if ((!*Args->Path) or (!*Args->Dest)) {
           if (Self->OutputID) print(Self, "Please supply valid Path and Destination settings.\n");
     
    -      return log.warning(ERR_Args);
    +      return log.warning(ERR::Args);
        }
     
        if (!Self->FileIO) {
           if (Self->OutputID) print(Self, "Internal error - decompression aborted.\n");
     
    -      return log.warning(ERR_MissingPath);
    +      return log.warning(ERR::MissingPath);
        }
     
    -   // If the object belongs to a Compression sub-class, return ERR_NoSupport
    +   // If the object belongs to a Compression sub-class, return ERR::NoSupport
     
    -   if (Self->isSubClass()) return ERR_NoSupport;
    +   if (Self->isSubClass()) return ERR::NoSupport;
     
        // Tell the user what we are doing
     
    @@ -1133,7 +1131,7 @@ static ERROR COMPRESSION_DecompressFile(extCompression *Self, struct cmpDecompre
        UWORD pathend = 0;
        for (UWORD i=0; Args->Path[i]; i++) if ((Args->Path[i] IS '/') or (Args->Path[i] IS '\\')) pathend = i + 1;
     
    -   ERROR error      = ERR_Okay;
    +   ERR error      = ERR::Okay;
        bool inflate_end = false;
        Self->FileIndex = 0;
     
    @@ -1142,7 +1140,7 @@ static ERROR COMPRESSION_DecompressFile(extCompression *Self, struct cmpDecompre
     
        for (auto &zf : Self->Files) {
           log.trace("Found %s", zf.Name);
    -      if (!StrCompare(Args->Path, zf.Name, 0, STR::WILDCARD)) {
    +      if (StrCompare(Args->Path, zf.Name, 0, STR::WILDCARD) IS ERR::Okay) {
              log.trace("Extracting \"%s\"", zf.Name);
     
              if (Self->OutputID) {
    @@ -1162,7 +1160,7 @@ static ERROR COMPRESSION_DecompressFile(extCompression *Self, struct cmpDecompre
     
              if ((destpath.back() IS '/') or (destpath.back() IS '\\')) {
                 LOC result;
    -            if ((!AnalysePath(destpath.c_str(), &result)) and (result IS LOC::DIRECTORY)) {
    +            if ((AnalysePath(destpath.c_str(), &result) IS ERR::Okay) and (result IS LOC::DIRECTORY)) {
                    Self->FileIndex++;
                    continue;
                 }
    @@ -1185,29 +1183,29 @@ static ERROR COMPRESSION_DecompressFile(extCompression *Self, struct cmpDecompre
              feedback.Progress       = 0;
     
              error = send_feedback(Self, &feedback);
    -         if ((error IS ERR_Terminate) or (error IS ERR_Cancelled)) {
    -            error = ERR_Cancelled;
    +         if ((error IS ERR::Terminate) or (error IS ERR::Cancelled)) {
    +            error = ERR::Cancelled;
                 goto exit;
              }
    -         else if (error IS ERR_Skip) {
    -            error = ERR_Okay;
    +         else if (error IS ERR::Skip) {
    +            error = ERR::Okay;
                 Self->FileIndex++; // Increase counter to show that the file was analysed
                 continue;
              }
    -         else error = ERR_Okay;
    +         else error = ERR::Okay;
     
              // Seek to the start of the compressed data
     
    -         if (acSeek(Self->FileIO, zf.Offset + HEAD_NAMELEN, SEEK::START) != ERR_Okay) {
    -            error = log.warning(ERR_Seek);
    +         if (acSeek(Self->FileIO, zf.Offset + HEAD_NAMELEN, SEEK::START) != ERR::Okay) {
    +            error = log.warning(ERR::Seek);
                 goto exit;
              }
     
              UWORD namelen, extralen;
    -         if (flReadLE(Self->FileIO, &namelen)) { error = ERR_Read; goto exit; }
    -         if (flReadLE(Self->FileIO, &extralen)) { error = ERR_Read; goto exit; }
    -         if (acSeek(Self->FileIO, namelen + extralen, SEEK::CURRENT) != ERR_Okay) {
    -            error = log.warning(ERR_Seek);
    +         if (flReadLE(Self->FileIO, &namelen) != ERR::Okay) { error = ERR::Read; goto exit; }
    +         if (flReadLE(Self->FileIO, &extralen) != ERR::Okay) { error = ERR::Read; goto exit; }
    +         if (acSeek(Self->FileIO, namelen + extralen, SEEK::CURRENT) != ERR::Okay) {
    +            error = log.warning(ERR::Seek);
                 goto exit;
              }
     
    @@ -1224,16 +1222,16 @@ static ERROR COMPRESSION_DecompressFile(extCompression *Self, struct cmpDecompre
                       // This routine is used if the file is stored rather than compressed
     
                       struct acRead read = { .Buffer = Self->Input, .Length = SIZE_COMPRESSION_BUFFER-1 };
    -                  if (!(error = Action(AC_Read, Self->FileIO, &read))) {
    +                  if ((error = Action(AC_Read, Self->FileIO, &read)) IS ERR::Okay) {
                          Self->Input[read.Result] = 0;
                          DeleteFile(destpath.c_str(), NULL);
                          error = CreateLink(destpath.c_str(), (CSTRING)Self->Input);
    -                     if (error IS ERR_NoSupport) error = ERR_Okay;
    +                     if (error IS ERR::NoSupport) error = ERR::Okay;
                       }
     
    -                  if (error) goto exit;
    +                  if (error != ERR::Okay) goto exit;
                    }
    -               else if ((zf.DeflateMethod IS 8) and (inflateInit2(&Self->Zip, -MAX_WBITS) IS ERR_Okay)) {
    +               else if ((zf.DeflateMethod IS 8) and (inflateInit2(&Self->Zip, -MAX_WBITS) IS Z_OK)) {
                       // Decompressing a link
     
                       inflate_end = true;
    @@ -1243,9 +1241,9 @@ static ERROR COMPRESSION_DecompressFile(extCompression *Self, struct cmpDecompre
                       if (zf.CompressedSize < SIZE_COMPRESSION_BUFFER) read.Length = zf.CompressedSize;
                       else read.Length = SIZE_COMPRESSION_BUFFER;
     
    -                  ERROR err = ERR_Okay;
    -                  if ((error = Action(AC_Read, Self->FileIO, &read)) != ERR_Okay) goto exit;
    -                  if (read.Result <= 0) { error = ERR_Read; goto exit; }
    +                  auto err = Z_OK;
    +                  if ((error = Action(AC_Read, Self->FileIO, &read)) != ERR::Okay) goto exit;
    +                  if (read.Result <= 0) { error = ERR::Read; goto exit; }
     
                       Self->Zip.next_in   = Self->Input;
                       Self->Zip.avail_in  = read.Result;
    @@ -1254,16 +1252,16 @@ static ERROR COMPRESSION_DecompressFile(extCompression *Self, struct cmpDecompre
     
                       err = inflate(&Self->Zip, Z_SYNC_FLUSH);
     
    -                  if ((err != ERR_Okay) and (err != Z_STREAM_END)) {
    +                  if ((err != Z_OK) and (err != Z_STREAM_END)) {
                          if (Self->Zip.msg) log.warning("%s", Self->Zip.msg);
    -                     error = ERR_Failed;
    +                     error = ERR::Failed;
                          goto exit;
                       }
     
                       Self->Output[zf.OriginalSize] = 0; // !!! We should terminate according to the amount of data decompressed
                       DeleteFile(destpath.c_str(), NULL);
                       error = CreateLink(destpath.c_str(), (CSTRING)Self->Output);
    -                  if (error IS ERR_NoSupport) error = ERR_Okay;
    +                  if (error IS ERR::NoSupport) error = ERR::Okay;
     
                       inflateEnd(&Self->Zip);
                       inflate_end = false;
    @@ -1294,13 +1292,13 @@ static ERROR COMPRESSION_DecompressFile(extCompression *Self, struct cmpDecompre
                 }
                 else permissions = Self->Permissions;
     
    -            objFile::create file = {
    +            auto file = objFile::create {
                    fl::Path(destpath), fl::Flags(FL::NEW|FL::WRITE), fl::Permissions(permissions)
                 };
     
                 if (!file.ok()) {
    -               log.warning("Error %d creating file \"%s\".", file.error, destpath.c_str());
    -               error = ERR_File;
    +               log.warning("Error %d creating file \"%s\".", LONG(file.error), destpath.c_str());
    +               error = ERR::File;
                    goto exit;
                 }
     
    @@ -1322,9 +1320,9 @@ static ERROR COMPRESSION_DecompressFile(extCompression *Self, struct cmpDecompre
                          .Length = (inputlen < SIZE_COMPRESSION_BUFFER) ? inputlen : SIZE_COMPRESSION_BUFFER
                       };
     
    -                  while ((!(error = Action(AC_Read, Self->FileIO, &read))) and (read.Result > 0)) {
    +                  while (((error = Action(AC_Read, Self->FileIO, &read)) IS ERR::Okay) and (read.Result > 0)) {
                          struct acWrite write = { .Buffer = Self->Input, .Length = read.Result };
    -                     if (Action(AC_Write, *file, &write) != ERR_Okay) { error = log.warning(ERR_Write); goto exit; }
    +                     if (Action(AC_Write, *file, &write) != ERR::Okay) { error = log.warning(ERR::Write); goto exit; }
     
                          inputlen -= read.Result;
                          if (inputlen <= 0) break;
    @@ -1332,9 +1330,9 @@ static ERROR COMPRESSION_DecompressFile(extCompression *Self, struct cmpDecompre
                          else read.Length = SIZE_COMPRESSION_BUFFER;
                       }
     
    -                  if (error) goto exit;
    +                  if (error != ERR::Okay) goto exit;
                    }
    -               else if ((zf.DeflateMethod IS 8) and (inflateInit2(&Self->Zip, -MAX_WBITS) IS ERR_Okay)) {
    +               else if ((zf.DeflateMethod IS 8) and (inflateInit2(&Self->Zip, -MAX_WBITS) IS Z_OK)) {
                       // Decompressing a file
     
                       log.trace("Inflating file from %d -> %d bytes @ offset %d.", zf.CompressedSize, zf.OriginalSize, zf.Offset);
    @@ -1346,8 +1344,8 @@ static ERROR COMPRESSION_DecompressFile(extCompression *Self, struct cmpDecompre
                          .Length = (zf.CompressedSize < SIZE_COMPRESSION_BUFFER) ? (LONG)zf.CompressedSize : SIZE_COMPRESSION_BUFFER
                       };
     
    -                  if ((error = Action(AC_Read, Self->FileIO, &read)) != ERR_Okay) goto exit;
    -                  if (read.Result <= 0) { error = ERR_Read; goto exit; }
    +                  if ((error = Action(AC_Read, Self->FileIO, &read)) != ERR::Okay) goto exit;
    +                  if (read.Result <= 0) { error = ERR::Read; goto exit; }
                       LONG inputlen = zf.CompressedSize - read.Result;
     
                       Self->Zip.next_in   = Self->Input;
    @@ -1357,13 +1355,13 @@ static ERROR COMPRESSION_DecompressFile(extCompression *Self, struct cmpDecompre
     
                       // Keep loooping until Z_STREAM_END or an error is returned
     
    -                  ERROR err = ERR_Okay;
    -                  while (err IS ERR_Okay) {
    +                  auto err = Z_OK;
    +                  while (err IS Z_OK) {
                          err = inflate(&Self->Zip, Z_SYNC_FLUSH);
     
    -                     if ((err != ERR_Okay) and (err != Z_STREAM_END)) {
    +                     if ((err != Z_OK) and (err != Z_STREAM_END)) {
                             if (Self->Zip.msg) log.warning("%s", Self->Zip.msg);
    -                        error = ERR_Failed;
    +                        error = ERR::Failed;
                             goto exit;
                          }
     
    @@ -1373,7 +1371,7 @@ static ERROR COMPRESSION_DecompressFile(extCompression *Self, struct cmpDecompre
                             .Buffer = Self->Output,
                             .Length = (LONG)(SIZE_COMPRESSION_BUFFER - Self->Zip.avail_out)
                          };
    -                     if (Action(AC_Write, *file, &write) != ERR_Okay) { error = log.warning(ERR_Write); goto exit; }
    +                     if (Action(AC_Write, *file, &write) != ERR::Okay) { error = log.warning(ERR::Write); goto exit; }
     
                          // Exit if all data has been written out
     
    @@ -1393,8 +1391,8 @@ static ERROR COMPRESSION_DecompressFile(extCompression *Self, struct cmpDecompre
                             if (inputlen < SIZE_COMPRESSION_BUFFER) read.Length = inputlen;
                             else read.Length = SIZE_COMPRESSION_BUFFER;
     
    -                        if ((error = Action(AC_Read, Self->FileIO, &read)) != ERR_Okay) goto exit;
    -                        if (read.Result <= 0) { error = ERR_Read; break; }
    +                        if ((error = Action(AC_Read, Self->FileIO, &read)) != ERR::Okay) goto exit;
    +                        if (read.Result <= 0) { error = ERR::Read; break; }
                             inputlen -= read.Result;
     
                             Self->Zip.next_in  = Self->Input;
    @@ -1428,9 +1426,9 @@ static ERROR COMPRESSION_DecompressFile(extCompression *Self, struct cmpDecompre
     exit:
        if (inflate_end) inflateEnd(&Self->Zip);
     
    -   if ((error IS ERR_Okay) and (Self->FileIndex <= 0)) {
    +   if ((error IS ERR::Okay) and (Self->FileIndex <= 0)) {
           log.msg("No files matched the path \"%s\".", Args->Path);
    -      error = ERR_Search;
    +      error = ERR::Search;
        }
     
        return error;
    @@ -1463,14 +1461,14 @@ Failed
     
     *********************************************************************************************************************/
     
    -static ERROR COMPRESSION_DecompressObject(extCompression *Self, struct cmpDecompressObject *Args)
    +static ERR COMPRESSION_DecompressObject(extCompression *Self, struct cmpDecompressObject *Args)
     {
        pf::Log log;
     
    -   if ((!Args) or (!Args->Path) or (!Args->Path[0])) return log.warning(ERR_NullArgs);
    -   if (!Args->Object) return log.warning(ERR_NullArgs);
    -   if (!Self->FileIO) return log.warning(ERR_MissingPath);
    -   if (Self->isSubClass()) return ERR_NoSupport; // Object belongs to a Compression sub-class
    +   if ((!Args) or (!Args->Path) or (!Args->Path[0])) return log.warning(ERR::NullArgs);
    +   if (!Args->Object) return log.warning(ERR::NullArgs);
    +   if (!Self->FileIO) return log.warning(ERR::MissingPath);
    +   if (Self->isSubClass()) return ERR::NoSupport; // Object belongs to a Compression sub-class
     
        log.branch("%s TO %p, Permissions: $%.8x", Args->Path, Args->Object, LONG(Self->Permissions));
     
    @@ -1480,11 +1478,11 @@ static ERROR COMPRESSION_DecompressObject(extCompression *Self, struct cmpDecomp
        CompressionFeedback fb;
        ClearMemory(&fb, sizeof(fb));
     
    -   ERROR error = ERR_Okay;
    +   ERR error = ERR::Okay;
        LONG total_scanned = 0;
        for (auto &list : Self->Files) {
           total_scanned++;
    -      if (StrCompare(Args->Path, list.Name, 0, STR::WILDCARD)) continue;
    +      if (StrCompare(Args->Path, list.Name, 0, STR::WILDCARD) != ERR::Okay) continue;
     
           log.trace("Decompressing \"%s\"", list.Name);
     
    @@ -1508,20 +1506,20 @@ static ERROR COMPRESSION_DecompressObject(extCompression *Self, struct cmpDecomp
     
           // Seek to the start of the compressed data
     
    -      if (acSeek(Self->FileIO, list.Offset + HEAD_NAMELEN, SEEK::START) != ERR_Okay) {
    -         return log.warning(ERR_Seek);
    +      if (acSeek(Self->FileIO, list.Offset + HEAD_NAMELEN, SEEK::START) != ERR::Okay) {
    +         return log.warning(ERR::Seek);
           }
     
           UWORD namelen, extralen;
    -      if (flReadLE(Self->FileIO, &namelen)) return ERR_Read;
    -      if (flReadLE(Self->FileIO, &extralen)) return ERR_Read;
    -      if (acSeek(Self->FileIO, namelen + extralen, SEEK::CURRENT) != ERR_Okay) {
    -         return log.warning(ERR_Seek);
    +      if (flReadLE(Self->FileIO, &namelen) != ERR::Okay) return ERR::Read;
    +      if (flReadLE(Self->FileIO, &extralen) != ERR::Okay) return ERR::Read;
    +      if (acSeek(Self->FileIO, namelen + extralen, SEEK::CURRENT) != ERR::Okay) {
    +         return log.warning(ERR::Seek);
           }
     
           if (list.Flags & ZIP_LINK) { // For symbolic links, decompress the data to get the destination link string
              log.warning("Unable to unzip symbolic link %s (flags $%.8x), size %d.", list.Name.c_str(), list.Flags, list.OriginalSize);
    -         return ERR_Failed;
    +         return ERR::Failed;
           }
           else { // Create the destination file or folder
              Self->Zip.next_in   = 0;
    @@ -1539,9 +1537,9 @@ static ERROR COMPRESSION_DecompressObject(extCompression *Self, struct cmpDecomp
                    if (inputlen < SIZE_COMPRESSION_BUFFER) read.Length = inputlen;
                    else read.Length = SIZE_COMPRESSION_BUFFER;
     
    -               while ((!(error = Action(AC_Read, Self->FileIO, &read))) and (read.Result > 0)) {
    +               while (((error = Action(AC_Read, Self->FileIO, &read)) IS ERR::Okay) and (read.Result > 0)) {
                       struct acWrite write = { .Buffer = Self->Input, .Length = read.Result };
    -                  if (Action(AC_Write, Args->Object, &write) != ERR_Okay) { error = ERR_Write; goto exit; }
    +                  if (Action(AC_Write, Args->Object, &write) != ERR::Okay) { error = ERR::Write; goto exit; }
     
                       inputlen -= read.Result;
                       if (inputlen <= 0) break;
    @@ -1549,9 +1547,9 @@ static ERROR COMPRESSION_DecompressObject(extCompression *Self, struct cmpDecomp
                       else read.Length = SIZE_COMPRESSION_BUFFER;
                    }
     
    -               if (error) goto exit;
    +               if (error != ERR::Okay) goto exit;
                 }
    -            else if ((list.DeflateMethod IS 8) and (inflateInit2(&Self->Zip, -MAX_WBITS) IS ERR_Okay)) {
    +            else if ((list.DeflateMethod IS 8) and (inflateInit2(&Self->Zip, -MAX_WBITS) IS Z_OK)) {
                    // Decompressing a file
     
                    inflate_end = true;
    @@ -1561,9 +1559,9 @@ static ERROR COMPRESSION_DecompressObject(extCompression *Self, struct cmpDecomp
                    if (list.CompressedSize < SIZE_COMPRESSION_BUFFER) read.Length = list.CompressedSize;
                    else read.Length = SIZE_COMPRESSION_BUFFER;
     
    -               ERROR err = ERR_Okay;
    -               if ((error = Action(AC_Read, Self->FileIO, &read)) != ERR_Okay) goto exit;
    -               if (read.Result <= 0) { error = ERR_Read; goto exit; }
    +               auto err = Z_OK;
    +               if ((error = Action(AC_Read, Self->FileIO, &read)) != ERR::Okay) goto exit;
    +               if (read.Result <= 0) { error = ERR::Read; goto exit; }
                    LONG inputlen = list.CompressedSize - read.Result;
     
                    Self->Zip.next_in   = Self->Input;
    @@ -1573,19 +1571,19 @@ static ERROR COMPRESSION_DecompressObject(extCompression *Self, struct cmpDecomp
     
                    // Keep loooping until Z_STREAM_END or an error is returned
     
    -               while (err IS ERR_Okay) {
    +               while (err IS Z_OK) {
                       err = inflate(&Self->Zip, Z_SYNC_FLUSH);
     
    -                  if ((err != ERR_Okay) and (err != Z_STREAM_END)) {
    +                  if ((err != Z_OK) and (err != Z_STREAM_END)) {
                          if (Self->Zip.msg) log.warning("%s", Self->Zip.msg);
    -                     error = ERR_Decompression;
    +                     error = ERR::Decompression;
                          goto exit;
                       }
     
                       // Write out the decompressed data
     
                       struct acWrite write = { Self->Output, (LONG)(SIZE_COMPRESSION_BUFFER - Self->Zip.avail_out) };
    -                  if (Action(AC_Write, Args->Object, &write) != ERR_Okay) { error = ERR_Write; goto exit; }
    +                  if (Action(AC_Write, Args->Object, &write) != ERR::Okay) { error = ERR::Write; goto exit; }
     
                       // Exit if all data has been written out
     
    @@ -1605,8 +1603,8 @@ static ERROR COMPRESSION_DecompressObject(extCompression *Self, struct cmpDecomp
                          if (inputlen < SIZE_COMPRESSION_BUFFER) read.Length = inputlen;
                          else read.Length = SIZE_COMPRESSION_BUFFER;
     
    -                     if ((error = Action(AC_Read, Self->FileIO, &read)) != ERR_Okay) goto exit;
    -                     if (read.Result <= 0) { error = ERR_Read; break; }
    +                     if ((error = Action(AC_Read, Self->FileIO, &read)) != ERR::Okay) goto exit;
    +                     if (read.Result <= 0) { error = ERR::Read; break; }
                          inputlen -= read.Result;
     
                          Self->Zip.next_in  = Self->Input;
    @@ -1631,14 +1629,14 @@ static ERROR COMPRESSION_DecompressObject(extCompression *Self, struct cmpDecomp
           break;
        }
     
    -   if (error) {
    +   if (error != ERR::Okay) {
           log.msg("No files matched the path \"%s\" from %d files.", Args->Path, total_scanned);
    -      return ERR_Search;
    +      return ERR::Search;
        }
     
     exit:
        if (inflate_end) inflateEnd(&Self->Zip);
    -   if (error) log.warning(error);
    +   if (error != ERR::Okay) log.warning(error);
        return error;
     }
     
    @@ -1671,23 +1669,23 @@ Search
     
     static THREADVAR CompressedItem glFindMeta;
     
    -static ERROR COMPRESSION_Find(extCompression *Self, struct cmpFind *Args)
    +static ERR COMPRESSION_Find(extCompression *Self, struct cmpFind *Args)
     {
        pf::Log log;
     
    -   if ((!Args) or (!Args->Path)) return log.warning(ERR_NullArgs);
    -   if (Self->isSubClass()) return ERR_NoSupport;
    +   if ((!Args) or (!Args->Path)) return log.warning(ERR::NullArgs);
    +   if (Self->isSubClass()) return ERR::NoSupport;
     
        log.traceBranch("Path: %s, Flags: $%.8x", Args->Path, LONG(Args->Flags));
        for (auto &item : Self->Files) {
    -      if (StrCompare(Args->Path, item.Name, 0, Args->Flags)) continue;
    +      if (StrCompare(Args->Path, item.Name, 0, Args->Flags) != ERR::Okay) continue;
     
           zipfile_to_item(item, glFindMeta);
           Args->Item = &glFindMeta;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
     
    -   return ERR_Search;
    +   return ERR::Search;
     }
     
     /*********************************************************************************************************************
    @@ -1696,9 +1694,9 @@ Flush: Flushes all pending actions.
     -END-
     *********************************************************************************************************************/
     
    -static ERROR COMPRESSION_Flush(extCompression *Self, APTR Void)
    +static ERR COMPRESSION_Flush(extCompression *Self, APTR Void)
     {
    -   if (Self->isSubClass()) return ERR_Okay;
    +   if (Self->isSubClass()) return ERR::Okay;
     
        Self->Zip.avail_in = 0;
     
    @@ -1710,7 +1708,7 @@ static ERROR COMPRESSION_Flush(extCompression *Self, APTR Void)
           LONG length, zerror;
           if ((length = SIZE_COMPRESSION_BUFFER - Self->Zip.avail_out) > 0) {
              struct acWrite write = { Self->Output, length };
    -         if (Action(AC_Write, Self->FileIO, &write) != ERR_Okay) return ERR_Write;
    +         if (Action(AC_Write, Self->FileIO, &write) != ERR::Okay) return ERR::Write;
              Self->Zip.next_out  = Self->Output;
              Self->Zip.avail_out = SIZE_COMPRESSION_BUFFER;
           }
    @@ -1721,21 +1719,21 @@ static ERROR COMPRESSION_Flush(extCompression *Self, APTR Void)
     
           // Ignore the second of two consecutive flushes:
     
    -      if ((!length) and (zerror IS Z_BUF_ERROR)) zerror = ERR_Okay;
    +      if ((!length) and (zerror IS Z_BUF_ERROR)) zerror = Z_OK;
     
           done = ((Self->Zip.avail_out != 0) or (zerror IS Z_STREAM_END));
     
    -      if ((zerror != ERR_Okay) and (zerror != Z_STREAM_END)) break;
    +      if ((zerror != Z_OK) and (zerror != Z_STREAM_END)) break;
        }
     
        acFlush(Self->FileIO);
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     
    -static ERROR COMPRESSION_Free(extCompression *Self, APTR Void)
    +static ERR COMPRESSION_Free(extCompression *Self, APTR Void)
     {
        // Before terminating anything, write the EOF signature (if modifications have been made).
     
    @@ -1746,9 +1744,9 @@ static ERROR COMPRESSION_Free(extCompression *Self, APTR Void)
           Self->ArchiveHash = 0;
        }
     
    -   if (Self->Feedback.Type IS CALL_SCRIPT) {
    +   if (Self->Feedback.isScript()) {
           UnsubscribeAction(Self->Feedback.Script.Script, AC_Free);
    -      Self->Feedback.Type = CALL_NONE;
    +      Self->Feedback.clear();
        }
     
        if (Self->Inflating)    { inflateEnd(&Self->InflateStream); Self->Inflating = false; }
    @@ -1761,28 +1759,26 @@ static ERROR COMPRESSION_Free(extCompression *Self, APTR Void)
     
        Self->~extCompression();
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
     
    -static ERROR COMPRESSION_Init(extCompression *Self, APTR Void)
    +static ERR COMPRESSION_Init(extCompression *Self, APTR Void)
     {
        pf::Log log;
    -   STRING path;
    -
    -   Self->get(FID_Path, &path);
    +   auto path = Self->get(FID_Path);
     
        if (!path) {
           // If no location has been set, assume that the developer only wants to use the buffer or stream compression routines.
     
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
        else if ((Self->Flags & CMF::NEW) != CMF::NIL) {
           // If the NEW flag is set then create a new archive, destroying any file already at that location
     
           if ((Self->FileIO = objFile::create::integral(fl::Path(path), fl::Flags(FL::READ|FL::WRITE|FL::NEW)))) {
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
           else {
              if (Self->OutputID) {
    @@ -1791,13 +1787,13 @@ static ERROR COMPRESSION_Init(extCompression *Self, APTR Void)
                 print(Self, out.str());
              }
     
    -         return log.warning(ERR_CreateObject);
    +         return log.warning(ERR::CreateObject);
           }
        }
        else {
    -      ERROR error = ERR_Okay;
    +      ERR error = ERR::Okay;
           LOC type;
    -      bool exists = ((!AnalysePath(path, &type)) and (type IS LOC::FILE));
    +      bool exists = ((AnalysePath(path, &type) IS ERR::Okay) and (type IS LOC::FILE));
     
           if (exists) {
              pf::Create file({
    @@ -1808,43 +1804,43 @@ static ERROR COMPRESSION_Init(extCompression *Self, APTR Void)
              // Try switching to read-only access if we were denied permission.
     
              if (file.ok()) Self->FileIO = *file;
    -         else if ((file.error IS ERR_NoPermission) and ((Self->Flags & CMF::READ_ONLY) IS CMF::NIL)) {
    +         else if ((file.error IS ERR::NoPermission) and ((Self->Flags & CMF::READ_ONLY) IS CMF::NIL)) {
                 log.trace("Trying read-only access...");
     
                 if ((Self->FileIO = objFile::create::integral(fl::Path(path), fl::Flags(FL::READ|FL::APPROXIMATE)))) {
                    Self->Flags |= CMF::READ_ONLY;
                 }
    -            else error = ERR_File;
    +            else error = ERR::File;
              }
    -         else error = ERR_File;
    +         else error = ERR::File;
           }
    -      else error = ERR_DoesNotExist;
    +      else error = ERR::DoesNotExist;
     
    -      if (!error) { // Test the given location to see if it matches our supported file format (pkzip).
    +      if (error IS ERR::Okay) { // Test the given location to see if it matches our supported file format (pkzip).
              LONG result;
    -         if (acRead(Self->FileIO, Self->Header, sizeof(Self->Header), &result) != ERR_Okay) return log.warning(ERR_Read);
    +         if (acRead(Self->FileIO, Self->Header, sizeof(Self->Header), &result) != ERR::Okay) return log.warning(ERR::Read);
     
              // If the file is empty then we will accept it as a zip file
     
    -         if (!result) return ERR_Okay;
    +         if (!result) return ERR::Okay;
     
              // Check for a pkzip header
     
              if ((Self->Header[0] IS 0x50) and (Self->Header[1] IS 0x4b) and
                  (Self->Header[2] IS 0x03) and (Self->Header[3] IS 0x04)) {
                 error = fast_scan_zip(Self);
    -            if (error != ERR_Okay) return log.warning(error);
    +            if (error != ERR::Okay) return log.warning(error);
                 else return error;
              }
    -         else return ERR_NoSupport;
    +         else return ERR::NoSupport;
           }
           else if ((!exists) and ((Self->Flags & CMF::CREATE_FILE) != CMF::NIL)) {
              // Create a new file if the requested location does not exist
     
    -         log.extmsg("Creating a new file because the location does not exist.");
    +         log.detail("Creating a new file because the location does not exist.");
     
              if ((Self->FileIO = objFile::create::integral(fl::Path(path), fl::Flags(FL::READ|FL::WRITE|FL::NEW)))) {
    -            return ERR_Okay;
    +            return ERR::Okay;
              }
              else {
                 if (Self->OutputID) {
    @@ -1853,37 +1849,37 @@ static ERROR COMPRESSION_Init(extCompression *Self, APTR Void)
                    print(Self, out.str());
                 }
     
    -            return log.warning(ERR_CreateObject);
    +            return log.warning(ERR::CreateObject);
              }
           }
           else {
              std::ostringstream out;
              out << "Failed to open \"" << path << "\".";
              print(Self, out.str());
    -         return log.warning(ERR_File);
    +         return log.warning(ERR::File);
           }
        }
     }
     
     //********************************************************************************************************************
     
    -static ERROR COMPRESSION_NewObject(extCompression *Self, APTR Void)
    +static ERR COMPRESSION_NewObject(extCompression *Self, APTR Void)
     {
        pf::Log log;
     
        new (Self) extCompression;
     
    -   if (!AllocMemory(SIZE_COMPRESSION_BUFFER, MEM::DATA, (APTR *)&Self->Output, NULL)) {
    -      if (!AllocMemory(SIZE_COMPRESSION_BUFFER, MEM::DATA, (APTR *)&Self->Input, NULL)) {
    +   if (AllocMemory(SIZE_COMPRESSION_BUFFER, MEM::DATA, (APTR *)&Self->Output, NULL) IS ERR::Okay) {
    +      if (AllocMemory(SIZE_COMPRESSION_BUFFER, MEM::DATA, (APTR *)&Self->Input, NULL) IS ERR::Okay) {
              Self->CompressionLevel = 60; // 60% compression by default
              Self->Permissions      = PERMIT::NIL; // Inherit permissions by default. PERMIT::READ|PERMIT::WRITE|PERMIT::GROUP_READ|PERMIT::GROUP_WRITE;
              Self->MinOutputSize    = (32 * 1024) + 2048; // Has to at least match the minimum 'window size' of each compression block, plus extra in case of overflow.  Min window size is typically 16k
              Self->WindowBits = MAX_WBITS; // If negative then you get raw compression when dealing with buffers and stream data, i.e. no header information
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
    -      else return log.warning(ERR_AllocMemory);
    +      else return log.warning(ERR::AllocMemory);
        }
    -   else return log.warning(ERR_AllocMemory);
    +   else return log.warning(ERR::AllocMemory);
     }
     
     /*********************************************************************************************************************
    @@ -1911,20 +1907,20 @@ NoSupport
     
     *********************************************************************************************************************/
     
    -static ERROR COMPRESSION_RemoveFile(extCompression *Self, struct cmpRemoveFile *Args)
    +static ERR COMPRESSION_RemoveFile(extCompression *Self, struct cmpRemoveFile *Args)
     {
        pf::Log log;
     
    -   if ((!Args) or (!Args->Path)) return log.warning(ERR_NullArgs);
    +   if ((!Args) or (!Args->Path)) return log.warning(ERR::NullArgs);
     
    -   if (Self->isSubClass()) return ERR_NoSupport;
    +   if (Self->isSubClass()) return ERR::NoSupport;
     
        // Search for the file(s) in our archive that match the given name and delete them.
     
        log.msg("%s", Args->Path);
     
        for (auto it = Self->Files.begin(); it != Self->Files.end(); ) {
    -      if (!StrCompare(Args->Path, it->Name, 0, STR::WILDCARD)) {
    +      if (StrCompare(Args->Path, it->Name, 0, STR::WILDCARD) IS ERR::Okay) {
              // Delete the file from the archive
     
              if (Self->OutputID) {
    @@ -1933,12 +1929,12 @@ static ERROR COMPRESSION_RemoveFile(extCompression *Self, struct cmpRemoveFile *
                 print(Self, out.str());
              }
     
    -         if (auto error = remove_file(Self, it)) return error;
    +         if (auto error = remove_file(Self, it); error != ERR::Okay) return error;
           }
           else it++;
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -1949,8 +1945,8 @@ Scan: Scan the archive's index of compressed data.
     Use the Scan method to search an archive's list of items.  Optional filtering can be applied using the Folder parameter
     to limit results to those within a folder, and Filter parameter to apply wildcard matching to item names.  Each item
     that is discovered during the scan will be passed to the function referenced in the Callback parameter.  If the
    -Callback function returns ERR_Terminate, the scan will stop immediately.  The synopsis of the callback function is
    -`ERROR Function(*Compression, *CompressedItem)`.
    +Callback function returns ERR::Terminate, the scan will stop immediately.  The synopsis of the callback function is
    +`ERR Function(*Compression, *CompressedItem)`.
     
     The &CompressedItem structure consists of the following fields:
     
    @@ -1971,13 +1967,13 @@ NullArgs
     
     *********************************************************************************************************************/
     
    -static ERROR COMPRESSION_Scan(extCompression *Self, struct cmpScan *Args)
    +static ERR COMPRESSION_Scan(extCompression *Self, struct cmpScan *Args)
     {
        pf::Log log;
     
    -   if ((!Args) or (!Args->Callback)) return log.warning(ERR_NullArgs);
    +   if ((!Args) or (!Args->Callback)) return log.warning(ERR::NullArgs);
     
    -   if (Self->isSubClass()) return ERR_NoSupport;
    +   if (Self->isSubClass()) return ERR::NoSupport;
     
        log.traceBranch("Folder: \"%s\", Filter: \"%s\"", Args->Folder, Args->Filter);
     
    @@ -1987,14 +1983,14 @@ static ERROR COMPRESSION_Scan(extCompression *Self, struct cmpScan *Args)
           if ((folder_len > 0) and (Args->Folder[folder_len-1] IS '/')) folder_len--;
        }
     
    -   ERROR error = ERR_Okay;
    +   ERR error = ERR::Okay;
     
        for (auto &item : Self->Files) {
           log.trace("Item: %s", item.Name);
     
           if (Args->Folder) {
              if ((LONG)item.Name.size() > folder_len) {
    -            if (!StrCompare(Args->Folder, item.Name)) {
    +            if (StrCompare(Args->Folder, item.Name) IS ERR::Okay) {
                    if ((folder_len > 0) and (item.Name[folder_len] != '/')) continue;
                    if ((item.Name[folder_len] IS '/') and (!item.Name[folder_len+1])) continue;
     
    @@ -2012,7 +2008,7 @@ static ERROR COMPRESSION_Scan(extCompression *Self, struct cmpScan *Args)
           }
     
           if ((Args->Filter) and (Args->Filter[0])) {
    -         if (!StrCompare(Args->Filter, item.Name, 0, STR::WILDCARD)) break;
    +         if (StrCompare(Args->Filter, item.Name, 0, STR::WILDCARD) IS ERR::Okay) break;
              else continue;
           }
     
    @@ -2020,22 +2016,21 @@ static ERROR COMPRESSION_Scan(extCompression *Self, struct cmpScan *Args)
           zipfile_to_item(item, meta);
     
           {
    -         if (Args->Callback->Type IS CALL_STDC) {
    +         if (Args->Callback->isC()) {
                 pf::SwitchContext context(Args->Callback->StdC.Context);
    -            auto routine = (ERROR (*)(extCompression *, CompressedItem *))Args->Callback->StdC.Routine;
    -            error = routine(Self, &meta);
    +            auto routine = (ERR (*)(extCompression *, CompressedItem *, APTR))Args->Callback->StdC.Routine;
    +            error = routine(Self, &meta, Args->Callback->StdC.Meta);
              }
    -         else if (Args->Callback->Type IS CALL_SCRIPT) {
    -            auto script = Args->Callback->Script.Script;
    +         else if (Args->Callback->isScript()) {
                 const ScriptArg args[] = {
                    { "Compression", Self, FD_OBJECTPTR },
                    { "CompressedItem:Item", &meta, FD_STRUCT|FD_PTR }
                 };
    -            if (scCallback(script, Args->Callback->Script.ProcedureID, args, ARRAYSIZE(args), &error)) error = ERR_Failed;
    +            if (scCallback(Args->Callback->Script.Script, Args->Callback->Script.ProcedureID, args, std::ssize(args), &error) != ERR::Okay) error = ERR::Failed;
              }
    -         else error = log.warning(ERR_WrongType);
    +         else error = log.warning(ERR::WrongType);
     
    -         if (error) break; // Break the scanning loop.
    +         if (error != ERR::Okay) break; // Break the scanning loop.
           }
        }
     
    @@ -2097,7 +2092,7 @@ static const FieldArray clFields[] = {
     
     //********************************************************************************************************************
     
    -extern "C" ERROR add_compression_class(void)
    +extern "C" ERR add_compression_class(void)
     {
        glCompressionClass = extMetaClass::create::global(
           fl::ClassVersion(VER_COMPRESSION),
    @@ -2112,7 +2107,7 @@ extern "C" ERROR add_compression_class(void)
           fl::Size(sizeof(extCompression)),
           fl::Path("modules:core"));
     
    -   return glCompressionClass ? ERR_Okay : ERR_AddClass;
    +   return glCompressionClass ? ERR::Okay : ERR::AddClass;
     }
     
     //********************************************************************************************************************
    diff --git a/src/core/compression/compression_fields.cpp b/src/core/compression/compression_fields.cpp
    index fc2ae661c..ba7d492b9 100644
    --- a/src/core/compression/compression_fields.cpp
    +++ b/src/core/compression/compression_fields.cpp
    @@ -10,7 +10,7 @@ module.  Please refer to the @FileArchive class for further information on this
     
     ****************************************************************************/
     
    -static ERROR SET_ArchiveName(extCompression *Self, CSTRING Value)
    +static ERR SET_ArchiveName(extCompression *Self, CSTRING Value)
     {
        if ((Value) and (*Value)) Self->ArchiveHash = StrHash(Value, 0);
        else Self->ArchiveHash = 0;
    @@ -18,7 +18,7 @@ static ERROR SET_ArchiveName(extCompression *Self, CSTRING Value)
        if (Self->ArchiveHash) add_archive(Self);
        else remove_archive(Self);
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /****************************************************************************
    @@ -32,12 +32,12 @@ but the compression ratio will improve.
     
     ****************************************************************************/
     
    -static ERROR SET_CompressionLevel(extCompression *Self, LONG Value)
    +static ERR SET_CompressionLevel(extCompression *Self, LONG Value)
     {
        if (Value < 0) Value = 0;
        else if (Value > 100) Value = 100;
        Self->CompressionLevel = Value;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /****************************************************************************
    @@ -46,13 +46,13 @@ static ERROR SET_CompressionLevel(extCompression *Self, LONG Value)
     Feedback: Provides feedback during the de/compression process.
     
     To receive feedback during any de/compression process, set a callback routine in this field. The format for the
    -callback routine is `ERROR Function(*Compression, *CompressionFeedback)`.
    +callback routine is `ERR Function(*Compression, *CompressionFeedback)`.
     
     For object classes, the object that initiated the de/compression process can be learned by calling the Core's
     ~Core.CurrentContext() function.
     
    -During the processing of multiple files, any individual file can be skipped by returning `ERR_Skip` and the entire
    -process can be cancelled by returning ERR_Terminate.  All other error codes are ignored.
    +During the processing of multiple files, any individual file can be skipped by returning `ERR::Skip` and the entire
    +process can be cancelled by returning ERR::Terminate.  All other error codes are ignored.
     
     The &CompressionFeedback structure consists of the following fields:
     
    @@ -60,27 +60,26 @@ The &CompressionFeedback structure consists of the following fields:
     
     ****************************************************************************/
     
    -static ERROR GET_Feedback(extCompression *Self, FUNCTION **Value)
    +static ERR GET_Feedback(extCompression *Self, FUNCTION **Value)
     {
    -   if (Self->Feedback.Type != CALL_NONE) {
    +   if (Self->Feedback.defined()) {
           *Value = &Self->Feedback;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return ERR_FieldNotSet;
    +   else return ERR::FieldNotSet;
     }
     
    -static ERROR SET_Feedback(extCompression *Self, FUNCTION *Value)
    +static ERR SET_Feedback(extCompression *Self, FUNCTION *Value)
     {
        if (Value) {
    -      if (Self->Feedback.Type IS CALL_SCRIPT) UnsubscribeAction(Self->Feedback.Script.Script, AC_Free);
    +      if (Self->Feedback.isScript()) UnsubscribeAction(Self->Feedback.Script.Script, AC_Free);
           Self->Feedback = *Value;
    -      if (Self->Feedback.Type IS CALL_SCRIPT) {
    -         auto callback = make_function_stdc(notify_free_feedback);
    -         SubscribeAction(Self->Feedback.Script.Script, AC_Free, &callback);
    +      if (Self->Feedback.isScript()) {
    +         SubscribeAction(Self->Feedback.Script.Script, AC_Free, FUNCTION(notify_free_feedback));
           }
        }
    -   else Self->Feedback.Type = CALL_NONE;
    -   return ERR_Okay;
    +   else Self->Feedback.clear();
    +   return ERR::Okay;
     }
     
     /****************************************************************************
    @@ -95,10 +94,10 @@ This field is only of use to sub-classes that need to examine the first 32 bytes
     
     ****************************************************************************/
     
    -static ERROR GET_Header(extCompression *Self, UBYTE **Header)
    +static ERR GET_Header(extCompression *Self, UBYTE **Header)
     {
        *Header = Self->Header;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /****************************************************************************
    @@ -110,22 +109,22 @@ To load or create a new file archive, set the Path field to the path of that fil
     
     ****************************************************************************/
     
    -static ERROR GET_Path(extCompression *Self, CSTRING *Value)
    +static ERR GET_Path(extCompression *Self, CSTRING *Value)
     {
    -   if (Self->Path) { *Value = Self->Path; return ERR_Okay; }
    -   else return ERR_FieldNotSet;
    +   if (Self->Path) { *Value = Self->Path; return ERR::Okay; }
    +   else return ERR::FieldNotSet;
     }
     
    -static ERROR SET_Path(extCompression *Self, CSTRING Value)
    +static ERR SET_Path(extCompression *Self, CSTRING Value)
     {
        pf::Log log;
     
        if (Self->Path) { FreeResource(Self->Path); Self->Path = NULL; }
     
        if ((Value) and (*Value)) {
    -      if (!(Self->Path = StrClone(Value))) return log.warning(ERR_AllocMemory);
    +      if (!(Self->Path = StrClone(Value))) return log.warning(ERR::AllocMemory);
        }
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /****************************************************************************
    @@ -157,13 +156,13 @@ across to it.
     
     ****************************************************************************/
     
    -static ERROR GET_Password(extCompression *Self, CSTRING *Value)
    +static ERR GET_Password(extCompression *Self, CSTRING *Value)
     {
        *Value = Self->Password;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
    -static ERROR SET_Password(extCompression *Self, CSTRING Value)
    +static ERR SET_Password(extCompression *Self, CSTRING Value)
     {
        if ((Value) and (*Value)) {
           StrCopy(Value, Self->Password, sizeof(Self->Password));
    @@ -171,7 +170,7 @@ static ERROR SET_Password(extCompression *Self, CSTRING Value)
        }
        else Self->Password[0] = 0;
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /****************************************************************************
    @@ -187,11 +186,11 @@ Size: Indicates the size of the source archive, in bytes.
     
     ****************************************************************************/
     
    -static ERROR GET_Size(extCompression *Self, LARGE *Value)
    +static ERR GET_Size(extCompression *Self, LARGE *Value)
     {
        *Value = 0;
        if (Self->FileIO) return Self->FileIO->get(FID_Size, Value);
    -   else return ERR_Okay;
    +   else return ERR::Okay;
     }
     
     /****************************************************************************
    @@ -211,14 +210,14 @@ information that may identify the compressed data is not included in the total.
     
     ****************************************************************************/
     
    -static ERROR GET_UncompressedSize(extCompression *Self, LARGE *Value)
    +static ERR GET_UncompressedSize(extCompression *Self, LARGE *Value)
     {
        LARGE size = 0;
        for (auto &f : Self->Files) {
           size += f.OriginalSize;
        }
        *Value = size;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /****************************************************************************
    @@ -237,14 +236,14 @@ To support GZIP decompression, please set the WindowBits value to 47.
     
     ****************************************************************************/
     
    -static ERROR SET_WindowBits(extCompression *Self, LONG Value)
    +static ERR SET_WindowBits(extCompression *Self, LONG Value)
     {
        pf::Log log;
     
        if (((Value >= 8) and (Value <= 15)) or ((Value >= -15) and (Value <= -8)) or
            (Value IS 15 + 32) or (Value IS 16 + 32)) {
           Self->WindowBits = Value;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return log.warning(ERR_OutOfRange);
    +   else return log.warning(ERR::OutOfRange);
     }
    diff --git a/src/core/compression/compression_func.cpp b/src/core/compression/compression_func.cpp
    index 56514e18f..30a02d6da 100644
    --- a/src/core/compression/compression_func.cpp
    +++ b/src/core/compression/compression_func.cpp
    @@ -45,14 +45,14 @@ static void print(extCompression *Self, std::string Buffer)
     
     //*********************************************************************************************************************
     
    -static ERROR compress_folder(extCompression *Self, std::string Location, std::string Path)
    +static ERR compress_folder(extCompression *Self, std::string Location, std::string Path)
     {
        pf::Log log(__FUNCTION__);
     
        log.branch("Compressing folder \"%s\" to \"%s\"", Location.c_str(), Path.c_str());
     
    -   objFile::create file = { fl::Path(Location) };
    -   if (!file.ok()) return log.warning(ERR_File);
    +   auto file = objFile::create { fl::Path(Location) };
    +   if (!file.ok()) return log.warning(ERR::File);
     
        if (((file->Flags & FL::LINK) != FL::NIL) and ((Self->Flags & CMF::NO_LINKS) IS CMF::NIL)) {
           log.msg("Folder is a link.");
    @@ -77,11 +77,11 @@ static ERROR compress_folder(extCompression *Self, std::string Location, std::st
           .CompressedSize = 0
        };
     
    -   ERROR error = send_feedback(Self, &feedback);
    +   ERR error = send_feedback(Self, &feedback);
     
        Self->FileIndex++;
    -   if ((error IS ERR_Terminate) or (error IS ERR_Cancelled)) return ERR_Cancelled;
    -   else if (error IS ERR_Skip) return ERR_Okay;
    +   if ((error IS ERR::Terminate) or (error IS ERR::Cancelled)) return ERR::Cancelled;
    +   else if (error IS ERR::Skip) return ERR::Okay;
     
        if (!Path.empty()) {
           // Seek to the position at which this new directory entry will be added
    @@ -89,24 +89,24 @@ static ERROR compress_folder(extCompression *Self, std::string Location, std::st
           ULONG dataoffset = 0;
           if (!Self->Files.empty()) {
              auto &last = Self->Files.back();
    -         if (acSeekStart(Self->FileIO, last.Offset + HEAD_NAMELEN) != ERR_Okay) {
    -            return log.warning(ERR_Seek);
    +         if (acSeekStart(Self->FileIO, last.Offset + HEAD_NAMELEN) != ERR::Okay) {
    +            return log.warning(ERR::Seek);
              }
     
              UWORD namelen, extralen;
    -         if (flReadLE(Self->FileIO, &namelen)) return ERR_Read;
    -         if (flReadLE(Self->FileIO, &extralen)) return ERR_Read;
    +         if (flReadLE(Self->FileIO, &namelen) != ERR::Okay) return ERR::Read;
    +         if (flReadLE(Self->FileIO, &extralen) != ERR::Okay) return ERR::Read;
              dataoffset = last.Offset + HEAD_LENGTH + namelen + extralen + last.CompressedSize;
           }
     
    -      if (acSeekStart(Self->FileIO, dataoffset) != ERR_Okay) return ERR_Seek;
    +      if (acSeekStart(Self->FileIO, dataoffset) != ERR::Okay) return ERR::Seek;
     
           // If a matching file name already exists in the archive, make a note of its position
     
     
           auto replace_file = Self->Files.begin();
           for (; replace_file != Self->Files.end(); replace_file++) {
    -         if (!StrMatch(replace_file->Name, Location)) break;
    +         if (StrMatch(replace_file->Name, Location) IS ERR::Okay) break;
           }
     
           // Allocate the file entry structure and set up some initial variables.
    @@ -118,14 +118,14 @@ static ERROR compress_folder(extCompression *Self, std::string Location, std::st
           // Convert the file date stamp into a DOS time stamp for zip
     
           DateTime *tm;
    -      if (!file->getPtr(FID_Date, &tm)) {
    +      if (file->getPtr(FID_Date, &tm) IS ERR::Okay) {
              if (tm->Year < 1980) entry.TimeStamp = 0x00210000;
              else entry.TimeStamp = ((tm->Year-1980)<<25) | (tm->Month<<21) | (tm->Day<<16) | (tm->Hour<<11) | (tm->Minute<<5) | (tm->Second>>1);
           }
     
           // Write the compression file entry
     
    -      if (acSeekStart(Self->FileIO, entry.Offset) != ERR_Okay) return ERR_Seek;
    +      if (acSeekStart(Self->FileIO, entry.Offset) != ERR::Okay) return ERR::Seek;
     
           UBYTE header[sizeof(glHeader)];
           CopyMemory(glHeader, header, sizeof(glHeader));
    @@ -136,8 +136,8 @@ static ERROR compress_folder(extCompression *Self, std::string Location, std::st
           wrb(entry.CompressedSize, header + HEAD_COMPRESSEDSIZE);
           wrb(entry.OriginalSize, header + HEAD_FILESIZE);
           wrb(entry.Name.size(), header + HEAD_NAMELEN);
    -      if (acWriteResult(Self->FileIO, header, HEAD_LENGTH) != HEAD_LENGTH) return ERR_Okay;
    -      if (acWriteResult(Self->FileIO, entry.Name.c_str(), entry.Name.size()) != (LONG)entry.Name.size()) return ERR_Okay;
    +      if (acWriteResult(Self->FileIO, header, HEAD_LENGTH) != HEAD_LENGTH) return ERR::Okay;
    +      if (acWriteResult(Self->FileIO, entry.Name.c_str(), entry.Name.size()) != (LONG)entry.Name.size()) return ERR::Okay;
     
           Self->Files.push_back(entry);
     
    @@ -151,8 +151,8 @@ static ERROR compress_folder(extCompression *Self, std::string Location, std::st
        // Enter the directory and compress its contents
     
        DirInfo *dir;
    -   if (!OpenDir(Location.c_str(), RDF::FILE|RDF::FOLDER|RDF::QUALIFY, &dir)) {
    -      while (!ScanDir(dir)) { // Recurse for each directory in the list
    +   if (OpenDir(Location.c_str(), RDF::FILE|RDF::FOLDER|RDF::QUALIFY, &dir) IS ERR::Okay) {
    +      while (ScanDir(dir) IS ERR::Okay) { // Recurse for each directory in the list
              FileInfo *scan = dir->Info;
              if (((scan->Flags & RDF::FOLDER) != RDF::NIL) and ((scan->Flags & RDF::LINK) IS RDF::NIL)) {
                 std::string location = Location + scan->Name;
    @@ -168,12 +168,12 @@ static ERROR compress_folder(extCompression *Self, std::string Location, std::st
           FreeResource(dir);
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //*********************************************************************************************************************
     
    -static ERROR compress_file(extCompression *Self, std::string Location, std::string Path, bool Link)
    +static ERR compress_file(extCompression *Self, std::string Location, std::string Path, bool Link)
     {
        pf::Log log(__FUNCTION__);
     
    @@ -197,7 +197,7 @@ static ERROR compress_file(extCompression *Self, std::string Location, std::stri
     
        // Open the source file for reading only
     
    -   objFile::create file = { fl::Path(Location), fl::Flags(Link ? FL::NIL : FL::READ) };
    +   auto file = objFile::create { fl::Path(Location), fl::Flags(Link ? FL::NIL : FL::READ) };
     
        if (!file.ok()) {
           if (Self->OutputID) {
    @@ -205,13 +205,13 @@ static ERROR compress_file(extCompression *Self, std::string Location, std::stri
              out << "  Error opening file \"" << Location << "\".";
              print(Self, out.str());
           }
    -      return log.warning(ERR_OpenFile);
    +      return log.warning(ERR::OpenFile);
        }
     
     
        if ((Link) and ((file->Flags & FL::LINK) IS FL::NIL)) {
           log.warning("Internal Error: Expected a link, but the file is not.");
    -      return ERR_Failed;
    +      return ERR::Failed;
        }
     
        // Determine the name that will be used for storing this file
    @@ -240,11 +240,13 @@ static ERROR compress_file(extCompression *Self, std::string Location, std::stri
        fb.Progress       = 0;
     
        switch (send_feedback(Self, &fb)) {
    -      case ERR_Terminate:
    -      case ERR_Cancelled:
    -         return ERR_Cancelled;
    -      case ERR_Skip:
    -         return ERR_Okay;
    +      case ERR::Terminate:
    +      case ERR::Cancelled:
    +         return ERR::Cancelled;
    +      case ERR::Skip:
    +         return ERR::Okay;
    +      default:
    +         break;
        }
     
        // Send informative output to the user
    @@ -260,15 +262,15 @@ static ERROR compress_file(extCompression *Self, std::string Location, std::stri
        if (!Self->Files.empty()) {
           auto &chain = Self->Files.back();
     
    -      if (acSeek(Self->FileIO, chain.Offset + HEAD_NAMELEN, SEEK::START) != ERR_Okay) return log.warning(ERR_Seek);
    +      if (acSeek(Self->FileIO, chain.Offset + HEAD_NAMELEN, SEEK::START) != ERR::Okay) return log.warning(ERR::Seek);
     
           UWORD namelen, extralen;
    -      if (flReadLE(Self->FileIO, &namelen)) return ERR_Read;
    -      if (flReadLE(Self->FileIO, &extralen)) return ERR_Read;
    +      if (flReadLE(Self->FileIO, &namelen) != ERR::Okay) return ERR::Read;
    +      if (flReadLE(Self->FileIO, &extralen) != ERR::Okay) return ERR::Read;
           dataoffset = chain.Offset + HEAD_LENGTH + namelen + extralen + chain.CompressedSize;
        }
     
    -   if (acSeek(Self->FileIO, dataoffset, SEEK::START) != ERR_Okay) return ERR_Seek;
    +   if (acSeek(Self->FileIO, dataoffset, SEEK::START) != ERR::Okay) return ERR::Seek;
     
        // Initialise the compression algorithm
     
    @@ -281,18 +283,18 @@ static ERROR compress_file(extCompression *Self, std::string Location, std::stri
        Self->Zip.total_in  = 0;
        Self->Zip.total_out = 0;
     
    -   if (deflateInit2(&Self->Zip, level, Z_DEFLATED, -MAX_WBITS, ZLIB_MEM_LEVEL, Z_DEFAULT_STRATEGY) IS ERR_Okay) {
    +   if (deflateInit2(&Self->Zip, level, Z_DEFLATED, -MAX_WBITS, ZLIB_MEM_LEVEL, Z_DEFAULT_STRATEGY) IS Z_OK) {
           deflateend = true;
           Self->Zip.next_out  = Self->Output;
           Self->Zip.avail_out = SIZE_COMPRESSION_BUFFER;
        }
    -   else return ERR_Failed;
    +   else return ERR::Failed;
     
        // If a matching file name already exists in the archive, make a note of its position
     
        auto replace_file = Self->Files.begin();
        for (; replace_file != Self->Files.end(); replace_file++) {
    -      if (!StrCompare(replace_file->Name, filename, 0, STR::MATCH_LEN)) break;
    +      if (StrCompare(replace_file->Name, filename, 0, STR::MATCH_LEN) IS ERR::Okay) break;
        }
     
        // Allocate the file entry structure and set up some initial variables.
    @@ -302,7 +304,7 @@ static ERROR compress_file(extCompression *Self, std::string Location, std::stri
        entry.Offset = dataoffset;
     
        if (((Self->Flags & CMF::NO_LINKS) IS CMF::NIL) and ((file->Flags & FL::LINK) != FL::NIL)) {
    -      if (!file->get(FID_Link, &symlink)) {
    +      if (file->get(FID_Link, &symlink) IS ERR::Okay) {
              log.msg("Note: File \"%s\" is a symbolic link to \"%s\"", filename.c_str(), symlink);
              entry.Flags |= ZIP_LINK;
           }
    @@ -311,13 +313,13 @@ static ERROR compress_file(extCompression *Self, std::string Location, std::stri
        // Convert the file date stamp into a DOS time stamp for zip
     
        DateTime *time;
    -   if (!file->getPtr(FID_Date, &time)) {
    +   if (file->getPtr(FID_Date, &time) IS ERR::Okay) {
           if (time->Year < 1980) entry.TimeStamp = 0x00210000;
           else entry.TimeStamp = ((time->Year-1980)<<25) | (time->Month<<21) | (time->Day<<16) | (time->Hour<<11) | (time->Minute<<5) | (time->Second>>1);
        }
     
        PERMIT permissions;
    -   if (!file->get(FID_Permissions, (LONG *)&permissions)) {
    +   if (file->get(FID_Permissions, (LONG *)&permissions) IS ERR::Okay) {
           if ((permissions & PERMIT::USER_READ) != PERMIT::NIL)   entry.Flags |= ZIP_UREAD;
           if ((permissions & PERMIT::GROUP_READ) != PERMIT::NIL)  entry.Flags |= ZIP_GREAD;
           if ((permissions & PERMIT::OTHERS_READ) != PERMIT::NIL) entry.Flags |= ZIP_OREAD;
    @@ -335,7 +337,7 @@ static ERROR compress_file(extCompression *Self, std::string Location, std::stri
     
        // Skip over the PKZIP header that will be written for this file (we will be updating the header later).
     
    -   if (acWriteResult(Self->FileIO, NULL, HEAD_LENGTH + entry.Name.size() + entry.Comment.size()) != LONG(HEAD_LENGTH + entry.Name.size() + entry.Comment.size())) return ERR_Write;
    +   if (acWriteResult(Self->FileIO, NULL, HEAD_LENGTH + entry.Name.size() + entry.Comment.size()) != LONG(HEAD_LENGTH + entry.Name.size() + entry.Comment.size())) return ERR::Write;
     
        // Specify the limitations of our buffer so that the compression routine doesn't overwrite its boundaries.  Then
        // start the compression of the input file.
    @@ -347,15 +349,15 @@ static ERROR compress_file(extCompression *Self, std::string Location, std::stri
           Self->Zip.avail_in  = len;
           Self->Zip.next_out  = Self->Output;
           Self->Zip.avail_out = SIZE_COMPRESSION_BUFFER;
    -      if (deflate(&Self->Zip, Z_NO_FLUSH) != ERR_Okay) {
    +      if (deflate(&Self->Zip, Z_NO_FLUSH) != Z_OK) {
              log.warning("Failure during data compression.");
    -         return ERR_Failed;
    +         return ERR::Failed;
           }
           entry.CRC = GenCRC32(entry.CRC, symlink, len);
        }
        else {
           struct acRead read = { .Buffer = Self->Input, .Length = SIZE_COMPRESSION_BUFFER };
    -      while ((!Action(AC_Read, *file, &read)) and (read.Result > 0)) {
    +      while ((Action(AC_Read, *file, &read) IS ERR::Okay) and (read.Result > 0)) {
              Self->Zip.next_in  = Self->Input;
              Self->Zip.avail_in = read.Result;
     
    @@ -374,9 +376,9 @@ static ERROR compress_file(extCompression *Self, std::string Location, std::stri
                    send_feedback(Self, &fb);
                 }
     
    -            if (deflate(&Self->Zip, Z_NO_FLUSH) != ERR_Okay) {
    +            if (deflate(&Self->Zip, Z_NO_FLUSH) != Z_OK) {
                    log.warning("Failure during data compression.");
    -               return ERR_Failed;
    +               return ERR::Failed;
                 }
              }
     
    @@ -384,7 +386,7 @@ static ERROR compress_file(extCompression *Self, std::string Location, std::stri
           }
        }
     
    -   if (acFlush(Self) != ERR_Okay) return ERR_Failed;
    +   if (acFlush(Self) != ERR::Okay) return ERR::Failed;
        deflateEnd(&Self->Zip);
        deflateend = false;
     
    @@ -404,7 +406,7 @@ static ERROR compress_file(extCompression *Self, std::string Location, std::stri
        // Update the header that we earlier wrote for our file entry.  Note that the header stores only some of the file's
        // meta information.  The majority is stored in the directory at the end of the zip file.
     
    -   if (acSeek(Self->FileIO, (DOUBLE)entry.Offset, SEEK::START) != ERR_Okay) return ERR_Seek;
    +   if (acSeek(Self->FileIO, (DOUBLE)entry.Offset, SEEK::START) != ERR::Okay) return ERR::Seek;
     
        UBYTE header[sizeof(glHeader)];
        CopyMemory(glHeader, header, sizeof(glHeader));
    @@ -414,8 +416,8 @@ static ERROR compress_file(extCompression *Self, std::string Location, std::stri
        wrb(entry.CompressedSize, header + HEAD_COMPRESSEDSIZE);
        wrb(entry.OriginalSize, header + HEAD_FILESIZE);
        wrb(entry.Name.size(), header + HEAD_NAMELEN);
    -   if (acWriteResult(Self->FileIO, header, HEAD_LENGTH) != HEAD_LENGTH) return ERR_Write;
    -   if (acWriteResult(Self->FileIO, entry.Name.c_str(), entry.Name.size()) != (LONG)entry.Name.size()) return ERR_Write;
    +   if (acWriteResult(Self->FileIO, header, HEAD_LENGTH) != HEAD_LENGTH) return ERR::Write;
    +   if (acWriteResult(Self->FileIO, entry.Name.c_str(), entry.Name.size()) != (LONG)entry.Name.size()) return ERR::Write;
     
        // Send updated feedback if necessary
     
    @@ -429,12 +431,12 @@ static ERROR compress_file(extCompression *Self, std::string Location, std::stri
     
        if (replace_file != Self->Files.end()) remove_file(Self, replace_file);
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //*********************************************************************************************************************
     
    -static ERROR remove_file(extCompression *Self, std::list::iterator &File)
    +static ERR remove_file(extCompression *Self, std::list::iterator &File)
     {
        pf::Log log(__FUNCTION__);
     
    @@ -443,26 +445,26 @@ static ERROR remove_file(extCompression *Self, std::list::iterator &Fil
        // Seek to the end of the compressed file.  We are going to delete the file by shifting all the data after the file
        // to the start of the file's position.
     
    -   if (acSeekStart(Self->FileIO, File->Offset + HEAD_NAMELEN) != ERR_Okay) return log.warning(ERR_Seek);
    +   if (acSeekStart(Self->FileIO, File->Offset + HEAD_NAMELEN) != ERR::Okay) return log.warning(ERR::Seek);
     
        UWORD namelen, extralen;
    -   if (flReadLE(Self->FileIO, &namelen)) return ERR_Read;
    -   if (flReadLE(Self->FileIO, &extralen)) return ERR_Read;
    +   if (flReadLE(Self->FileIO, &namelen) != ERR::Okay) return ERR::Read;
    +   if (flReadLE(Self->FileIO, &extralen) != ERR::Okay) return ERR::Read;
        LONG chunksize  = HEAD_LENGTH + namelen + extralen + File->CompressedSize;
        DOUBLE currentpos = File->Offset + chunksize;
    -   if (acSeekStart(Self->FileIO, currentpos) != ERR_Okay) return log.warning(ERR_Seek);
    +   if (acSeekStart(Self->FileIO, currentpos) != ERR::Okay) return log.warning(ERR::Seek);
     
        DOUBLE writepos = File->Offset;
     
        struct acRead read = { Self->Input, SIZE_COMPRESSION_BUFFER };
    -   while ((!Action(AC_Read, Self->FileIO, &read)) and (read.Result > 0)) {
    -      if (acSeekStart(Self->FileIO, writepos) != ERR_Okay) return log.warning(ERR_Seek);
    +   while ((Action(AC_Read, Self->FileIO, &read) IS ERR::Okay) and (read.Result > 0)) {
    +      if (acSeekStart(Self->FileIO, writepos) != ERR::Okay) return log.warning(ERR::Seek);
           struct acWrite write = { Self->Input, read.Result };
    -      if (Action(AC_Write, Self->FileIO, &write) != ERR_Okay) return log.warning(ERR_Write);
    +      if (Action(AC_Write, Self->FileIO, &write) != ERR::Okay) return log.warning(ERR::Write);
           writepos += write.Result;
     
           currentpos += read.Result;
    -      if (acSeekStart(Self->FileIO, currentpos) != ERR_Okay) return log.warning(ERR_Seek);
    +      if (acSeekStart(Self->FileIO, currentpos) != ERR::Okay) return log.warning(ERR::Seek);
        }
     
        Self->FileIO->set(FID_Size, writepos);
    @@ -473,7 +475,7 @@ static ERROR remove_file(extCompression *Self, std::list::iterator &Fil
        for (++scan; scan != Self->Files.end(); scan++) scan->Offset -= chunksize;
     
        File = Self->Files.erase(File); // Remove the file reference from the chain
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //*********************************************************************************************************************
    @@ -483,15 +485,15 @@ static ERROR remove_file(extCompression *Self, std::list::iterator &Fil
     // if the zip file is damaged or partially downloaded, it will fail.  In the event that the directory is unavailable,
     // the function will fallback to scan_zip().
     
    -static ERROR fast_scan_zip(extCompression *Self)
    +static ERR fast_scan_zip(extCompression *Self)
     {
        pf::Log log(__FUNCTION__);
        ziptail tail;
     
        log.traceBranch("");
     
    -   if (acSeek(Self->FileIO, TAIL_LENGTH, SEEK::END) != ERR_Okay) return ERR_Seek; // Surface error, fail
    -   if (acRead(Self->FileIO, &tail, TAIL_LENGTH, NULL) != ERR_Okay) return ERR_Read; // Surface error, fail
    +   if (acSeek(Self->FileIO, TAIL_LENGTH, SEEK::END) != ERR::Okay) return ERR::Seek; // Surface error, fail
    +   if (acRead(Self->FileIO, &tail, TAIL_LENGTH, NULL) != ERR::Okay) return ERR::Read; // Surface error, fail
     
        if (0x06054b50 != ((ULONG *)&tail)[0]) {
           // Tail not available, use the slow scanner instead
    @@ -504,13 +506,13 @@ static ERROR fast_scan_zip(extCompression *Self)
        tail.listoffset = le32_cpu(tail.listoffset);
     #endif
     
    -   if (acSeek(Self->FileIO, tail.listoffset, SEEK::START) != ERR_Okay) return ERR_Seek;
    +   if (acSeek(Self->FileIO, tail.listoffset, SEEK::START) != ERR::Okay) return ERR::Seek;
     
        zipentry *list, *scan;
        LONG total_files = 0;
    -   if (!AllocMemory(tail.listsize, MEM::DATA|MEM::NO_CLEAR, (APTR *)&list, NULL)) {
    +   if (AllocMemory(tail.listsize, MEM::DATA|MEM::NO_CLEAR, (APTR *)&list, NULL) IS ERR::Okay) {
           log.trace("Reading end-of-central directory from index %d, %d bytes.", tail.listoffset, tail.listsize);
    -      if (acRead(Self->FileIO, list, tail.listsize, NULL) != ERR_Okay) {
    +      if (acRead(Self->FileIO, list, tail.listsize, NULL) != ERR::Okay) {
              FreeResource(list);
              return scan_zip(Self);
           }
    @@ -580,27 +582,27 @@ static ERROR fast_scan_zip(extCompression *Self)
        }
     
        FreeResource(list);
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //*********************************************************************************************************************
     // Scans a zip file and adds file entries to the Compression object.
     
    -static ERROR scan_zip(extCompression *Self)
    +static ERR scan_zip(extCompression *Self)
     {
        pf::Log log(__FUNCTION__);
     
        log.traceBranch("");
     
    -   if (acSeek(Self->FileIO, 0.0, SEEK::START) != ERR_Okay) return log.warning(ERR_Seek);
    +   if (acSeek(Self->FileIO, 0.0, SEEK::START) != ERR::Okay) return log.warning(ERR::Seek);
     
        LONG type, result;
        LONG total_files = 0;
    -   while (!flReadLE(Self->FileIO, &type)) {
    +   while (flReadLE(Self->FileIO, &type) IS ERR::Okay) {
           if (type IS 0x04034b50) {
              // PKZIP file header entry detected
     
    -         if (acSeek(Self->FileIO, (DOUBLE)HEAD_COMPRESSEDSIZE-4, SEEK::CURRENT) != ERR_Okay) return log.warning(ERR_Seek);
    +         if (acSeek(Self->FileIO, (DOUBLE)HEAD_COMPRESSEDSIZE-4, SEEK::CURRENT) != ERR::Okay) return log.warning(ERR::Seek);
     
              struct {
                 ULONG compressedsize;
    @@ -609,7 +611,7 @@ static ERROR scan_zip(extCompression *Self)
                 UWORD extralen;
              } header;
     
    -         if (acRead(Self->FileIO, &header, sizeof(header), &result) != ERR_Okay) return log.warning(ERR_Read);
    +         if (acRead(Self->FileIO, &header, sizeof(header), &result) != ERR::Okay) return log.warning(ERR::Read);
     
     #ifndef REVERSE_BYTEORDER
              header.compressedsize = le32_cpu(header.compressedsize);
    @@ -618,7 +620,7 @@ static ERROR scan_zip(extCompression *Self)
              header.extralen       = le16_cpu(header.extralen);
     #endif
     
    -         if (acSeekCurrent(Self->FileIO, header.compressedsize + header.namelen + header.extralen) != ERR_Okay) return log.warning(ERR_Seek);
    +         if (acSeekCurrent(Self->FileIO, header.compressedsize + header.namelen + header.extralen) != ERR::Okay) return log.warning(ERR::Seek);
           }
           else if (type IS 0x02014b50) {
              // PKZIP list entry detected
    @@ -626,7 +628,7 @@ static ERROR scan_zip(extCompression *Self)
              total_files++;
     
              zipentry zipentry;
    -         if (acRead(Self->FileIO, &zipentry, sizeof(zipentry), &result) != ERR_Okay) return log.warning(ERR_Read);
    +         if (acRead(Self->FileIO, &zipentry, sizeof(zipentry), &result) != ERR::Okay) return log.warning(ERR::Read);
     
     #ifndef REVERSE_BYTEORDER
              zipentry.deflatemethod  = le16_cpu(zipentry.deflatemethod);
    @@ -646,17 +648,17 @@ static ERROR scan_zip(extCompression *Self)
              ZipFile entry;
     
              entry.Name.resize(zipentry.namelen);
    -         if (acRead(Self->FileIO, (APTR)entry.Name.c_str(), zipentry.namelen, &result)) return log.warning(ERR_Read);
    +         if (acRead(Self->FileIO, (APTR)entry.Name.c_str(), zipentry.namelen, &result) != ERR::Okay) return log.warning(ERR::Read);
     
              if (zipentry.extralen > 0) { // Not currently used
                 std::string extra(zipentry.extralen, '\0');
                 struct acRead read = { (APTR)extra.c_str(), zipentry.extralen };
    -            if (Action(AC_Read, Self->FileIO, &read)) return log.warning(ERR_Read);
    +            if (Action(AC_Read, Self->FileIO, &read) != ERR::Okay) return log.warning(ERR::Read);
              }
     
              if (zipentry.commentlen > 0) {
                 entry.Comment.resize(zipentry.commentlen);
    -            if (acRead(Self->FileIO, (APTR)entry.Comment.c_str(), zipentry.commentlen, &result)) return log.warning(ERR_Read);
    +            if (acRead(Self->FileIO, (APTR)entry.Comment.c_str(), zipentry.commentlen, &result) != ERR::Okay) return log.warning(ERR::Read);
              }
     
              entry.NameLen        = zipentry.namelen;
    @@ -690,41 +692,38 @@ static ERROR scan_zip(extCompression *Self)
           else {
              // Unrecognised PKZIP data
              log.warning("Unrecognised PKZIP entry $%.8x in the central directory.", type);
    -         return ERR_InvalidData;
    +         return ERR::InvalidData;
           }
        }
     
        log.trace("Detected %d files.", total_files);
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //*********************************************************************************************************************
     
    -static ERROR send_feedback(extCompression *Self, CompressionFeedback *Feedback)
    +static ERR send_feedback(extCompression *Self, CompressionFeedback *Feedback)
     {
        pf::Log log(__FUNCTION__);
    -   ERROR error;
    +   ERR error;
     
    -   if (!Self->Feedback.Type) return ERR_Okay;
    +   if (!Self->Feedback.Type) return ERR::Okay;
     
    -   if (Self->Feedback.Type IS CALL_STDC) {
    -      auto routine = (ERROR (*)(extCompression *, CompressionFeedback *))Self->Feedback.StdC.Routine;
    -      if (Self->Feedback.StdC.Context) {
    -         pf::SwitchContext context(Self->Feedback.StdC.Context);
    -         error = routine(Self, Feedback);
    -      }
    -      else error = routine(Self, Feedback);
    +   if (Self->Feedback.isC()) {
    +      auto routine = (ERR (*)(extCompression *, CompressionFeedback *, APTR Meta))Self->Feedback.StdC.Routine;
    +      pf::SwitchContext context(Self->Feedback.StdC.Context);
    +      error = routine(Self, Feedback, Self->Feedback.StdC.Meta);
        }
    -   else if (Self->Feedback.Type IS CALL_SCRIPT) {
    +   else if (Self->Feedback.isScript()) {
           const ScriptArg args[] = {
              { "Compression", Self, FD_OBJECTPTR },
              { "CompressionFeedback:Feedback", Feedback, FD_POINTER|FD_STRUCT }
           };
    -      if (scCallback(Self->Feedback.Script.Script, Self->Feedback.Script.ProcedureID, args, ARRAYSIZE(args), &error)) error = ERR_Failed;
    +      if (scCallback(Self->Feedback.Script.Script, Self->Feedback.Script.ProcedureID, args, std::ssize(args), &error) != ERR::Okay) error = ERR::Failed;
        }
        else {
           log.warning("Callback function structure does not specify a recognised Type.");
    -      error = ERR_Terminate;
    +      error = ERR::Terminate;
        }
     
        return error;
    @@ -742,8 +741,8 @@ static void write_eof(extCompression *Self)
              acSeekStart(Self->FileIO, last.Offset + HEAD_NAMELEN);
     
              UWORD namelen, extralen;
    -         if (flReadLE(Self->FileIO, &namelen)) return;
    -         if (flReadLE(Self->FileIO, &extralen)) return;
    +         if (flReadLE(Self->FileIO, &namelen) != ERR::Okay) return;
    +         if (flReadLE(Self->FileIO, &extralen) != ERR::Okay) return;
              acSeekCurrent(Self->FileIO, last.CompressedSize + namelen + extralen);
              ULONG listoffset = last.Offset + last.CompressedSize + namelen + extralen + HEAD_LENGTH;
     
    diff --git a/src/core/core.cpp b/src/core/core.cpp
    index 11eea657c..2fb4c9251 100644
    --- a/src/core/core.cpp
    +++ b/src/core/core.cpp
    @@ -97,25 +97,25 @@ static LONG CrashHandler(LONG Code, APTR Address, LONG Continuable, LONG *Info)
     static void BreakHandler(void)  __attribute__((unused));
     #endif
     
    -extern "C" ERROR add_archive_class(void);
    -extern "C" ERROR add_compressed_stream_class(void);
    -extern "C" ERROR add_compression_class(void);
    -extern "C" ERROR add_script_class(void);
    -extern "C" ERROR add_task_class(void);
    -extern "C" ERROR add_thread_class(void);
    -extern "C" ERROR add_module_class(void);
    -extern "C" ERROR add_config_class(void);
    -extern "C" ERROR add_time_class(void);
    +extern "C" ERR add_archive_class(void);
    +extern "C" ERR add_compressed_stream_class(void);
    +extern "C" ERR add_compression_class(void);
    +extern "C" ERR add_script_class(void);
    +extern "C" ERR add_task_class(void);
    +extern "C" ERR add_thread_class(void);
    +extern "C" ERR add_module_class(void);
    +extern "C" ERR add_config_class(void);
    +extern "C" ERR add_time_class(void);
     #ifdef __ANDROID__
    -extern "C" ERROR add_asset_class(void);
    +extern "C" ERR add_asset_class(void);
     #endif
    -extern "C" ERROR add_file_class(void);
    -extern "C" ERROR add_storage_class(void);
    +extern "C" ERR add_file_class(void);
    +extern "C" ERR add_storage_class(void);
     
     LONG InitCore(void);
     __export void CloseCore(void);
    -__export ERROR OpenCore(OpenInfo *, struct CoreBase **);
    -static ERROR init_volumes(const std::forward_list &);
    +__export ERR OpenCore(OpenInfo *, struct CoreBase **);
    +static ERR init_volumes(const std::forward_list &);
     
     #ifdef _WIN32
     #define DLLCALL // __declspec(dllimport)
    @@ -158,7 +158,7 @@ void _init(void)
     
     //********************************************************************************************************************
     
    -ERROR OpenCore(OpenInfo *Info, struct CoreBase **JumpTable)
    +ERR OpenCore(OpenInfo *Info, struct CoreBase **JumpTable)
     {
        #ifdef __unix__
           struct timeval tmday;
    @@ -169,8 +169,8 @@ ERROR OpenCore(OpenInfo *Info, struct CoreBase **JumpTable)
        #endif
        LONG i;
     
    -   if (!Info) return ERR_Failed;
    -   if ((Info->Flags & OPF::ERROR) != OPF::NIL) Info->Error = ERR_Failed;
    +   if (!Info) return ERR::Failed;
    +   if ((Info->Flags & OPF::ERROR) != OPF::NIL) Info->Error = ERR::Failed;
        glOpenInfo   = Info;
        tlMainThread = TRUE;
        glCodeIndex  = 0; // Reset the code index so that CloseCore() will work.
    @@ -254,7 +254,7 @@ ERROR OpenCore(OpenInfo *Info, struct CoreBase **JumpTable)
              else if (winGetCurrentDirectory(sizeof(buffer), buffer)) glRootPath = buffer;
              else {
                 fprintf(stderr, "Failed to determine root folder.\n");
    -            return ERR_Failed;
    +            return ERR::Failed;
              }
              if (glRootPath.back() != '\\') glRootPath += '\\';
           #else
    @@ -318,34 +318,34 @@ ERROR OpenCore(OpenInfo *Info, struct CoreBase **JumpTable)
              if ((arg[0] != '-') or (arg[1] != '-')) { newargs.push_back(arg); continue; }
              arg += 2; // Skip '--' as this prepends all Core arguments
     
    -         if (!StrMatch(arg, "log-memory")) {
    +         if (ERR::Okay IS StrMatch(arg, "log-memory")) {
                 glShowPrivate = true;
                 glDebugMemory = true;
              }
    -         else if (!StrCompare(arg, "gfx-driver=", 11)) {
    +         else if (ERR::Okay IS StrCompare(arg, "gfx-driver=", 11)) {
                 StrCopy(arg+11, glDisplayDriver, sizeof(glDisplayDriver));
              }
    -         else if ((!StrMatch(arg, "set-volume")) and (i+1 < Info->ArgCount)) { // --set-volume scripts=my:location/
    +         else if ((ERR::Okay IS StrMatch(arg, "set-volume")) and (i+1 < Info->ArgCount)) { // --set-volume scripts=my:location/
                 volumes.emplace_front(Info->Args[++i]);
              }
    -         else if (!StrMatch(arg, "no-crash-handler")) glEnableCrashHandler = false;
    -         else if (!StrMatch(arg, "sync"))        glSync = true;
    -         else if (!StrMatch(arg, "log-threads")) glLogThreads = true;
    -         else if (!StrMatch(arg, "log-none"))    glLogLevel = 0;
    -         else if (!StrMatch(arg, "log-error"))   glLogLevel = 1;
    -         else if (!StrMatch(arg, "log-warn"))    glLogLevel = 2;
    -         else if (!StrMatch(arg, "log-warning")) glLogLevel = 2;
    -         else if (!StrMatch(arg, "log-info"))    glLogLevel = 4; // Levels 3/4 are for applications (no internal detail)
    -         else if (!StrMatch(arg, "log-api"))     glLogLevel = 5; // Default level for API messages
    -         else if (!StrMatch(arg, "log-extapi"))  glLogLevel = 6;
    -         else if (!StrMatch(arg, "log-debug"))   glLogLevel = 7;
    -         else if (!StrMatch(arg, "log-trace"))   glLogLevel = 9;
    -         else if (!StrMatch(arg, "log-all"))     glLogLevel = 9; // 9 is the absolute maximum
    -         else if (!StrMatch(arg, "time"))        glTimeLog = PreciseTime();
    +         else if (ERR::Okay IS StrMatch(arg, "no-crash-handler")) glEnableCrashHandler = false;
    +         else if (ERR::Okay IS StrMatch(arg, "sync"))        glSync = true;
    +         else if (ERR::Okay IS StrMatch(arg, "log-threads")) glLogThreads = true;
    +         else if (ERR::Okay IS StrMatch(arg, "log-none"))    glLogLevel = 0;
    +         else if (ERR::Okay IS StrMatch(arg, "log-error"))   glLogLevel = 1;
    +         else if (ERR::Okay IS StrMatch(arg, "log-warn"))    glLogLevel = 2;
    +         else if (ERR::Okay IS StrMatch(arg, "log-warning")) glLogLevel = 2;
    +         else if (ERR::Okay IS StrMatch(arg, "log-info"))    glLogLevel = 4; // Levels 3/4 are for applications (no internal detail)
    +         else if (ERR::Okay IS StrMatch(arg, "log-api"))     glLogLevel = 5; // Default level for API messages
    +         else if (ERR::Okay IS StrMatch(arg, "log-extapi"))  glLogLevel = 6;
    +         else if (ERR::Okay IS StrMatch(arg, "log-debug"))   glLogLevel = 7;
    +         else if (ERR::Okay IS StrMatch(arg, "log-trace"))   glLogLevel = 9;
    +         else if (ERR::Okay IS StrMatch(arg, "log-all"))     glLogLevel = 9; // 9 is the absolute maximum
    +         else if (ERR::Okay IS StrMatch(arg, "time"))        glTimeLog = PreciseTime();
              #if defined(__unix__) && !defined(__ANDROID__)
    -         else if (!StrMatch(arg, "holdpriority")) hold_priority = true;
    +         else if (ERR::Okay IS StrMatch(arg, "holdpriority")) hold_priority = true;
              #endif
    -         else if (!StrCompare("home=", arg, 7)) glHomeFolderName.assign(arg + 7);
    +         else if (ERR::Okay IS StrCompare("home=", arg, 7)) glHomeFolderName.assign(arg + 7);
              else newargs.push_back(Info->Args[i]);
           }
     
    @@ -457,20 +457,20 @@ ERROR OpenCore(OpenInfo *Info, struct CoreBase **JumpTable)
     
                    KMSG("Attempting to re-use an earlier bind().\n");
                    if (setsockopt(glSocket, SOL_SOCKET, SO_REUSEADDR, &reuse, sizeof(reuse)) IS -1) {
    -                  if ((Info->Flags & OPF::ERROR) != OPF::NIL) Info->Error = ERR_SystemCall;
    -                  return ERR_SystemCall;
    +                  if ((Info->Flags & OPF::ERROR) != OPF::NIL) Info->Error = ERR::SystemCall;
    +                  return ERR::SystemCall;
                    }
                 }
                 else {
    -               if ((Info->Flags & OPF::ERROR) != OPF::NIL) Info->Error = ERR_SystemCall;
    -               return ERR_SystemCall;
    +               if ((Info->Flags & OPF::ERROR) != OPF::NIL) Info->Error = ERR::SystemCall;
    +               return ERR::SystemCall;
                 }
              }
           }
           else {
              KERR("Failed to create a new socket communication point.\n");
    -         if ((Info->Flags & OPF::ERROR) != OPF::NIL) Info->Error = ERR_SystemCall;
    -         return ERR_SystemCall;
    +         if ((Info->Flags & OPF::ERROR) != OPF::NIL) Info->Error = ERR::SystemCall;
    +         return ERR::SystemCall;
           }
     
           RegisterFD(glSocket, RFD::READ, NULL, NULL);
    @@ -483,38 +483,38 @@ ERROR OpenCore(OpenInfo *Info, struct CoreBase **JumpTable)
     
        init_metaclass();
     
    -   if (add_task_class() != ERR_Okay)    { CloseCore(); return ERR_AddClass; }
    -   if (add_thread_class() != ERR_Okay)  { CloseCore(); return ERR_AddClass; }
    -   if (add_module_class() != ERR_Okay)  { CloseCore(); return ERR_AddClass; }
    -   if (add_time_class() != ERR_Okay)    { CloseCore(); return ERR_AddClass; }
    -   if (add_config_class() != ERR_Okay)  { CloseCore(); return ERR_AddClass; }
    -   if (add_storage_class() != ERR_Okay) { CloseCore(); return ERR_AddClass; }
    -   if (add_file_class() != ERR_Okay)    { CloseCore(); return ERR_AddClass; }
    -   if (add_script_class() != ERR_Okay)  { CloseCore(); return ERR_AddClass; }
    -   if (add_archive_class() != ERR_Okay) { CloseCore(); return ERR_AddClass; }
    -   if (add_compressed_stream_class() != ERR_Okay) { CloseCore(); return ERR_AddClass; }
    -   if (add_compression_class() != ERR_Okay) { CloseCore(); return ERR_AddClass; }
    +   if (add_task_class() != ERR::Okay)    { CloseCore(); return ERR::AddClass; }
    +   if (add_thread_class() != ERR::Okay)  { CloseCore(); return ERR::AddClass; }
    +   if (add_module_class() != ERR::Okay)  { CloseCore(); return ERR::AddClass; }
    +   if (add_time_class() != ERR::Okay)    { CloseCore(); return ERR::AddClass; }
    +   if (add_config_class() != ERR::Okay)  { CloseCore(); return ERR::AddClass; }
    +   if (add_storage_class() != ERR::Okay) { CloseCore(); return ERR::AddClass; }
    +   if (add_file_class() != ERR::Okay)    { CloseCore(); return ERR::AddClass; }
    +   if (add_script_class() != ERR::Okay)  { CloseCore(); return ERR::AddClass; }
    +   if (add_archive_class() != ERR::Okay) { CloseCore(); return ERR::AddClass; }
    +   if (add_compressed_stream_class() != ERR::Okay) { CloseCore(); return ERR::AddClass; }
    +   if (add_compression_class() != ERR::Okay) { CloseCore(); return ERR::AddClass; }
        #ifdef __ANDROID__
    -   if (add_asset_class() != ERR_Okay) { CloseCore(); return ERR_AddClass; }
    +   if (add_asset_class() != ERR::Okay) { CloseCore(); return ERR::AddClass; }
        #endif
     
        if (!(glCurrentTask = extTask::create::untracked())) {
           CloseCore();
    -      return ERR_CreateObject;
    +      return ERR::CreateObject;
        }
     
    -   if (init_volumes(volumes)) {
    +   if (init_volumes(volumes) != ERR::Okay) {
           KERR("Failed to initialise the filesystem.");
           CloseCore();
    -      return ERR_Failed;
    +      return ERR::Failed;
        }
     
        fs_initialised = true;
     
     #ifndef PARASOL_STATIC
        if ((Info->Flags & OPF::SCAN_MODULES) IS OPF::NIL) {
    -      ERROR error;
    -      objFile::create file = { fl::Path(glClassBinPath), fl::Flags(FL::READ) };
    +      ERR error;
    +      auto file = objFile::create { fl::Path(glClassBinPath), fl::Flags(FL::READ) };
     
           if (file.ok()) {
              LONG filesize;
    @@ -525,17 +525,17 @@ ERROR OpenCore(OpenInfo *Info, struct CoreBase **JumpTable)
              if (hdr IS CLASSDB_HEADER) {
                 while (file->Position + ClassRecord::MIN_SIZE < filesize) {
                    ClassRecord item;
    -               if ((error = item.read(*file))) break;
    +               if ((error = item.read(*file)) != ERR::Okay) break;
     
                    if (glClassDB.contains(item.ClassID)) {
                       log.warning("Invalid class dictionary file, %s is registered twice.", item.Name.c_str());
    -                  error = ERR_Failed;
    +                  error = ERR::Failed;
                       break;
                    }
                    glClassDB[item.ClassID] = item;
                 }
     
    -            if (error) glScanClasses = true;
    +            if (error != ERR::Okay) glScanClasses = true;
              }
              else {
                 // File is probably from an old version and requires recalculation.
    @@ -553,7 +553,7 @@ ERROR OpenCore(OpenInfo *Info, struct CoreBase **JumpTable)
     #ifdef _WIN32
        {
           STRING libpath;
    -      if (!ResolvePath("modules:lib", RSF::NO_FILE_CHECK, &libpath)) {
    +      if (ResolvePath("modules:lib", RSF::NO_FILE_CHECK, &libpath) IS ERR::Okay) {
              winSetDllDirectory(libpath);
              FreeResource(libpath);
           }
    @@ -597,10 +597,10 @@ ERROR OpenCore(OpenInfo *Info, struct CoreBase **JumpTable)
        log.msg("PROGRAM OPENED");
     
        glSystemState = 0; // Indicates that initialisation is complete.
    -   if ((Info->Flags & OPF::ERROR) != OPF::NIL) Info->Error = ERR_Okay;
    +   if ((Info->Flags & OPF::ERROR) != OPF::NIL) Info->Error = ERR::Okay;
     
        *JumpTable = LocalCoreBase;
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     //********************************************************************************************************************
    @@ -988,26 +988,26 @@ static LONG CrashHandler(LONG Code, APTR Address, LONG Continuable, LONG *Info)
     
     //********************************************************************************************************************
     
    -extern "C" ERROR convert_errno(LONG Error, ERROR Default)
    +extern "C" ERR convert_errno(LONG Error, ERR Default)
     {
        switch (Error) {
    -      case 0:       return ERR_Okay;
    -      case ENAMETOOLONG: return ERR_BufferOverflow;
    -      case EACCES:  return ERR_NoPermission;
    -      case EPERM:   return ERR_NoPermission;
    -      case EBUSY:   return ERR_Locked;
    -      case EROFS:   return ERR_ReadOnly;
    -      case EMFILE:  return ERR_ArrayFull;
    -      case ENFILE:  return ERR_ArrayFull;
    -      case ENOENT:  return ERR_FileNotFound;
    -      case ENOMEM:  return ERR_AllocMemory;
    -      case ENOTDIR: return ERR_FileNotFound;
    -      case EEXIST:  return ERR_FileExists;
    -      case ENOSPC:  return ERR_OutOfSpace;
    -      case EFAULT:  return ERR_IllegalAddress;
    -      case EIO:     return ERR_Failed;
    +      case 0:       return ERR::Okay;
    +      case ENAMETOOLONG: return ERR::BufferOverflow;
    +      case EACCES:  return ERR::NoPermission;
    +      case EPERM:   return ERR::NoPermission;
    +      case EBUSY:   return ERR::Locked;
    +      case EROFS:   return ERR::ReadOnly;
    +      case EMFILE:  return ERR::ArrayFull;
    +      case ENFILE:  return ERR::ArrayFull;
    +      case ENOENT:  return ERR::FileNotFound;
    +      case ENOMEM:  return ERR::AllocMemory;
    +      case ENOTDIR: return ERR::FileNotFound;
    +      case EEXIST:  return ERR::FileExists;
    +      case ENOSPC:  return ERR::OutOfSpace;
    +      case EFAULT:  return ERR::IllegalAddress;
    +      case EIO:     return ERR::Failed;
           #ifdef ELOOP
    -      case ELOOP:   return ERR_Loop;
    +      case ELOOP:   return ERR::Loop;
           #endif
           default:      return Default;
        }
    @@ -1047,7 +1047,7 @@ static void win32_enum_folders(CSTRING Volume, CSTRING Label, CSTRING Path, CSTR
     
     //********************************************************************************************************************
     
    -static ERROR init_volumes(const std::forward_list &Volumes)
    +static ERR init_volumes(const std::forward_list &Volumes)
     {
        pf::Log log("Core");
     
    @@ -1102,7 +1102,7 @@ static ERROR init_volumes(const std::forward_list &Volumes)
        #else
           SetVolume("templates", "scripts:templates/", "misc/openbook", NULL, NULL, VOLUME::HIDDEN|VOLUME::SYSTEM);
           SetVolume("config", "system:config/", "tools/cog", NULL, NULL, VOLUME::HIDDEN|VOLUME::SYSTEM);
    -      if (!AnalysePath("parasol:bin/", NULL)) { // Bin is the location of the fluid and parasol binaries
    +      if (AnalysePath("parasol:bin/", NULL) IS ERR::Okay) { // Bin is the location of the fluid and parasol binaries
              SetVolume("bin", "parasol:bin/", NULL, NULL, NULL, VOLUME::HIDDEN|VOLUME::SYSTEM);
           }
           else SetVolume("bin", "parasol:", NULL, NULL, NULL, VOLUME::HIDDEN|VOLUME::SYSTEM);
    @@ -1112,7 +1112,6 @@ static ERROR init_volumes(const std::forward_list &Volumes)
        SetVolume("fonts", "system:config/fonts/", "items/font", NULL, NULL, VOLUME::HIDDEN|VOLUME::SYSTEM);
        SetVolume("scripts", "system:scripts/", "filetypes/source", NULL, NULL, VOLUME::HIDDEN|VOLUME::SYSTEM);
        SetVolume("styles", "system:config/styles/", "tools/image_gallery", NULL, NULL, VOLUME::HIDDEN);
    -   SetVolume("icons", "EXT:widget", "misc/picture", NULL, NULL, VOLUME::HIDDEN|VOLUME::SYSTEM); // Refer to widget module for actual configuration
     
        // Some platforms need to have special volumes added - these are provided in the OpenInfo structure passed to
        // the Core.
    @@ -1141,7 +1140,7 @@ static ERROR init_volumes(const std::forward_list &Volumes)
        std::string buffer("config:users/default/");
     
        #ifdef __unix__
    -      if (auto homedir = getenv("HOME"); homedir and homedir[0] and (StrMatch("/", homedir) != ERR_Okay)) {
    +      if (auto homedir = getenv("HOME"); homedir and homedir[0] and (StrMatch("/", homedir) != ERR::Okay)) {
              buffer = homedir;
              if (buffer.back() IS '/') buffer.pop_back();
     
    @@ -1171,7 +1170,7 @@ static ERROR init_volumes(const std::forward_list &Volumes)
     
        if (buffer != "config:users/default/") {
           LOC location_type = LOC::NIL;
    -      if ((AnalysePath(buffer.c_str(), &location_type) != ERR_Okay) or (location_type != LOC::DIRECTORY)) {
    +      if ((AnalysePath(buffer.c_str(), &location_type) != ERR::Okay) or (location_type != LOC::DIRECTORY)) {
              buffer.pop_back();
              SetDefaultPermissions(-1, -1, PERMIT::READ|PERMIT::WRITE);
                 CopyFile("config:users/default/", buffer.c_str(), NULL);
    @@ -1189,11 +1188,11 @@ static ERROR init_volumes(const std::forward_list &Volumes)
        CreateFolder("user:config/", PERMIT::READ|PERMIT::EXEC|PERMIT::WRITE);
        CreateFolder("user:temp/", PERMIT::READ|PERMIT::EXEC|PERMIT::WRITE);
     
    -   if (AnalysePath("temp:", NULL) != ERR_Okay) {
    +   if (AnalysePath("temp:", NULL) != ERR::Okay) {
           SetVolume("temp", "user:temp/", "items/trash", NULL, NULL, VOLUME::REPLACE|VOLUME::HIDDEN|VOLUME::SYSTEM);
        }
     
    -   if (AnalysePath("clipboard:", NULL) != ERR_Okay) {
    +   if (AnalysePath("clipboard:", NULL) != ERR::Okay) {
           SetVolume("clipboard", "temp:clipboard/", "items/clipboard", NULL, NULL, VOLUME::REPLACE|VOLUME::HIDDEN|VOLUME::SYSTEM);
        }
     
    @@ -1275,7 +1274,7 @@ static ERROR init_volumes(const std::forward_list &Volumes)
     
              CSTRING str = buffer;
              while (*str) {
    -            if (!StrCompare("/dev/hd", str)) {
    +            if (ERR::Okay IS StrCompare("/dev/hd", str)) {
                    // Extract mount point
     
                    LONG i = 0;
    @@ -1302,11 +1301,11 @@ static ERROR init_volumes(const std::forward_list &Volumes)
              }
              FreeResource(buffer);
           }
    -      else log.warning(ERR_AllocMemory);
    +      else log.warning(ERR::AllocMemory);
     
           close(file);
        }
    -   else log.warning(ERR_File);
    +   else log.warning(ERR::File);
     
        const CSTRING cdroms[] = {
           "/mnt/cdrom", "/mnt/cdrom0", "/mnt/cdrom1", "/mnt/cdrom2", "/mnt/cdrom3", "/mnt/cdrom4", "/mnt/cdrom5", "/mnt/cdrom6", // RedHat
    @@ -1342,13 +1341,13 @@ static ERROR init_volumes(const std::forward_list &Volumes)
     #ifndef PARASOL_STATIC
        // Change glModulePath to an absolute path to optimise the loading of modules.
        STRING mpath;
    -   if (!ResolvePath("modules:", RSF::NO_FILE_CHECK, &mpath)) {
    +   if (ResolvePath("modules:", RSF::NO_FILE_CHECK, &mpath) IS ERR::Okay) {
           glModulePath = mpath;
           FreeResource(mpath);
        }
     #endif
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     #include "core_close.cpp"
    diff --git a/src/core/core_close.cpp b/src/core/core_close.cpp
    index 9acac82dc..083246eee 100644
    --- a/src/core/core_close.cpp
    +++ b/src/core/core_close.cpp
    @@ -143,6 +143,7 @@ void CloseCore(void)
              pf::Log log("Shutdown");
              log.branch("Freeing the task object and its resources.");
              FreeResource(glCurrentTask);
    +         glCurrentTask = NULL;
           }
     
           // Remove locks on any private objects that have not been unlocked yet
    @@ -150,7 +151,7 @@ void CloseCore(void)
           for (const auto & [ id, mem ] : glPrivateMemory) {
              if (((mem.Flags & MEM::OBJECT) != MEM::NIL) and (mem.AccessCount > 0)) {
                 if (auto obj = mem.Object) {
    -               log.warning("Removing locks on object #%d, Owner: %d, Locks: %d", obj->UID, obj->OwnerID, mem.AccessCount);
    +               log.warning("Removing locks on object #%d, Owner: %d, Locks: %d", obj->UID, obj->Owner ? obj->Owner->UID : 0, mem.AccessCount);
                    for (auto count=mem.AccessCount; count > 0; count--) ReleaseObject(obj);
                 }
              }
    @@ -306,9 +307,9 @@ __export void Expunge(WORD Force)
                    if (mod_master->Expunge) {
                       pf::Log log(__FUNCTION__);
                       log.branch("Sending expunge request to the %s module #%d.", mod_master->Name, mod_master->UID);
    -                  if (!mod_master->Expunge()) {
    +                  if (mod_master->Expunge() IS ERR::Okay) {
                          ccount++;
    -                     if (FreeResource(mod_master)) {
    +                     if (FreeResource(mod_master) != ERR::Okay) {
                             log.warning("RootModule data is corrupt");
                             mod_count = ccount; // Break the loop because the chain links are broken.
                             break;
    @@ -318,7 +319,7 @@ __export void Expunge(WORD Force)
                    }
                    else {
                       ccount++;
    -                  if (FreeResource(mod_master)) {
    +                  if (FreeResource(mod_master) != ERR::Okay) {
                          log.warning("RootModule data is corrupt");
                          mod_count = ccount; // Break the loop because the chain links are broken.
                          break;
    diff --git a/src/core/data.cpp b/src/core/data.cpp
    index a1158e18a..91123362a 100644
    --- a/src/core/data.cpp
    +++ b/src/core/data.cpp
    @@ -194,7 +194,10 @@ THREADVAR WORD tlPreventSleep = 0;
     THREADVAR WORD tlPublicLockCount = 0; // This variable is controlled by GLOBAL_LOCK() and can be used to check if locks are being held prior to sleeping.
     THREADVAR WORD tlPrivateLockCount = 0; // Count of private *memory* locks held per-thread
     
    -struct BaseClass glDummyObject;
    +struct BaseClass glDummyObject = {
    +   .Class = NULL, .ChildPrivate = NULL, .CreatorMeta = NULL, .Owner = NULL, .NotifyFlags = 0, .UID = 0, .Flags = NF::NIL,
    +   .ThreadID = 0, .Name = "", .ThreadPending = 0, .Queue = 0, .SleepQueue = 0, .Locked = 0, .ActionDepth = 0
    +};
     class ObjectContext glTopContext; // Top-level context is a dummy and can be thread-shared
     THREADVAR ObjectContext *tlContext = &glTopContext;
     
    @@ -204,7 +207,7 @@ objTime *glTime = NULL;
     THREADVAR WORD tlMsgRecursion = 0;
     THREADVAR TaskMessage *tlCurrentMsg = NULL;
     
    -ERROR (*glMessageHandler)(struct Message *) = NULL;
    +ERR (*glMessageHandler)(struct Message *) = NULL;
     void (*glVideoRecovery)(void) = NULL;
     void (*glKeyboardRecovery)(void) = NULL;
     void (*glNetProcessMessages)(LONG, APTR) = NULL;
    diff --git a/src/core/data_errors.c b/src/core/data_errors.c
    index 901bac25d..7ff15aa97 100644
    --- a/src/core/data_errors.c
    +++ b/src/core/data_errors.c
    @@ -1,5 +1,5 @@
     
    -const CSTRING glMessages[ERR_END+1] = {
    +const CSTRING glMessages[LONG(ERR::END)+1] = {
      "Operation successful.",
      "The result is false.",
      "Limited success.",
    diff --git a/src/core/defs.h b/src/core/defs.h
    index 2340c1f9a..cadaa0e06 100644
    --- a/src/core/defs.h
    +++ b/src/core/defs.h
    @@ -86,6 +86,7 @@ using namespace std::chrono_literals;
     
     #define BREAKPOINT { UBYTE *nz = 0; nz[0] = 0; }
     
    +#include 
     #include 
     
     #include 
    @@ -159,7 +160,7 @@ struct rkWatchPath {
     using namespace pf;
     
     struct ActionEntry {
    -   ERROR (*PerformAction)(OBJECTPTR, APTR);     // Internal
    +   ERR (*PerformAction)(OBJECTPTR, APTR);     // Internal
     };
     
     struct ThreadMessage {
    @@ -171,7 +172,7 @@ struct ThreadActionMessage {
        OBJECTPTR Object;    // Direct pointer to a target object.
        LONG      ActionID;  // The action to execute.
        LONG      Key;       // Internal
    -   ERROR     Error;     // The error code resulting from the action's execution.
    +   ERR       Error;     // The error code resulting from the action's execution.
        FUNCTION  Callback;  // Callback function to execute on action completion.
     };
     
    @@ -236,11 +237,16 @@ class PrivateAddress {
     struct ActionSubscription {
        OBJECTPTR Subscriber; // The object that initiated the subscription
        OBJECTID SubscriberID; // Required for sanity checks on subscriber still existing.
    -   void (*Callback)(OBJECTPTR, ACTIONID, ERROR, APTR);
    +   void (*Callback)(OBJECTPTR, ACTIONID, ERR, APTR, APTR);
    +   APTR Meta;
     
    -   ActionSubscription() : Subscriber(NULL), SubscriberID(0), Callback(NULL) { }
    -   ActionSubscription(OBJECTPTR pContext, void (*pCallback)(OBJECTPTR, ACTIONID, ERROR, APTR)) : Subscriber(pContext), SubscriberID(pContext->UID), Callback(pCallback) { }
    -   ActionSubscription(OBJECTPTR pContext, APTR pCallback) : Subscriber(pContext), SubscriberID(pContext->UID), Callback((void (*)(OBJECTPTR, ACTIONID, ERROR, APTR))pCallback) { }
    +   ActionSubscription() : Subscriber(NULL), SubscriberID(0), Callback(NULL), Meta(NULL) { }
    +
    +   ActionSubscription(OBJECTPTR pContext, void (*pCallback)(OBJECTPTR, ACTIONID, ERR, APTR, APTR), APTR pMeta) :
    +      Subscriber(pContext), SubscriberID(pContext->UID), Callback(pCallback), Meta(pMeta) { }
    +
    +   ActionSubscription(OBJECTPTR pContext, APTR pCallback, APTR pMeta) :
    +      Subscriber(pContext), SubscriberID(pContext->UID), Callback((void (*)(OBJECTPTR, ACTIONID, ERR, APTR, APTR))pCallback), Meta(pMeta) { }
     };
     
     struct virtual_drive {
    @@ -248,22 +254,22 @@ struct virtual_drive {
        LONG  DriverSize;  // The driver may reserve a private area for its own structure attached to DirInfo.
        char  Name[32];    // Volume name, including the trailing colon at the end
        ULONG CaseSensitive:1;
    -   ERROR (*ScanDir)(DirInfo *);
    -   ERROR (*Rename)(STRING, STRING);
    -   ERROR (*Delete)(STRING, FUNCTION *);
    -   ERROR (*OpenDir)(DirInfo *);
    -   ERROR (*CloseDir)(DirInfo *);
    -   ERROR (*Obsolete)(CSTRING, DirInfo **, LONG);
    -   ERROR (*TestPath)(CSTRING, RSF, LOC *);
    -   ERROR (*WatchPath)(class extFile *);
    +   ERR (*ScanDir)(DirInfo *);
    +   ERR (*Rename)(STRING, STRING);
    +   ERR (*Delete)(STRING, FUNCTION *);
    +   ERR (*OpenDir)(DirInfo *);
    +   ERR (*CloseDir)(DirInfo *);
    +   ERR (*Obsolete)(CSTRING, DirInfo **, LONG);
    +   ERR (*TestPath)(CSTRING, RSF, LOC *);
    +   ERR (*WatchPath)(class extFile *);
        void  (*IgnoreFile)(class extFile *);
    -   ERROR (*GetInfo)(CSTRING, FileInfo *, LONG);
    -   ERROR (*GetDeviceInfo)(CSTRING, objStorageDevice *);
    -   ERROR (*IdentifyFile)(STRING, CLASSID *, CLASSID *);
    -   ERROR (*CreateFolder)(CSTRING, PERMIT);
    -   ERROR (*SameFile)(CSTRING, CSTRING);
    -   ERROR (*ReadLink)(STRING, STRING *);
    -   ERROR (*CreateLink)(CSTRING, CSTRING);
    +   ERR (*GetInfo)(CSTRING, FileInfo *, LONG);
    +   ERR (*GetDeviceInfo)(CSTRING, objStorageDevice *);
    +   ERR (*IdentifyFile)(STRING, CLASSID *, CLASSID *);
    +   ERR (*CreateFolder)(CSTRING, PERMIT);
    +   ERR (*SameFile)(CSTRING, CSTRING);
    +   ERR (*ReadLink)(STRING, STRING *);
    +   ERR (*CreateLink)(CSTRING, CSTRING);
        inline bool is_default() const { return VirtualID IS 0; }
        inline bool is_virtual() const { return VirtualID != 0; }
     };
    @@ -318,7 +324,7 @@ class CoreTimer {
        LARGE     Interval;       // The amount of microseconds to wait at each interval
        OBJECTPTR Subscriber;     // The object that is subscribed (pointer, if private)
        OBJECTID  SubscriberID;   // The object that is subscribed
    -   FUNCTION  Routine;        // Routine to call if not using AC_Timer - ERROR Routine(OBJECTID, LONG, LONG);
    +   FUNCTION  Routine;        // Routine to call if not using AC_Timer - ERR Routine(OBJECTID, LONG, LONG);
        UBYTE     Cycle;
        bool      Locked;
     };
    @@ -518,10 +524,10 @@ struct ClassRecord {
           if (pHeader) Header = pHeader;
        }
     
    -   inline ERROR write(objFile *File) {
    -      if (File->write(&ClassID, sizeof(ClassID), NULL)) return ERR_Write;
    -      if (File->write(&ParentID, sizeof(ParentID), NULL)) return ERR_Write;
    -      if (File->write(&Category, sizeof(Category), NULL)) return ERR_Write;
    +   inline ERR write(objFile *File) {
    +      if (File->write(&ClassID, sizeof(ClassID), NULL) != ERR::Okay) return ERR::Write;
    +      if (File->write(&ParentID, sizeof(ParentID), NULL) != ERR::Okay) return ERR::Write;
    +      if (File->write(&Category, sizeof(Category), NULL) != ERR::Okay) return ERR::Write;
     
           auto size = LONG(Name.size());
           File->write(&size, sizeof(size));
    @@ -539,13 +545,13 @@ struct ClassRecord {
           File->write(&size, sizeof(size));
           if (size) File->write(Header.c_str(), size);
     
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
     
    -   inline ERROR read(objFile *File) {
    -      if (File->read(&ClassID, sizeof(ClassID))) return ERR_Read;
    -      if (File->read(&ParentID, sizeof(ParentID))) return ERR_Read;
    -      if (File->read(&Category, sizeof(Category))) return ERR_Read;
    +   inline ERR read(objFile *File) {
    +      if (File->read(&ClassID, sizeof(ClassID)) != ERR::Okay) return ERR::Read;
    +      if (File->read(&ParentID, sizeof(ParentID)) != ERR::Okay) return ERR::Read;
    +      if (File->read(&Category, sizeof(Category)) != ERR::Okay) return ERR::Read;
     
           char buffer[256];
           LONG size = 0;
    @@ -554,30 +560,30 @@ struct ClassRecord {
              File->read(buffer, size);
              Name.assign(buffer, size);
           }
    -      else return ERR_BufferOverflow;
    +      else return ERR::BufferOverflow;
     
           File->read(&size, sizeof(size));
           if (size < (LONG)sizeof(buffer)) {
              File->read(buffer, size);
              Path.assign(buffer, size);
           }
    -      else return ERR_BufferOverflow;
    +      else return ERR::BufferOverflow;
     
           File->read(&size, sizeof(size));
           if (size < (LONG)sizeof(buffer)) {
              File->read(buffer, size);
              Match.assign(buffer, size);
           }
    -      else return ERR_BufferOverflow;
    +      else return ERR::BufferOverflow;
     
           File->read(&size, sizeof(size));
           if (size < (LONG)sizeof(buffer)) {
              File->read(buffer, size);
              Header.assign(buffer, size);
           }
    -      else return ERR_BufferOverflow;
    +      else return ERR::BufferOverflow;
     
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
     };
     
    @@ -651,7 +657,7 @@ extern std::unordered_map glFields; // Reverse lookup for co
     extern std::unordered_map glWFOList;
     extern std::map glVolumes; // VolumeName = { Key, Value }
     extern std::vector glTasks;
    -extern const CSTRING glMessages[ERR_END+1];       // Read-only table of error messages.
    +extern const CSTRING glMessages[LONG(ERR::END)+1];       // Read-only table of error messages.
     extern const LONG glTotalMessages;
     extern "C" LONG glProcessID;   // Read only
     extern HOSTHANDLE glConsoleFD;
    @@ -721,7 +727,7 @@ extern THREADVAR PERMIT glDefaultPermissions;
     
     //********************************************************************************************************************
     
    -extern ERROR (*glMessageHandler)(struct Message *);
    +extern ERR (*glMessageHandler)(struct Message *);
     extern void (*glVideoRecovery)(void);
     extern void (*glKeyboardRecovery)(void);
     extern void (*glNetProcessMessages)(LONG, APTR);
    @@ -811,8 +817,8 @@ class TaskMessage {
     
           if (pSize <= Buffer.size()) CopyMemory(pData, Buffer.data(), pSize);
           else {
    -         ExtBuffer = new char[pSize];
    -         CopyMemory(pData, ExtBuffer, pSize);
    +         ExtBuffer = new (std::nothrow) char[pSize];
    +         if (ExtBuffer) CopyMemory(pData, ExtBuffer, pSize);
           }
     
           Size = pSize;
    @@ -938,10 +944,10 @@ class RootModule : public BaseClass {
        MHF    Flags;
        UBYTE  NoUnload;
        UBYTE  DLL;                 // TRUE if the module is a Windows DLL
    -   LONG   (*Init)(OBJECTPTR, struct CoreBase *);
    +   ERR    (*Init)(OBJECTPTR, struct CoreBase *);
        void   (*Close)(OBJECTPTR);
    -   LONG   (*Open)(OBJECTPTR);
    -   LONG   (*Expunge)(void);
    +   ERR    (*Open)(OBJECTPTR);
    +   ERR    (*Expunge)(void);
        struct ActionEntry prvActions[AC_END]; // Action routines to be intercepted by the program
        char   LibraryName[40]; // Name of the library loaded from disk
     };
    @@ -952,41 +958,41 @@ extern "C" {
     
     //********************************************************************************************************************
     
    -ERROR SetFieldF(OBJECTPTR, FIELD, va_list);
    +ERR SetFieldF(OBJECTPTR, FIELD, va_list);
     
    -ERROR fs_closedir(DirInfo *);
    -ERROR fs_createlink(CSTRING, CSTRING);
    -ERROR fs_delete(STRING, FUNCTION *);
    -ERROR fs_getinfo(CSTRING, FileInfo *, LONG);
    -ERROR fs_getdeviceinfo(CSTRING, objStorageDevice *);
    +ERR fs_closedir(DirInfo *);
    +ERR fs_createlink(CSTRING, CSTRING);
    +ERR fs_delete(STRING, FUNCTION *);
    +ERR fs_getinfo(CSTRING, FileInfo *, LONG);
    +ERR fs_getdeviceinfo(CSTRING, objStorageDevice *);
     void  fs_ignore_file(class extFile *);
    -ERROR fs_makedir(CSTRING, PERMIT);
    -ERROR fs_opendir(DirInfo *);
    -ERROR fs_readlink(STRING, STRING *);
    -ERROR fs_rename(STRING, STRING);
    -ERROR fs_samefile(CSTRING, CSTRING);
    -ERROR fs_scandir(DirInfo *);
    -ERROR fs_testpath(CSTRING, RSF, LOC *);
    -ERROR fs_watch_path(class extFile *);
    +ERR fs_makedir(CSTRING, PERMIT);
    +ERR fs_opendir(DirInfo *);
    +ERR fs_readlink(STRING, STRING *);
    +ERR fs_rename(STRING, STRING);
    +ERR fs_samefile(CSTRING, CSTRING);
    +ERR fs_scandir(DirInfo *);
    +ERR fs_testpath(CSTRING, RSF, LOC *);
    +ERR fs_watch_path(class extFile *);
     
     const virtual_drive * get_fs(CSTRING Path);
     void  free_storage_class(void);
     
    -ERROR  convert_zip_error(struct z_stream_s *, LONG);
    -ERROR  check_cache(OBJECTPTR, LARGE, LARGE);
    -ERROR  get_class_cmd(CSTRING, objConfig *, LONG, CLASSID, STRING *);
    -ERROR  fs_copy(CSTRING, CSTRING, FUNCTION *, BYTE);
    -ERROR  fs_copydir(STRING, STRING, FileFeedback *, FUNCTION *, BYTE);
    +ERR  convert_zip_error(struct z_stream_s *, LONG);
    +ERR  check_cache(OBJECTPTR, LARGE, LARGE);
    +ERR  get_class_cmd(CSTRING, objConfig *, LONG, CLASSID, STRING *);
    +ERR  fs_copy(CSTRING, CSTRING, FUNCTION *, BYTE);
    +ERR  fs_copydir(STRING, STRING, FileFeedback *, FUNCTION *, BYTE);
     PERMIT get_parent_permissions(CSTRING, LONG *, LONG *);
    -ERROR  load_datatypes(void);
    -ERROR  RenameVolume(CSTRING, CSTRING);
    -ERROR  findfile(STRING);
    +ERR  load_datatypes(void);
    +ERR  RenameVolume(CSTRING, CSTRING);
    +ERR  findfile(STRING);
     PERMIT convert_fs_permissions(LONG);
     LONG   convert_permissions(PERMIT);
     void   set_memory_manager(APTR, ResourceManager *);
     BYTE   strip_folder(STRING) __attribute__ ((unused));
    -ERROR  get_file_info(CSTRING, FileInfo *, LONG);
    -extern "C" ERROR  convert_errno(LONG Error, ERROR Default);
    +ERR  get_file_info(CSTRING, FileInfo *, LONG);
    +extern "C" ERR  convert_errno(LONG Error, ERR Default);
     void   free_file_cache(void);
     
     __export void Expunge(WORD);
    @@ -999,58 +1005,58 @@ CSTRING action_name(OBJECTPTR Object, LONG ActionID);
     #ifndef PARASOL_STATIC
     APTR   build_jump_table(const Function *);
     #endif
    -ERROR  copy_args(const FunctionField *, LONG, BYTE *, BYTE *, LONG, LONG *, CSTRING);
    -ERROR  copy_field_to_buffer(OBJECTPTR, Field *, LONG, APTR, CSTRING, LONG *);
    -ERROR  create_archive_volume(void);
    -ERROR  delete_tree(STRING, LONG, FUNCTION *, FileFeedback *);
    +ERR  copy_args(const FunctionField *, LONG, BYTE *, BYTE *, LONG, LONG *, CSTRING);
    +ERR  copy_field_to_buffer(OBJECTPTR, Field *, LONG, APTR, CSTRING, LONG *);
    +ERR  create_archive_volume(void);
    +ERR  delete_tree(STRING, LONG, FUNCTION *, FileFeedback *);
     struct ClassItem * find_class(CLASSID);
    -ERROR  find_private_object_entry(OBJECTID, LONG *);
    +ERR  find_private_object_entry(OBJECTID, LONG *);
     void   free_events(void);
     void   free_module_entry(RootModule *);
     void   free_wakelocks(void);
     LONG   get_thread_id(void);
     void   init_metaclass(void);
    -ERROR  init_sleep(LONG, LONG, LONG);
    +ERR  init_sleep(LONG, LONG, LONG);
     void   local_free_args(APTR, const FunctionField *);
     Field * lookup_id(OBJECTPTR, ULONG, OBJECTPTR *);
    -ERROR  msg_event(APTR, LONG, LONG, APTR, LONG);
    -ERROR  msg_threadcallback(APTR, LONG, LONG, APTR, LONG);
    -ERROR  msg_threadaction(APTR, LONG, LONG, APTR, LONG);
    -ERROR  msg_free(APTR, LONG, LONG, APTR, LONG);
    +ERR  msg_event(APTR, LONG, LONG, APTR, LONG);
    +ERR  msg_threadcallback(APTR, LONG, LONG, APTR, LONG);
    +ERR  msg_threadaction(APTR, LONG, LONG, APTR, LONG);
    +ERR  msg_free(APTR, LONG, LONG, APTR, LONG);
     void   optimise_write_field(Field &);
     void   PrepareSleep(void);
    -ERROR  process_janitor(OBJECTID, LONG, LONG);
    +ERR  process_janitor(OBJECTID, LONG, LONG);
     void   remove_process_waitlocks(void);
    -ERROR  resolve_args(APTR, const FunctionField *);
    +ERR  resolve_args(APTR, const FunctionField *);
     
     #ifndef PARASOL_STATIC
     void   scan_classes(void);
     #endif
     
     void   remove_threadpool(void);
    -ERROR  threadpool_get(extThread **);
    +ERR  threadpool_get(extThread **);
     void   threadpool_release(extThread *);
    -ERROR  writeval_default(OBJECTPTR, Field *, LONG, const void *, LONG);
    -extern "C" ERROR validate_process(LONG);
    +ERR  writeval_default(OBJECTPTR, Field *, LONG, const void *, LONG);
    +extern "C" ERR validate_process(LONG);
     void   free_iconv(void);
    -ERROR  check_paths(CSTRING, PERMIT);
    +ERR  check_paths(CSTRING, PERMIT);
     void   merge_groups(ConfigGroups &, ConfigGroups &);
     
     #ifdef _WIN32
    -   extern "C" ERROR open_public_waitlock(WINHANDLE *, CSTRING);
    +   extern "C" ERR open_public_waitlock(WINHANDLE *, CSTRING);
        extern "C" WINHANDLE get_threadlock(void);
        extern "C" void  free_threadlocks(void);
    -   extern "C" ERROR wake_waitlock(WINHANDLE, LONG);
    -   extern "C" ERROR alloc_public_waitlock(WINHANDLE *, const char *Name);
    +   extern "C" ERR wake_waitlock(WINHANDLE, LONG);
    +   extern "C" ERR alloc_public_waitlock(WINHANDLE *, const char *Name);
        extern "C" void  free_public_waitlock(WINHANDLE);
    -   extern "C" ERROR send_thread_msg(WINHANDLE, LONG Type, APTR, LONG);
    +   extern "C" ERR send_thread_msg(WINHANDLE, LONG Type, APTR, LONG);
        extern "C" LONG  sleep_waitlock(WINHANDLE, LONG);
     #else
        struct sockaddr_un * get_socket_path(LONG, socklen_t *);
    -   ERROR alloc_public_cond(CONDLOCK *, ALF);
    +   ERR alloc_public_cond(CONDLOCK *, ALF);
        void  free_public_cond(CONDLOCK *);
    -   ERROR public_cond_wait(THREADLOCK *, CONDLOCK *, LONG);
    -   ERROR send_thread_msg(LONG, LONG, APTR, LONG);
    +   ERR public_cond_wait(THREADLOCK *, CONDLOCK *, LONG);
    +   ERR send_thread_msg(LONG, LONG, APTR, LONG);
     #endif
     
     #ifdef _WIN32
    @@ -1107,7 +1113,7 @@ extern "C" LONG winWaitThread(WINHANDLE, LONG);
     extern "C" LONG winWriteStd(APTR, CPTR Buffer, LONG Size);
     extern "C" int winDeleteFile(char *Path);
     extern "C" LONG winCheckDirectoryExists(CSTRING);
    -extern "C" LONG winCreateDir(CSTRING);
    +extern "C" ERR winCreateDir(CSTRING);
     extern "C" LONG winCurrentDirectory(STRING, LONG);
     extern "C" LONG winFileInfo(CSTRING, long long *, struct DateTime *, BYTE *);
     extern "C" void winFindClose(WINHANDLE);
    @@ -1131,7 +1137,7 @@ extern "C" LONG winScan(APTR *, STRING, STRING, LARGE *, struct DateTime *, stru
     extern "C" LONG winSetAttrib(CSTRING, LONG);
     extern "C" LONG winSetEOF(CSTRING, LARGE);
     extern "C" LONG winTestLocation(CSTRING, BYTE);
    -extern "C" LONG winWatchFile(LONG, CSTRING, APTR, WINHANDLE *, LONG *);
    +extern "C" ERR winWatchFile(LONG, CSTRING, APTR, WINHANDLE *, LONG *);
     extern "C" void winFindCloseChangeNotification(WINHANDLE);
     extern "C" APTR winFindDirectory(STRING, APTR *, STRING);
     extern "C" APTR winFindFile(STRING, APTR *, STRING);
    @@ -1153,21 +1159,21 @@ class ScopedObjectAccess {
           OBJECTPTR obj;
     
        public:
    -      ERROR error;
    +      ERR error;
     
           ScopedObjectAccess(OBJECTPTR Object) {
              error = Object->lock();
              obj = Object;
           }
     
    -      ~ScopedObjectAccess() { if (!error) obj->unlock(); }
    +      ~ScopedObjectAccess() { if (error IS ERR::Okay) obj->unlock(); }
     
    -      bool granted() { return error == ERR_Okay; }
    +      bool granted() { return error == ERR::Okay; }
     
           void release() {
    -         if (!error) {
    +         if (error IS ERR::Okay) {
                 obj->unlock();
    -            error = ERR_NotLocked;
    +            error = ERR::NotLocked;
              }
           }
     };
    diff --git a/src/core/defs/core.fdl b/src/core/defs/core.fdl
    index d05b18bdd..9051f8969 100644
    --- a/src/core/defs/core.fdl
    +++ b/src/core/defs/core.fdl
    @@ -1,8 +1,8 @@
     --$FLUID:Include
     
    -module({ name="Core", copyright="Paul Manias 1996-2023" }, function()
    +module({ name="Core", copyright="Paul Manias 1996-2024" }, function()
       c_include("", "")
    -  cpp_include("", "", "", "", "", "", "")
    +  cpp_include("", "", "", "", "", "", "", "")
     
       platform("Windows", function()
          enum("NETMSG", {}, "START", "END")
    @@ -11,6 +11,10 @@ module({ name="Core", copyright="Paul Manias 1996-2023" }, function()
       privateNames({ "ScriptArg", "CoreBase", "RootModule" })
     
       priority([[
    +#if defined(_DEBUG) && defined(__linux__)
    + #include 
    +#endif
    +
     #ifndef DEFINE_ENUM_FLAG_OPERATORS
     template  struct _ENUM_FLAG_INTEGER_FOR_SIZE;
     template <> struct _ENUM_FLAG_INTEGER_FOR_SIZE<1> { typedef BYTE type; };
    @@ -45,7 +49,7 @@ inline ENUMTYPE &operator &= (ENUMTYPE &a, ENUMTYPE b) { return (ENUMTYPE &)(((_
       flags("MSF", { comment="Message flags." },
          "WAIT: Wait before inserting the message if the queue is at maximum capacity.",
          "UPDATE: If the Type parameter matches a message already inside the queue, the data for that message will be deleted, then the new message will be added to the end of the queue.",
    -     "NO_DUPLICATE: If the Type parameter matches a message already inside the queue, the new message will not be added and the function will immediately return with ERR_Okay.",
    +     "NO_DUPLICATE: If the Type parameter matches a message already inside the queue, the new message will not be added and the function will immediately return with ERR::Okay.",
          "ADD: The default behaviour - this will add the message to the end of the queue.",
          "ADDRESS: Internal flag that changes the behaviour of the input parameters so that queues can be processed by address rather than ID.",
          "MESSAGE_ID: The Type parameter refers to a unique message ID rather than a message type for this call.")
    @@ -77,8 +81,8 @@ inline ENUMTYPE &operator &= (ENUMTYPE &a, ENUMTYPE b) { return (ENUMTYPE &)(((_
         "PIPE: Enable the output pipe to the launched process so that it can read data.")
     
       hash("AHASH", "0x%s",
    -    "ACTIVATE",     "ACCESSOBJECT",  "CLEAR",     "FREEWARNING", "COPYDATA",
    -    "DATAFEED",     "DEACTIVATE",    "DRAW",      "FLUSH",       "FOCUS",        "FREE",         "RELEASEOBJECT",
    +    "ACTIVATE",     "CLEAR",         "FREEWARNING", "COPYDATA",
    +    "DATAFEED",     "DEACTIVATE",    "DRAW",      "FLUSH",       "FOCUS",        "FREE",
         "GETVAR",       "DRAGDROP",      "HIDE",      "INIT",        "LOCK",         "LOSTFOCUS",    "MOVE",
         "MOVETOBACK",   "MOVETOFRONT",   "NEWCHILD",  "NEWOWNER",    "NEWOBJECT",    "REDO",         "QUERY",
         "READ",         "RENAME",        "RESET",     "RESIZE",      "SAVEIMAGE",    "SAVETOOBJECT", "SCROLL",
    @@ -95,7 +99,7 @@ inline ENUMTYPE &operator &= (ENUMTYPE &a, ENUMTYPE b) { return (ENUMTYPE &)(((_
     
       flags("MTF", { comment="MoveToPoint flags" }, "X", "Y", "Z", "ANIM", "RELATIVE")
     
    -  flags("VLF", { comment="VlogF flags" }, "BRANCH", "ERROR", "WARNING", "CRITICAL", "INFO", "API", "EXTAPI", "DEBUG", "TRACE", "FUNCTION")
    +  flags("VLF", { comment="VlogF flags" }, "BRANCH", "ERROR", "WARNING", "CRITICAL", "INFO", "API", "DETAIL", "TRACE", "FUNCTION")
     
       flags("MOF", { comment="Module flags" },
         "LINK_LIBRARY: Module refers to a symbolic link library (e.g. libz DLL or SO)",
    @@ -130,7 +134,7 @@ inline ENUMTYPE &operator &= (ENUMTYPE &a, ENUMTYPE b) { return (ENUMTYPE &)(((_
     
       flags("RSF", { comment="Flags for ResolvePath()"},
         "NO_FILE_CHECK: Do not test for the existence of the targeted file or folder during the resolution process.",
    -    "CHECK_VIRTUAL: If the volume referenced by Path is traced to another volume that is reserved by a virtual file system driver, ERR_VirtualVolume is returned. The volume is still resolved as far as possible and the resulting path will be returned by this function.",
    +    "CHECK_VIRTUAL: If the volume referenced by Path is traced to another volume that is reserved by a virtual file system driver, ERR::VirtualVolume is returned. The volume is still resolved as far as possible and the resulting path will be returned by this function.",
         "APPROXIMATE: Ignores file extensions for the purpose of file name matching.",
         "NO_DEEP_SCAN: Do not perform more than one iteration when resolving the source file path.",
         "PATH: Use the PATH environment variable to resolve the file name in the Path parameter.",
    @@ -221,7 +225,7 @@ inline ENUMTYPE &operator &= (ENUMTYPE &a, ENUMTYPE b) { return (ENUMTYPE &)(((_
         "FILE: The path refers to a file.")
     
       flags("LDF", { comment="Flags for LoadFile()" },
    -    "CHECK_EXISTS: Limits the routine to checking the file cache for the existence of the file.  If found, the relevant cache entry is returned. The open count is not incremented by this action (it is therefore unnecessary to follow-up with a call to UnloadFile()).  If no up-to-date cache entry is available, ERR_Search is returned.")
    +    "CHECK_EXISTS: Limits the routine to checking the file cache for the existence of the file.  If found, the relevant cache entry is returned. The open count is not incremented by this action (it is therefore unnecessary to follow-up with a call to UnloadFile()).  If no up-to-date cache entry is available, ERR::Search is returned.")
     
       enum("FBK", { type="int", start=1, comment="Flags for file feedback." },
         "MOVE_FILE: A file is to be, or has been moved.",
    @@ -279,7 +283,7 @@ inline ENUMTYPE &operator &= (ENUMTYPE &a, ENUMTYPE b) { return (ENUMTYPE &)(((_
         "RECLASSED: The object switched from the base-class to a sub-class during initialisation.",
         "MESSAGE: Action has been called against the object through the message system (managed by ProcessMessages()).",
         "SIGNALLED: The object has been signalled and is awaiting processing.",
    -    { UNIQUE = "0x40000000: Use to allocate an object that has a guaranteed unique name.  This will prevent code from shadowing any object that exists with the same name, which can be imperative when creating shared objects.  If it is discovered that an identically named object exists, NewObject() will return ERR_ObjectExists.  This flag works in conjunction with the Name argument.",
    +    { UNIQUE = "0x40000000: Use to allocate an object that has a guaranteed unique name.  This will prevent code from shadowing any object that exists with the same name, which can be imperative when creating shared objects.  If it is discovered that an identically named object exists, NewObject() will return ERR::ObjectExists.  This flag works in conjunction with the Name argument.",
           NAME   = "0x80000000: Use the Name parameter to name the created object.  This flag is not required if using NF_UNIQUE.",
           PRIVATE = 0
         }
    @@ -527,6 +531,8 @@ inline ENUMTYPE &operator &= (ENUMTYPE &a, ENUMTYPE b) { return (ENUMTYPE &)(((_
     #endif
     
     typedef const std::vector> STRUCTS;
    +typedef std::map KEYVALUE;
    +typedef std::map CONST_KEYVALUE;
     
     #ifndef STRINGIFY
     #define STRINGIFY(x) #x
    @@ -537,7 +543,7 @@ typedef const std::vector> STRUCTS;
     
     #ifdef PARASOL_STATIC
     __export void CloseCore(void);
    -__export ERROR OpenCore(struct OpenInfo *, struct CoreBase **);
    +__export ERR OpenCore(struct OpenInfo *, struct CoreBase **);
     #else
     __export struct ModHeader ModHeader;
     #endif
    @@ -634,12 +640,12 @@ struct OpenInfo {
        CSTRING SystemPath;      // OPF::SYSTEM_PATH
        CSTRING ModulePath;      // OPF::MODULE_PATH
        CSTRING RootPath;        // OPF::ROOT_PATH
    -   struct OpenTag *Options; // OPF::OPTIONS Typecast to va_list (defined in stdarg.h)
    +   OpenTag *Options;        // OPF::OPTIONS Typecast to va_list (defined in stdarg.h)
        OPF     Flags;           // OPF::flags need to be set for fields that have been defined in this structure.
        LONG    MaxDepth;        // OPF::MAX_DEPTH
        LONG    Detail;          // OPF::DETAIL
        LONG    ArgCount;        // OPF::ARGS
    -   ERROR   Error;           // OPF::ERROR
    +   ERR     Error;           // OPF::ERROR
     };
     
     // Flags for defining fields, methods, actions and functions.  CLASSDEF's can only be used in field definitions for
    @@ -689,7 +695,7 @@ struct OpenInfo {
     #define FDF_INTEGRAL    (FD_POINTER|FD_INTEGRAL) // Field refers to an integral object
     #define FDF_STRING      (FD_POINTER|FD_STRING)   // Field points to a string.  NB: Ideally want to remove the FD_POINTER as it should be redundant
     #define FDF_STR         (FDF_STRING)
    -#define FDF_PERCENTAGE  FD_PERCENTAGE
    +#define FDF_SCALED      FD_SCALED
     #define FDF_FLAGS       FD_FLAGS                // Field contains flags
     #define FDF_ALLOC       FD_ALLOC                // Field is a dynamic allocation - either a memory block or object
     #define FDF_LOOKUP      FD_LOOKUP               // Lookup names for values in this field
    @@ -719,13 +725,11 @@ struct OpenInfo {
     #define TLARGE    0x0400000000000000LL
     #define TFUNCTION 0x0200000000000000LL
     #define TSTR      0x0080000000000000LL
    -#define TRELATIVE 0x0020000000000000LL
     #define TARRAY    0x0000100000000000LL
    -#define TPERCENT  TRELATIVE
    +#define TSCALE    0x0020000000000000LL
     #define TAGEND    0LL
     #define TAGDIVERT -1LL
     #define TSTRING   TSTR
    -#define TREL      TRELATIVE
     
     #define nextutf8(str) if (*(str)) for (++(str); (*(str) & 0xc0) IS 0x80; (str)++);
     
    @@ -742,22 +746,36 @@ struct FieldValue {
           APTR    Pointer;
           CPTR    CPointer;
           DOUBLE  Double;
    -      PERCENT Percent;
    +      SCALE   Percent;
           LARGE   Large;
           LONG    Long;
        };
     
        //std::string not included as not compatible with constexpr
    -   constexpr FieldValue(ULONG pFID, CSTRING pValue) : FieldID(pFID), Type(FD_STRING), String(pValue) { };
    -   constexpr FieldValue(ULONG pFID, LONG pValue)    : FieldID(pFID), Type(FD_LONG), Long(pValue) { };
    -   constexpr FieldValue(ULONG pFID, LARGE pValue)   : FieldID(pFID), Type(FD_LARGE), Large(pValue) { };
    -   constexpr FieldValue(ULONG pFID, DOUBLE pValue)  : FieldID(pFID), Type(FD_DOUBLE), Double(pValue) { };
    -   constexpr FieldValue(ULONG pFID, PERCENT pValue) : FieldID(pFID), Type(FD_DOUBLE|FD_PERCENTAGE), Percent(pValue) { };
    -   constexpr FieldValue(ULONG pFID, APTR pValue)    : FieldID(pFID), Type(FD_POINTER), Pointer(pValue) { };
    -   constexpr FieldValue(ULONG pFID, CPTR pValue)    : FieldID(pFID), Type(FD_POINTER), CPointer(pValue) { };
    +   constexpr FieldValue(ULONG pFID, CSTRING pValue)   : FieldID(pFID), Type(FD_STRING), String(pValue) { };
    +   constexpr FieldValue(ULONG pFID, LONG pValue)      : FieldID(pFID), Type(FD_LONG), Long(pValue) { };
    +   constexpr FieldValue(ULONG pFID, LARGE pValue)     : FieldID(pFID), Type(FD_LARGE), Large(pValue) { };
    +   constexpr FieldValue(ULONG pFID, DOUBLE pValue)    : FieldID(pFID), Type(FD_DOUBLE), Double(pValue) { };
    +   constexpr FieldValue(ULONG pFID, SCALE pValue)     : FieldID(pFID), Type(FD_DOUBLE|FD_SCALED), Percent(pValue) { };
    +   constexpr FieldValue(ULONG pFID, const FUNCTION &pValue) : FieldID(pFID), Type(FDF_FUNCTIONPTR), CPointer(&pValue) { };
    +   constexpr FieldValue(ULONG pFID, const FUNCTION *pValue) : FieldID(pFID), Type(FDF_FUNCTIONPTR), CPointer(pValue) { };
    +   constexpr FieldValue(ULONG pFID, APTR pValue)      : FieldID(pFID), Type(FD_POINTER), Pointer(pValue) { };
    +   constexpr FieldValue(ULONG pFID, CPTR pValue)      : FieldID(pFID), Type(FD_POINTER), CPointer(pValue) { };
        constexpr FieldValue(ULONG pFID, CPTR pValue, LONG pCustom) : FieldID(pFID), Type(pCustom), CPointer(pValue) { };
     };
     
    +
    +class FloatRect {
    +   public:
    +   DOUBLE X;    // Left-most coordinate
    +   DOUBLE Y;     // Top coordinate
    +   DOUBLE Width;   // Right-most coordinate
    +   DOUBLE Height;  // Bottom coordinate
    +   FloatRect() { }
    +   FloatRect(DOUBLE Value) : X(Value), Y(Value), Width(Value), Height(Value) { }
    +   FloatRect(DOUBLE pX, DOUBLE pY, DOUBLE pWidth, DOUBLE pHeight) : X(pX), Y(pY), Width(pWidth), Height(pHeight) { }
    +};
    +
     }
     
     #include  // memset()
    @@ -814,10 +832,10 @@ struct FieldValue {
       [[
        STRUCTS *StructDefs;
        class RootModule *Root;
    -   ModHeader(ERROR (*pInit)(OBJECTPTR, struct CoreBase *),
    +   ModHeader(ERR (*pInit)(OBJECTPTR, struct CoreBase *),
           void  (*pClose)(OBJECTPTR),
    -      ERROR (*pOpen)(OBJECTPTR),
    -      ERROR (*pExpunge)(void),
    +      ERR (*pOpen)(OBJECTPTR),
    +      ERR (*pExpunge)(void),
           CSTRING pDef,
           STRUCTS *pStructs,
           CSTRING pName) {
    @@ -836,7 +854,7 @@ struct FieldValue {
       struct("FieldArray", { comment="Used to construct class blueprints for the MetaClass." }, [[
         cstr   Name      # The name of the field, e.g. "Width"
         ptr    GetField  # void GetField(*Object, APTR Result);
    -    ptr    SetField  # ERROR SetField(*Object, APTR Value);
    +    ptr    SetField  # ERR SetField(*Object, APTR Value);
         maxint Arg       # Can be a pointer or an integer value
         uint   Flags     # Special flags that describe the field
       ]],
    @@ -887,7 +905,7 @@ struct FieldValue {
     
       struct("MethodEntry", { restrict="c" }, [[
         int  MethodID   # Unique method identifier
    -    ptr  Routine    # The method entry point, defined as ERROR (*Routine)(OBJECTPTR, APTR);
    +    ptr  Routine    # The method entry point, defined as ERR (*Routine)(OBJECTPTR, APTR);
         cstr Name       # Name of the method
         cstruct(*FunctionField) Args  # List of parameters accepted by the method
         int  Size       # Total byte-size of all accepted parameters when they are assembled as a C structure.
    @@ -1178,7 +1196,7 @@ template  inline MEMORYID GetMemoryID(T &&A) {
        return ((MEMORYID *)A)[-2];
     }
     
    -inline ERROR DeregisterFD(HOSTHANDLE Handle) {
    +inline ERR DeregisterFD(HOSTHANDLE Handle) {
        return RegisterFD(Handle, RFD::REMOVE|RFD::READ|RFD::WRITE|RFD::EXCEPT|RFD::ALWAYS_CALL, 0, 0);
     }
     
    @@ -1190,7 +1208,7 @@ inline APTR GetResourcePtr(RES ID) { return (APTR)(MAXINT)GetResource(ID); }
     inline CSTRING to_cstring(const std::string &A) { return A.c_str(); }
     constexpr inline CSTRING to_cstring(CSTRING A) { return A; }
     
    -template  inline ERROR StrMatch(T &&A, U &&B) {
    +template  inline ERR StrMatch(T &&A, U &&B) {
        return StrCompare(to_cstring(A), to_cstring(B), 0, STR::MATCH_LEN);
     }
     
    @@ -1214,38 +1232,51 @@ template  inline LONG StrCopy(T &&Source, STRING Dest, LONG Length = 0x
     }
     
     #ifndef PRV_CORE_DATA
    +// These overloaded functions can't be used in the Core as they will confuse the compiler in key areas.
    +
    +inline ERR SubscribeAction(OBJECTPTR Object, LONG Action, FUNCTION Callback) {
    +   return SubscribeAction(Object,Action,&Callback);
    +}
     
    -inline ERROR ReleaseMemory(const void *Address) {
    -   if (!Address) return ERR_NullArgs;
    +inline ERR SubscribeEvent(LARGE Event, FUNCTION Callback, APTR Custom, APTR Handle) {
    +   return SubscribeEvent(Event,&Callback,Custom,Handle);
    +}
    +
    +inline ERR SubscribeTimer(DOUBLE Interval, FUNCTION Callback, APTR Subscription) {
    +   return SubscribeTimer(Interval,&Callback,Subscription);
    +}
    +
    +inline ERR ReleaseMemory(const void *Address) {
    +   if (!Address) return ERR::NullArgs;
        return ReleaseMemory(((MEMORYID *)Address)[-2]);
     }
     
    -inline ERROR FreeResource(const void *Address) {
    -   if (!Address) return ERR_NullArgs;
    +inline ERR FreeResource(const void *Address) {
    +   if (!Address) return ERR::NullArgs;
        return FreeResource(((LONG *)Address)[-2]);
     }
     
    -inline ERROR AllocMemory(LONG Size, MEM Flags, APTR Address) {
    +inline ERR AllocMemory(LONG Size, MEM Flags, APTR Address) {
        return AllocMemory(Size, Flags, (APTR *)Address, NULL);
     }
     
    -template inline ERROR NewObject(LARGE ClassID, T **Result) {
    +template inline ERR NewObject(LARGE ClassID, T **Result) {
        return NewObject(ClassID, NF::NIL, Result);
     }
     
    -inline ERROR MemoryIDInfo(MEMORYID ID, struct MemInfo * MemInfo) {
    +inline ERR MemoryIDInfo(MEMORYID ID, struct MemInfo * MemInfo) {
        return MemoryIDInfo(ID,MemInfo,sizeof(struct MemInfo));
     }
     
    -inline ERROR MemoryPtrInfo(APTR Address, struct MemInfo * MemInfo) {
    +inline ERR MemoryPtrInfo(APTR Address, struct MemInfo * MemInfo) {
        return MemoryPtrInfo(Address,MemInfo,sizeof(struct MemInfo));
     }
     
    -inline ERROR QueueAction(LONG Action, OBJECTID ObjectID) {
    +inline ERR QueueAction(LONG Action, OBJECTID ObjectID) {
        return QueueAction(Action, ObjectID, NULL);
     }
     
    -template  inline ERROR StrCompare(T &&A, U &&B, LONG Length = 0, STR Flags = STR::NIL) {
    +template  inline ERR StrCompare(T &&A, U &&B, LONG Length = 0, STR Flags = STR::NIL) {
        return StrCompare(to_cstring(A), to_cstring(B), Length, Flags);
     }
     
    @@ -1253,18 +1284,23 @@ inline ULONG StrHash(const std::string Value) {
        return StrHash(Value.c_str(), FALSE);
     }
     
    -template  inline ERROR SetArray(OBJECTPTR Object, FIELD FieldID, pf::vector Array)
    +template  inline ERR SetArray(OBJECTPTR Object, FIELD FieldID, pf::vector &Array)
     {
        return SetArray(Object, FieldID, Array.data(), Array.size());
     }
     
    -template  inline ERROR SetArray(OBJECTPTR Object, FIELD FieldID, std::vector Array)
    +template  inline ERR SetArray(OBJECTPTR Object, FIELD FieldID, std::vector &Array)
     {
        return SetArray(Object, FieldID, Array.data(), Array.size());
     }
    +
    +template  inline ERR SetArray(OBJECTPTR Object, FIELD FieldID, std::array Array)
    +{
    +   return SetArray(Object, FieldID, Array.data(), SIZE);
    +}
     #endif
     
    -typedef std::map ConfigKeys;
    +typedef KEYVALUE ConfigKeys;
     typedef std::pair ConfigGroup;
     typedef std::vector ConfigGroups;
     
    @@ -1305,7 +1341,7 @@ inline void CopyMemory(const void *Src, APTR Dest, LONG Length)
     
        auto len = LONG(strlen(String));
        STRING newstr;
    -   if (!AllocMemory(len+1, MEM::STRING, (APTR *)&newstr, NULL)) {
    +   if (AllocMemory(len+1, MEM::STRING, (APTR *)&newstr, NULL) IS ERR::Okay) {
           CopyMemory(String, newstr, len+1);
           return newstr;
        }
    @@ -1352,10 +1388,10 @@ inline LONG IntToStr(LARGE Integer, STRING String, LONG StringSize) {
        return len;
     }
     
    -inline ERROR ClearMemory(APTR Memory, LONG Length) {
    -   if (!Memory) return ERR_NullArgs;
    +inline ERR ClearMemory(APTR Memory, LONG Length) {
    +   if (!Memory) return ERR::NullArgs;
        memset(Memory, 0, Length); // memset() is assumed to be optimised by the compiler.
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     namespace pf {
    @@ -1436,10 +1472,10 @@ class Log { // C++ wrapper for Parasol's log functionality
              if ((Flags & VLF::BRANCH) != VLF::NIL) branches++;
           }
     
    -      void extmsg(CSTRING Message, ...) __attribute__((format(printf, 2, 3))) { // Extended API message
    +      void detail(CSTRING Message, ...) __attribute__((format(printf, 2, 3))) { // Detailed API message
              va_list arg;
              va_start(arg, Message);
    -         VLogF(VLF::EXTAPI, header, Message, arg);
    +         VLogF(VLF::DETAIL, header, Message, arg);
              va_end(arg);
           }
     
    @@ -1464,13 +1500,6 @@ class Log { // C++ wrapper for Parasol's log functionality
              va_end(arg);
           }
     
    -      void debug(CSTRING Message, ...) __attribute__((format(printf, 2, 3))) {
    -         va_list arg;
    -         va_start(arg, Message);
    -         VLogF(VLF::DEBUG, header, Message, arg);
    -         va_end(arg);
    -      }
    -
           void function(CSTRING Message, ...) __attribute__((format(printf, 2, 3))) { // Equivalent to branch() but without a new branch being created
              va_list arg;
              va_start(arg, Message);
    @@ -1478,12 +1507,12 @@ class Log { // C++ wrapper for Parasol's log functionality
              va_end(arg);
           }
     
    -      ERROR error(ERROR Code) { // Technically a warning
    +      ERR error(ERR Code) { // Technically a warning
              FuncError(header, Code);
              return Code;
           }
     
    -      ERROR warning(ERROR Code) {
    +      ERR warning(ERR Code) {
              FuncError(header, Code);
              return Code;
           }
    @@ -1505,10 +1534,44 @@ class Log { // C++ wrapper for Parasol's log functionality
                 va_end(arg);
              #endif
           }
    +
    +      ERR traceWarning(ERR Code) {
    +         #ifdef _DEBUG
    +            FuncError(header, Code);
    +         #endif
    +         return Code;
    +      }
    +};
    +
    +class LogLevel {
    +   private:
    +      LONG level;
    +   public:
    +      LogLevel(LONG Level) : level(Level) {
    +         AdjustLogLevel(Level);
    +      }
    +
    +      ~LogLevel() {
    +         AdjustLogLevel(-level);
    +      }
     };
     
     } // namespace
     
    +//********************************************************************************************************************
    +// Refer to BaseClass->get() to see what this is about...
    +
    +template  inline LARGE FIELD_TAG()     { return 0; }
    +template <> inline LARGE FIELD_TAG()    { return TDOUBLE; }
    +template <> inline LARGE FIELD_TAG()      { return TLONG; }
    +template <> inline LARGE FIELD_TAG()     { return TFLOAT; }
    +template <> inline LARGE FIELD_TAG() { return TPTR; }
    +template <> inline LARGE FIELD_TAG()      { return TPTR; }
    +template <> inline LARGE FIELD_TAG()     { return TLARGE; }
    +template <> inline LARGE FIELD_TAG()   { return TSTRING; }
    +template <> inline LARGE FIELD_TAG()    { return TSTRING; }
    +template <> inline LARGE FIELD_TAG()     { return TDOUBLE|TSCALE; }
    +
     //********************************************************************************************************************
     // Header used for all objects.
     
    @@ -1518,10 +1581,11 @@ struct BaseClass { // Must be 64-bit aligned
           class extMetaClass *ExtClass; // [Private] Internal version of the class pointer
        };
        APTR     ChildPrivate;        // Address for the ChildPrivate structure, if allocated
    -   APTR     CreatorMeta;         // The creator (via NewObject) is permitted to store a custom data pointer here.
    +   APTR     CreatorMeta;         // The creator of the object is permitted to store a custom data pointer here.
    +   struct BaseClass *Owner;      // The owner of this object
        std::atomic_uint64_t NotifyFlags; // Action subscription flags - space for 64 actions max
    +   LONG     Dummy;               // For 64-bit alignment
        OBJECTID UID;                 // Unique object identifier
    -   OBJECTID OwnerID;             // The owner of this object
        NF       Flags;               // Object flags
        volatile LONG  ThreadID;      // Managed by locking functions
        char Name[MAX_NAME_LEN];      // The name of the object (optional)
    @@ -1534,13 +1598,13 @@ struct BaseClass { // Must be 64-bit aligned
        inline bool initialised() { return (Flags & NF::INITIALISED) != NF::NIL; }
        inline bool defined(NF pFlags) { return (Flags & pFlags) != NF::NIL; }
        inline bool isSubClass();
    -   inline OBJECTID ownerID() { return OwnerID; }
    +   inline OBJECTID ownerID() { return Owner ? Owner->UID : 0; }
        inline NF flags() { return Flags; }
     
        CSTRING className();
     
        inline bool collecting() { // Is object being freed or marked for collection?
    -      return (Flags & (NF::FREE|NF::COLLECT)) != NF::NIL;
    +      return (Flags & (NF::FREE|NF::COLLECT|NF::FREE_ON_UNLOCK)) != NF::NIL;
        }
     
        inline bool terminating() { // Is object currently being freed?
    @@ -1549,13 +1613,13 @@ struct BaseClass { // Must be 64-bit aligned
     
        // Use lock() to quickly obtain an object lock without a call to LockObject()
     
    -   inline ERROR lock() {
    +   inline ERR lock() {
           if (++Queue IS 1) {
              ThreadID = pf::_get_thread_id();
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
           else {
    -         if (ThreadID IS pf::_get_thread_id()) return ERR_Okay; // If this is for the same thread then it's a nested lock, so there's no issue.
    +         if (ThreadID IS pf::_get_thread_id()) return ERR::Okay; // If this is for the same thread then it's a nested lock, so there's no issue.
              --Queue; // Restore the lock count
              return LockObject(this, -1); // Can fail if object is marked for deletion.
           }
    @@ -1568,54 +1632,64 @@ struct BaseClass { // Must be 64-bit aligned
        }
     
        inline bool hasOwner(OBJECTID ID) { // Return true if ID has ownership.
    -      auto oid = this->OwnerID;
    -      while ((oid) and (oid != ID)) oid = GetOwnerID(oid);
    -      return oid ? true : false;
    +      auto obj = this->Owner;
    +      while ((obj) and (obj->UID != ID)) obj = obj->Owner;
    +      return obj ? true : false;
        }
     
    -   inline ERROR set(ULONG FieldID, int Value)             { return SetField(this, (FIELD)FieldID|TLONG, Value); }
    -   inline ERROR set(ULONG FieldID, unsigned int Value)    { return SetField(this, (FIELD)FieldID|TLONG, Value); }
    -   inline ERROR set(ULONG FieldID, LARGE Value)           { return SetField(this, (FIELD)FieldID|TLARGE, Value); }
    -   inline ERROR set(ULONG FieldID, DOUBLE Value)          { return SetField(this, (FIELD)FieldID|TDOUBLE, Value); }
    -   inline ERROR set(ULONG FieldID, const FUNCTION *Value) { return SetField(this, (FIELD)FieldID|TFUNCTION, Value); }
    -   inline ERROR set(ULONG FieldID, const char *Value)     { return SetField(this, (FIELD)FieldID|TSTRING, Value); }
    -   inline ERROR set(ULONG FieldID, const unsigned char *Value) { return SetField(this, (FIELD)FieldID|TSTRING, Value); }
    -   inline ERROR set(ULONG FieldID, const std::string &Value)   { return SetField(this, (FIELD)FieldID|TSTRING, Value.c_str()); }
    -   inline ERROR set(ULONG FieldID, const Variable *Value)      { return SetField(this, (FIELD)FieldID|TVAR, Value); }
    +   inline ERR set(ULONG FieldID, int Value)             { return SetField(this, (FIELD)FieldID|TLONG, Value); }
    +   inline ERR set(ULONG FieldID, unsigned int Value)    { return SetField(this, (FIELD)FieldID|TLONG, Value); }
    +   inline ERR set(ULONG FieldID, LARGE Value)           { return SetField(this, (FIELD)FieldID|TLARGE, Value); }
    +   inline ERR set(ULONG FieldID, DOUBLE Value)          { return SetField(this, (FIELD)FieldID|TDOUBLE, Value); }
    +   inline ERR set(ULONG FieldID, const FUNCTION *Value) { return SetField(this, (FIELD)FieldID|TFUNCTION, Value); }
    +   inline ERR set(ULONG FieldID, const char *Value)     { return SetField(this, (FIELD)FieldID|TSTRING, Value); }
    +   inline ERR set(ULONG FieldID, const unsigned char *Value) { return SetField(this, (FIELD)FieldID|TSTRING, Value); }
    +   inline ERR set(ULONG FieldID, const std::string &Value)   { return SetField(this, (FIELD)FieldID|TSTRING, Value.c_str()); }
    +   inline ERR set(ULONG FieldID, const Variable *Value)      { return SetField(this, (FIELD)FieldID|TVAR, Value); }
        // Works both for regular data pointers and function pointers if field is defined correctly.
    -   inline ERROR set(ULONG FieldID, const void *Value) { return SetField(this, (FIELD)FieldID|TPTR, Value); }
    -
    -   inline ERROR setPercentage(ULONG FieldID, DOUBLE Value) { return SetField(this, (FIELD)FieldID|TDOUBLE|TPERCENT, Value); }
    -
    -   inline ERROR get(ULONG FieldID, LONG *Value)     { return GetField(this, (FIELD)FieldID|TLONG, Value); }
    -   inline ERROR get(ULONG FieldID, LARGE *Value)    { return GetField(this, (FIELD)FieldID|TLARGE, Value); }
    -   inline ERROR get(ULONG FieldID, DOUBLE *Value)   { return GetField(this, (FIELD)FieldID|TDOUBLE, Value); }
    -   inline ERROR get(ULONG FieldID, STRING *Value)   { return GetField(this, (FIELD)FieldID|TSTRING, Value); }
    -   inline ERROR get(ULONG FieldID, CSTRING *Value)  { return GetField(this, (FIELD)FieldID|TSTRING, Value); }
    -   inline ERROR get(ULONG FieldID, Variable *Value) { return GetField(this, (FIELD)FieldID|TVAR, Value); }
    -   inline ERROR getPtr(ULONG FieldID, APTR Value)   { return GetField(this, (FIELD)FieldID|TPTR, Value); }
    -   inline ERROR getPercentage(ULONG FieldID, DOUBLE *Value) { return GetField(this, (FIELD)FieldID|TDOUBLE|TPERCENT, Value); }
    +   inline ERR set(ULONG FieldID, const void *Value) { return SetField(this, (FIELD)FieldID|TPTR, Value); }
    +
    +   inline ERR setScale(ULONG FieldID, DOUBLE Value) { return SetField(this, (FIELD)FieldID|TDOUBLE|TSCALE, Value); }
    +
    +   // There are two mechanisms for retrieving object values; the first allows the value to be retrieved with an error
    +   // code and the value itself; the second ignores the error code and returns a value that could potentially be invalid.
    +
    +   inline ERR get(ULONG FieldID, LONG *Value)     { return GetField(this, (FIELD)FieldID|TLONG, Value); }
    +   inline ERR get(ULONG FieldID, LARGE *Value)    { return GetField(this, (FIELD)FieldID|TLARGE, Value); }
    +   inline ERR get(ULONG FieldID, DOUBLE *Value)   { return GetField(this, (FIELD)FieldID|TDOUBLE, Value); }
    +   inline ERR get(ULONG FieldID, STRING *Value)   { return GetField(this, (FIELD)FieldID|TSTRING, Value); }
    +   inline ERR get(ULONG FieldID, CSTRING *Value)  { return GetField(this, (FIELD)FieldID|TSTRING, Value); }
    +   inline ERR get(ULONG FieldID, Variable *Value) { return GetField(this, (FIELD)FieldID|TVAR, Value); }
    +   inline ERR getPtr(ULONG FieldID, APTR Value)   { return GetField(this, (FIELD)FieldID|TPTR, Value); }
    +   inline ERR getScale(ULONG FieldID, DOUBLE *Value) { return GetField(this, (FIELD)FieldID|TDOUBLE|TSCALE, Value); }
    +
    +   template  inline T get(ULONG FieldID) { // Validity of the result is not guaranteed
    +      T val;
    +      GetField(this, (FIELD)FieldID|FIELD_TAG(), &val);
    +      return val;
    +   };
     
    -   template  ERROR setFields(Args&&... pFields) {
    +   template  ERR setFields(Args&&... pFields) {
           pf::Log log("setFields");
     
           lock();
     
           std::initializer_list Fields = { std::forward(pFields)... };
     
    +      auto ctx = CurrentContext();
           for (auto &f : Fields) {
              OBJECTPTR target;
              if (auto field = FindField(this, f.FieldID, &target)) {
    -            if ((!(field->Flags & (FD_INIT|FD_WRITE))) and (CurrentContext() != target)) {
    -               log.warning("Field \"%s\" of class %s is not writeable.", field->Name, className());
    +            if ((!(field->Flags & (FD_INIT|FD_WRITE))) and (ctx != target)) {
    +               log.warning("%s.%s is immutable.", className(), field->Name);
                 }
    -            else if ((field->Flags & FD_INIT) and (target->initialised()) and (CurrentContext() != target)) {
    -               log.warning("Field \"%s\" of class %s is init-only.", field->Name, className());
    +            else if ((field->Flags & FD_INIT) and (target->initialised()) and (ctx != target)) {
    +               log.warning("%s.%s is init-only.", className(), field->Name);
                 }
                 else {
                    if (target != this) target->lock();
     
    -               ERROR error;
    +               ERR error;
                    if (f.Type & (FD_POINTER|FD_STRING|FD_ARRAY|FD_FUNCTION|FD_VARIABLE)) {
                       error = field->WriteValue(target, field, f.Type, f.Pointer, 0);
                    }
    @@ -1631,22 +1705,21 @@ struct BaseClass { // Must be 64-bit aligned
     
                    // NB: NoSupport is considered a 'soft' error that does not warrant failure.
     
    -               if ((error) and (error != ERR_NoSupport)) {
    -                  log.warning("(%s:%d) Failed to set field %s (error #%d).", target->className(), target->UID, field->Name, error);
    +               if ((error != ERR::Okay) and (error != ERR::NoSupport)) {
    +                  log.warning("%s.%s: %s", target->className(), field->Name, GetErrorMsg(error));
                       unlock();
                       return error;
                    }
                 }
              }
              else {
    -            log.warning("Field %s is not supported by class %s.", FieldName(f.FieldID), className());
                 unlock();
    -            return ERR_UnsupportedField;
    +            return log.warning(ERR::UnsupportedField);
              }
           }
     
           unlock();
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
     
     } __attribute__ ((aligned (8)));
    @@ -1659,9 +1732,10 @@ class Create {
           T *obj;
     
        public:
    -      ERROR error;
    +      ERR error;
     
    -      // Return an unscoped direct object pointer.  NB: Globals are still tracked
    +      // Return an unscoped direct object pointer.  NB: Globals are still tracked to their owner; use untracked() if
    +      // you don't want this.
     
           template  static T * global(Args&&... Fields) {
              pf::Create object = { std::forward(Fields)... };
    @@ -1673,7 +1747,18 @@ class Create {
              else return NULL;
           }
     
    -      // Return an unscoped integral object (suitable for class allocations only).
    +      inline static T * global(const std::initializer_list Fields) {
    +         pf::Create object(Fields);
    +         if (object.ok()) {
    +            auto result = *object;
    +            object.obj = NULL;
    +            return result;
    +         }
    +         else return NULL;
    +      }
    +
    +      // Return an unscoped integral object (suitable for class allocations only).  This marks the object as
    +      // being 'hidden' from the client unless explicitly makes it available.
     
           template  static T * integral(Args&&... Fields) {
              pf::Create object({ std::forward(Fields)... }, NF::INTEGRAL);
    @@ -1681,6 +1766,12 @@ class Create {
              else return NULL;
           }
     
    +      inline static T * integral(const std::initializer_list Fields) {
    +         pf::Create object(Fields, NF::INTEGRAL);
    +         if (object.ok()) return *object;
    +         else return NULL;
    +      }
    +
           // Return an unscoped and untracked object pointer.
     
           template  static T * untracked(Args&&... Fields) {
    @@ -1689,30 +1780,32 @@ class Create {
              else return NULL;
           }
     
    +      inline static T * untracked(const std::initializer_list Fields) {
    +         pf::Create object(Fields, NF::UNTRACKED);
    +         if (object.ok()) return *object;
    +         else return NULL;
    +      }
    +
           // Create a scoped object that is not initialised.
     
    -      Create(NF Flags = NF::NIL) : obj(NULL), error(ERR_NewObject) {
    -         if (!NewObject(T::CLASS_ID, Flags, (BaseClass **)&obj)) {
    -            error = ERR_Okay;
    +      Create(NF Flags = NF::NIL) : obj(NULL), error(ERR::NewObject) {
    +         if (NewObject(T::CLASS_ID, Flags, (BaseClass **)&obj) IS ERR::Okay) {
    +            error = ERR::Okay;
              }
           }
     
           // Create a scoped object that is fully initialised.
     
    -      Create(std::initializer_list Fields, NF Flags = NF::NIL) : obj(NULL), error(ERR_Failed) {
    +      Create(const std::initializer_list Fields, NF Flags = NF::NIL) : obj(NULL), error(ERR::Failed) {
              pf::Log log("CreateObject");
              log.branch(T::CLASS_NAME);
     
    -         if (!NewObject(T::CLASS_ID, NF::SUPPRESS_LOG|Flags, (BaseClass **)&obj)) {
    +         if (NewObject(T::CLASS_ID, NF::SUPPRESS_LOG|Flags, (BaseClass **)&obj) IS ERR::Okay) {
                 for (auto &f : Fields) {
                    OBJECTPTR target;
                    if (auto field = FindField(obj, f.FieldID, &target)) {
    -                  if ((!(field->Flags & (FD_INIT|FD_WRITE))) and (CurrentContext() != target)) {
    -                     error = log.warning(ERR_NoFieldAccess);
    -                     return;
    -                  }
    -                  else if ((field->Flags & FD_INIT) and (target->initialised()) and (CurrentContext() != target)) {
    -                     error = log.warning(ERR_NoFieldAccess);
    +                  if (!(field->Flags & (FD_WRITE|FD_INIT))) {
    +                     error = log.warning(ERR::NoFieldAccess);
                          return;
                       }
                       else {
    @@ -1727,30 +1820,28 @@ class Create {
                          else if (f.Type & FD_LARGE) {
                             error = field->WriteValue(target, field, f.Type, &f.Large, 1);
                          }
    -                     else {
    -                        error = field->WriteValue(target, field, f.Type, &f.Long, 1);
    -                     }
    +                     else error = field->WriteValue(target, field, f.Type, &f.Long, 1);
     
                          target->unlock();
     
                          // NB: NoSupport is considered a 'soft' error that does not warrant failure.
     
    -                     if ((error) and (error != ERR_NoSupport)) return;
    +                     if ((error != ERR::Okay) and (error != ERR::NoSupport)) return;
                       }
                    }
                    else {
    -                  log.warning("Field %s is not supported by class %s.", FieldName(f.FieldID), T::CLASS_NAME);
    -                  error = log.warning(ERR_UnsupportedField);
    +                  log.warning("%s.%s field not supported.", T::CLASS_NAME, FieldName(f.FieldID));
    +                  error = log.warning(ERR::UnsupportedField);
                       return;
                    }
                 }
     
    -            if ((error = InitObject(obj))) {
    +            if ((error = InitObject(obj)) != ERR::Okay) {
                    FreeResource(obj->UID);
                    obj = NULL;
                 }
              }
    -         else error = ERR_NewObject;
    +         else error = ERR::NewObject;
           }
     
           ~Create() {
    @@ -1768,7 +1859,7 @@ class Create {
           T * operator->() { return obj; }; // Promotes underlying methods and fields
           T * & operator*() { return obj; }; // To allow object pointer referencing when calling functions
     
    -      inline bool ok() { return error == ERR_Okay; }
    +      inline bool ok() { return error == ERR::Okay; }
     };
     }
     
    @@ -1805,68 +1896,67 @@ struct acWrite         { CPTR Buffer; LONG Length; LONG Result; };
     
     // Action Macros
     
    -inline ERROR acActivate(OBJECTPTR Object) { return Action(AC_Activate,Object,NULL); }
    -inline ERROR acClear(OBJECTPTR Object) { return Action(AC_Clear,Object,NULL); }
    -inline ERROR acDeactivate(OBJECTPTR Object) { return Action(AC_Deactivate,Object,NULL); }
    -inline ERROR acDisable(OBJECTPTR Object) { return Action(AC_Disable,Object,NULL); }
    -inline ERROR acDraw(OBJECTPTR Object) { return Action(AC_Draw,Object,NULL); }
    -inline ERROR acEnable(OBJECTPTR Object) { return Action(AC_Enable,Object,NULL); }
    -inline ERROR acFlush(OBJECTPTR Object) { return Action(AC_Flush,Object,NULL); }
    -inline ERROR acFocus(OBJECTPTR Object) { return Action(AC_Focus,Object,NULL); }
    -inline ERROR acHide(OBJECTPTR Object) { return Action(AC_Hide,Object,NULL); }
    -inline ERROR acLock(OBJECTPTR Object) { return Action(AC_Lock,Object,NULL); }
    -inline ERROR acLostFocus(OBJECTPTR Object) { return Action(AC_LostFocus,Object,NULL); }
    -inline ERROR acMoveToBack(OBJECTPTR Object) { return Action(AC_MoveToBack,Object,NULL); }
    -inline ERROR acMoveToFront(OBJECTPTR Object) { return Action(AC_MoveToFront,Object,NULL); }
    -inline ERROR acNext(OBJECTPTR Object) { return Action(AC_Next,Object,NULL); }
    -inline ERROR acPrev(OBJECTPTR Object) { return Action(AC_Prev,Object,NULL); }
    -inline ERROR acQuery(OBJECTPTR Object) { return Action(AC_Query,Object,NULL); }
    -inline ERROR acRefresh(OBJECTPTR Object) { return Action(AC_Refresh, Object, NULL); }
    -inline ERROR acReset(OBJECTPTR Object) { return Action(AC_Reset,Object,NULL); }
    -inline ERROR acSaveSettings(OBJECTPTR Object) { return Action(AC_SaveSettings,Object,NULL); }
    -inline ERROR acShow(OBJECTPTR Object) { return Action(AC_Show,Object,NULL); }
    -inline ERROR acSignal(OBJECTPTR Object) { return Action(AC_Signal,Object,NULL); }
    -inline ERROR acSort(OBJECTPTR Object) { return Action(AC_Sort,Object,NULL); }
    -inline ERROR acUnlock(OBJECTPTR Object) { return Action(AC_Unlock,Object,NULL); }
    -
    -inline ERROR acClipboard(OBJECTPTR Object, CLIPMODE Mode) {
    +inline ERR acActivate(OBJECTPTR Object) { return Action(AC_Activate,Object,NULL); }
    +inline ERR acClear(OBJECTPTR Object) { return Action(AC_Clear,Object,NULL); }
    +inline ERR acDeactivate(OBJECTPTR Object) { return Action(AC_Deactivate,Object,NULL); }
    +inline ERR acDisable(OBJECTPTR Object) { return Action(AC_Disable,Object,NULL); }
    +inline ERR acDraw(OBJECTPTR Object) { return Action(AC_Draw,Object,NULL); }
    +inline ERR acEnable(OBJECTPTR Object) { return Action(AC_Enable,Object,NULL); }
    +inline ERR acFlush(OBJECTPTR Object) { return Action(AC_Flush,Object,NULL); }
    +inline ERR acFocus(OBJECTPTR Object) { return Action(AC_Focus,Object,NULL); }
    +inline ERR acHide(OBJECTPTR Object) { return Action(AC_Hide,Object,NULL); }
    +inline ERR acLock(OBJECTPTR Object) { return Action(AC_Lock,Object,NULL); }
    +inline ERR acLostFocus(OBJECTPTR Object) { return Action(AC_LostFocus,Object,NULL); }
    +inline ERR acMoveToBack(OBJECTPTR Object) { return Action(AC_MoveToBack,Object,NULL); }
    +inline ERR acMoveToFront(OBJECTPTR Object) { return Action(AC_MoveToFront,Object,NULL); }
    +inline ERR acNext(OBJECTPTR Object) { return Action(AC_Next,Object,NULL); }
    +inline ERR acPrev(OBJECTPTR Object) { return Action(AC_Prev,Object,NULL); }
    +inline ERR acQuery(OBJECTPTR Object) { return Action(AC_Query,Object,NULL); }
    +inline ERR acRefresh(OBJECTPTR Object) { return Action(AC_Refresh, Object, NULL); }
    +inline ERR acReset(OBJECTPTR Object) { return Action(AC_Reset,Object,NULL); }
    +inline ERR acSaveSettings(OBJECTPTR Object) { return Action(AC_SaveSettings,Object,NULL); }
    +inline ERR acShow(OBJECTPTR Object) { return Action(AC_Show,Object,NULL); }
    +inline ERR acSignal(OBJECTPTR Object) { return Action(AC_Signal,Object,NULL); }
    +inline ERR acSort(OBJECTPTR Object) { return Action(AC_Sort,Object,NULL); }
    +inline ERR acUnlock(OBJECTPTR Object) { return Action(AC_Unlock,Object,NULL); }
    +
    +inline ERR acClipboard(OBJECTPTR Object, CLIPMODE Mode) {
        struct acClipboard args = { Mode };
        return Action(AC_Clipboard, Object, &args);
     }
     
    -inline ERROR acDragDrop(OBJECTPTR Object, OBJECTPTR Source, LONG Item, CSTRING Datatype) {
    +inline ERR acDragDrop(OBJECTPTR Object, OBJECTPTR Source, LONG Item, CSTRING Datatype) {
        struct acDragDrop args = { Source, Item, Datatype };
        return Action(AC_DragDrop, Object, &args);
     }
     
    -inline ERROR acDrawArea(OBJECTPTR Object, LONG X, LONG Y, LONG Width, LONG Height) {
    +inline ERR acDrawArea(OBJECTPTR Object, LONG X, LONG Y, LONG Width, LONG Height) {
        struct acDraw args = { X, Y, Width, Height };
        return Action(AC_Draw, Object, &args);
     }
     
    -inline ERROR acDataFeed(OBJECTPTR Object, OBJECTPTR Sender, DATA Datatype, const void *Buffer, LONG Size) {
    +inline ERR acDataFeed(OBJECTPTR Object, OBJECTPTR Sender, DATA Datatype, const void *Buffer, LONG Size) {
        struct acDataFeed args = { Sender, Datatype, Buffer, Size };
        return Action(AC_DataFeed, Object, &args);
     }
     
    -inline ERROR acGetVar(OBJECTPTR Object, CSTRING FieldName, STRING Buffer, LONG Size) {
    +inline ERR acGetVar(OBJECTPTR Object, CSTRING FieldName, STRING Buffer, LONG Size) {
        struct acGetVar args = { FieldName, Buffer, Size };
    -   ERROR error = Action(AC_GetVar, Object, &args);
    -   if ((error) and (Buffer)) Buffer[0] = 0;
    +   ERR error = Action(AC_GetVar, Object, &args);
    +   if ((error != ERR::Okay) and (Buffer)) Buffer[0] = 0;
        return error;
     }
     
    -inline ERROR acMove(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z) {
    +inline ERR acMove(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z) {
        struct acMove args = { X, Y, Z };
        return Action(AC_Move, Object, &args);
     }
     
    -inline ERROR acRead(OBJECTPTR Object, APTR Buffer, LONG Bytes, LONG *Read) {
    -   ERROR error;
    +inline ERR acRead(OBJECTPTR Object, APTR Buffer, LONG Bytes, LONG *Read) {
        struct acRead read = { (BYTE *)Buffer, Bytes };
    -   if (!(error = Action(AC_Read, Object, &read))) {
    +   if (auto error = Action(AC_Read, Object, &read); error IS ERR::Okay) {
           if (Read) *Read = read.Result;
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
        else {
           if (Read) *Read = 0;
    @@ -1874,90 +1964,92 @@ inline ERROR acRead(OBJECTPTR Object, APTR Buffer, LONG Bytes, LONG *Read) {
        }
     }
     
    -inline ERROR acRedo(OBJECTPTR Object, LONG Steps = 1) {
    +inline ERR acRedo(OBJECTPTR Object, LONG Steps = 1) {
        struct acRedo args = { Steps };
        return Action(AC_Redo, Object, &args);
     }
     
    -inline ERROR acRedimension(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE Width, DOUBLE Height, DOUBLE Depth) {
    +inline ERR acRedimension(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE Width, DOUBLE Height, DOUBLE Depth) {
        struct acRedimension args = { X, Y, Z, Width, Height, Depth };
        return Action(AC_Redimension, Object, &args);
     }
     
    -inline ERROR acRename(OBJECTPTR Object, CSTRING Name) {
    +inline ERR acRename(OBJECTPTR Object, CSTRING Name) {
        struct acRename args = { Name };
        return Action(AC_Rename, Object, &args);
     }
     
    -inline ERROR acResize(OBJECTPTR Object, DOUBLE Width, DOUBLE Height, DOUBLE Depth) {
    +inline ERR acResize(OBJECTPTR Object, DOUBLE Width, DOUBLE Height, DOUBLE Depth) {
        struct acResize args = { Width, Height, Depth };
        return Action(AC_Resize, Object, &args);
     }
     
    -inline ERROR acScroll(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z) {
    +inline ERR acScroll(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z) {
        struct acScroll args = { X, Y, Z };
        return Action(AC_Scroll, Object, &args);
     }
     
    -inline ERROR acScrollToPoint(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z, STP Flags) {
    +inline ERR acScrollToPoint(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z, STP Flags) {
        struct acScrollToPoint args = { X, Y, Z, Flags };
        return Action(AC_ScrollToPoint, Object, &args);
     }
     
    -inline ERROR acMoveToPoint(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z, MTF Flags) {
    +inline ERR acMoveToPoint(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Z, MTF Flags) {
        struct acMoveToPoint moveto = { X, Y, Z, Flags };
        return Action(AC_MoveToPoint, Object, &moveto);
     }
     
    -inline ERROR acSaveImage(OBJECTPTR Object, OBJECTPTR Dest, CLASSID ClassID = 0) {
    +inline ERR acSaveImage(OBJECTPTR Object, OBJECTPTR Dest, CLASSID ClassID = 0) {
        struct acSaveImage args = { Dest, { ClassID } };
        return Action(AC_SaveImage, Object, &args);
     }
     
    -inline ERROR acSaveToObject(OBJECTPTR Object, OBJECTPTR Dest, CLASSID ClassID = 0) {
    +inline ERR acSaveToObject(OBJECTPTR Object, OBJECTPTR Dest, CLASSID ClassID = 0) {
        struct acSaveToObject args = { Dest, { ClassID } };
        return Action(AC_SaveToObject, Object, &args);
     }
     
    -inline ERROR acSeek(OBJECTPTR Object, DOUBLE Offset, SEEK Position) {
    +inline ERR acSeek(OBJECTPTR Object, DOUBLE Offset, SEEK Position) {
        struct acSeek args = { Offset, Position };
        return Action(AC_Seek, Object, &args);
     }
     
    -inline ERROR acSetVars(OBJECTPTR Object, CSTRING tags, ...) {
    +inline ERR acSetVars(OBJECTPTR Object, CSTRING tags, ...) {
        struct acSetVar args;
        va_list list;
     
        va_start(list, tags);
        while ((args.Field = va_arg(list, STRING)) != TAGEND) {
           args.Value = va_arg(list, STRING);
    -      if (Action(AC_SetVar, Object, &args) != ERR_Okay) {
    +      if (Action(AC_SetVar, Object, &args) != ERR::Okay) {
              va_end(list);
    -         return ERR_Failed;
    +         return ERR::Failed;
           }
        }
        va_end(list);
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
    -inline ERROR acUndo(OBJECTPTR Object, LONG Steps) {
    +inline ERR acUndo(OBJECTPTR Object, LONG Steps) {
        struct acUndo args = { Steps };
        return Action(AC_Undo, Object, &args);
     }
     
    -inline ERROR acWrite(OBJECTPTR Object, CPTR Buffer, LONG Bytes, LONG *Result) {
    -   ERROR error;
    +inline ERR acWrite(OBJECTPTR Object, CPTR Buffer, LONG Bytes, LONG *Result) {
        struct acWrite write = { (BYTE *)Buffer, Bytes };
    -   if (!(error = Action(AC_Write, Object, &write))) {
    +   if (auto error = Action(AC_Write, Object, &write); error IS ERR::Okay) {
           if (Result) *Result = write.Result;
    +      return error;
    +   }
    +   else {
    +      if (Result) *Result = 0;
    +      return error;
        }
    -   else if (Result) *Result = 0;
    -   return error;
     }
     
     inline LONG acWriteResult(OBJECTPTR Object, CPTR Buffer, LONG Bytes) {
        struct acWrite write = { (BYTE *)Buffer, Bytes };
    -   if (!Action(AC_Write, Object, &write)) return write.Result;
    +   if (Action(AC_Write, Object, &write) IS ERR::Okay) return write.Result;
        else return 0;
     }
     
    @@ -1965,12 +2057,12 @@ inline LONG acWriteResult(OBJECTPTR Object, CPTR Buffer, LONG Bytes) {
     #define acSeekEnd(a,b)      acSeek((a),(b),SEEK::END)
     #define acSeekCurrent(a,b)  acSeek((a),(b),SEEK::CURRENT)
     
    -inline ERROR acSelectArea(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) {
    +inline ERR acSelectArea(OBJECTPTR Object, DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) {
        struct acSelectArea area = { X, Y, Width, Height };
        return Action(AC_SelectArea, Object, &area);
     }
     
    -inline ERROR acSetVar(OBJECTPTR Object, CSTRING FieldName, CSTRING Value) {
    +inline ERR acSetVar(OBJECTPTR Object, CSTRING FieldName, CSTRING Value) {
        struct acSetVar args = { FieldName, Value };
        return Action(AC_SetVar, Object, &args);
     }
    @@ -2056,64 +2148,64 @@ inline bool BaseClass::isSubClass() { return Class->ClassID != Class->BaseClassI
     
        // For C++ only, these read variants avoid method calls for speed, but apply identical logic.
     
    -   inline ERROR read(CSTRING pGroup, CSTRING pKey, DOUBLE *pValue) {
    +   inline ERR read(CSTRING pGroup, CSTRING pKey, DOUBLE *pValue) {
           for (auto& [group, keys] : Groups[0]) {
              if ((pGroup) and (group.compare(pGroup))) continue;
              if (!pKey) {
                 *pValue = strtod(keys.cbegin()->second.c_str(), NULL);
    -            return ERR_Okay;
    +            return ERR::Okay;
              }
              else if (keys.contains(pKey)) {
                 *pValue = strtod(keys[pKey].c_str(), NULL);
    -            return ERR_Okay;
    +            return ERR::Okay;
              }
           }
    -      return ERR_Search;
    +      return ERR::Search;
        }
     
    -   inline ERROR read(CSTRING pGroup, CSTRING pKey, LONG *pValue) {
    +   inline ERR read(CSTRING pGroup, CSTRING pKey, LONG *pValue) {
           for (auto& [group, keys] : Groups[0]) {
              if ((pGroup) and (group.compare(pGroup))) continue;
              if (!pKey) {
                 *pValue = strtol(keys.cbegin()->second.c_str(), NULL, 0);
    -            return ERR_Okay;
    +            return ERR::Okay;
              }
              else if (keys.contains(pKey)) {
                 *pValue = strtol(keys[pKey].c_str(), NULL, 0);
    -            return ERR_Okay;
    +            return ERR::Okay;
              }
           }
    -      return ERR_Search;
    +      return ERR::Search;
        }
     
    -   inline ERROR read(CSTRING pGroup, CSTRING pKey, std::string &pValue) {
    +   inline ERR read(CSTRING pGroup, CSTRING pKey, std::string &pValue) {
           for (auto& [group, keys] : Groups[0]) {
              if ((pGroup) and (group.compare(pGroup))) continue;
              if (!pKey) {
                 pValue = keys.cbegin()->second;
    -            return ERR_Okay;
    +            return ERR::Okay;
              }
              else if (keys.contains(pKey)) {
                 pValue = keys[pKey];
    -            return ERR_Okay;
    +            return ERR::Okay;
              }
           }
    -      return ERR_Search;
    +      return ERR::Search;
        }
     
    -   inline ERROR write(CSTRING Group, CSTRING Key, CSTRING Value) {
    +   inline ERR write(CSTRING Group, CSTRING Key, CSTRING Value) {
           struct cfgWriteValue write = { Group, Key, Value };
           return Action(MT_CfgWriteValue, this, &write);
        }
    -   inline ERROR write(CSTRING Group, CSTRING Key, STRING Value) {
    +   inline ERR write(CSTRING Group, CSTRING Key, STRING Value) {
           struct cfgWriteValue write = { Group, Key, Value };
           return Action(MT_CfgWriteValue, this, &write);
        }
    -   inline ERROR write(CSTRING Group, CSTRING Key, std::string Value) {
    +   inline ERR write(CSTRING Group, CSTRING Key, std::string Value) {
           struct cfgWriteValue write = { Group, Key, Value.c_str() };
           return Action(MT_CfgWriteValue, this, &write);
        }
    -   template  inline ERROR write(CSTRING Group, CSTRING Key, T Value) {
    +   template  inline ERR write(CSTRING Group, CSTRING Key, T Value) {
           auto str = std::to_string(Value);
           struct cfgWriteValue write = { Group, Key, str.c_str() };
           return Action(MT_CfgWriteValue, this, &write);
    @@ -2121,24 +2213,22 @@ inline bool BaseClass::isSubClass() { return Class->ClassID != Class->BaseClassI
       ]])
     
       c_insert([[
    -inline ERROR cfgRead(OBJECTPTR Self, CSTRING Group, CSTRING Key, DOUBLE *Value)
    +inline ERR cfgRead(OBJECTPTR Self, CSTRING Group, CSTRING Key, DOUBLE *Value)
     {
    -   ERROR error;
        struct cfgReadValue read = { .Group = Group, .Key = Key };
    -   if (!(error = Action(MT_CfgReadValue, Self, &read))) {
    +   if (auto error = Action(MT_CfgReadValue, Self, &read); error IS ERR::Okay) {
           *Value = strtod(read.Data, NULL);
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
        else { *Value = 0; return error; }
     }
     
    -inline ERROR cfgRead(OBJECTPTR Self, CSTRING Group, CSTRING Key, LONG *Value)
    +inline ERR cfgRead(OBJECTPTR Self, CSTRING Group, CSTRING Key, LONG *Value)
     {
    -   ERROR error;
        struct cfgReadValue read = { .Group = Group, .Key = Key };
    -   if (!(error = Action(MT_CfgReadValue, Self, &read))) {
    +   if (auto error = Action(MT_CfgReadValue, Self, &read); error IS ERR::Okay) {
           *Value = strtol(read.Data, NULL, 0);
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
        else { *Value = 0; return error; }
     }
    @@ -2160,7 +2250,7 @@ inline ERROR cfgRead(OBJECTPTR Self, CSTRING Group, CSTRING Key, LONG *Value)
       ]],
       [[
        LARGE    ProcedureID;          // For callbacks
    -   std::map Vars; // Global parameters
    +   KEYVALUE Vars; // Global parameters
        STRING   *Results;
        char     Language[4];          // 3-character language code, null-terminated
        const ScriptArg *ProcArgs;     // Procedure args - applies during Exec
    @@ -2217,23 +2307,23 @@ inline ERROR cfgRead(OBJECTPTR Self, CSTRING Group, CSTRING Key, LONG *Value)
       ]],
       nil,
       [[
    -   static ERROR load(std::string Name, OBJECTPTR *Module = NULL, APTR Functions = NULL) {
    +   static ERR load(std::string Name, OBJECTPTR *Module = NULL, APTR Functions = NULL) {
           if (auto module = objModule::create::global(pf::FieldValue(FID_Name, Name.c_str()))) {
              #ifdef PARASOL_STATIC
                 if (Module) *Module = module;
                 if (Functions) ((APTR *)Functions)[0] = NULL;
    -            return ERR_Okay;
    +            return ERR::Okay;
              #else
                 APTR functionbase;
    -            if (!module->getPtr(FID_ModBase, &functionbase)) {
    +            if (module->getPtr(FID_ModBase, &functionbase) IS ERR::Okay) {
                    if (Module) *Module = module;
                    if (Functions) ((APTR *)Functions)[0] = functionbase;
    -               return ERR_Okay;
    +               return ERR::Okay;
                 }
    -            else return ERR_GetField;
    +            else return ERR::GetField;
              #endif
           }
    -      else return ERR_CreateObject;
    +      else return ERR::CreateObject;
        }
       ]])
     
    @@ -2302,78 +2392,78 @@ inline ERROR cfgRead(OBJECTPTR Self, CSTRING Group, CSTRING Key, LONG *Value)
     #define acDataXML(a,b)      acDataFeed((a),0,DATA::XML,(b),0)
     #define acDataText(a,b)     acDataFeed((a),0,DATA::TEXT,(b),0)
     
    -inline ERROR acCustom(OBJECTID ObjectID, LONG Number, CSTRING String) {
    +inline ERR acCustom(OBJECTID ObjectID, LONG Number, CSTRING String) {
        struct acCustom args = { Number, String };
        return ActionMsg(AC_Custom, ObjectID, &args);
     }
     
    -inline ERROR acDataFeed(OBJECTID ObjectID, OBJECTPTR Sender, DATA Datatype, const APTR Data, LONG Size) {
    +inline ERR acDataFeed(OBJECTID ObjectID, OBJECTPTR Sender, DATA Datatype, const APTR Data, LONG Size) {
        struct acDataFeed channel = { Sender, Datatype, Data, Size };
        return ActionMsg(AC_DataFeed, ObjectID, &channel);
     }
     
    -inline ERROR acDragDrop(OBJECTID ObjectID, OBJECTPTR Source, LONG Item, CSTRING Datatype) {
    +inline ERR acDragDrop(OBJECTID ObjectID, OBJECTPTR Source, LONG Item, CSTRING Datatype) {
        struct acDragDrop args = { Source, Item, Datatype };
        return ActionMsg(AC_DragDrop, ObjectID, &args);
     }
     
    -inline ERROR acDrawArea(OBJECTID ObjectID, LONG X, LONG Y, LONG Width, LONG Height) {
    +inline ERR acDrawArea(OBJECTID ObjectID, LONG X, LONG Y, LONG Width, LONG Height) {
        struct acDraw draw = { X, Y, Width, Height };
        return ActionMsg(AC_Draw, ObjectID, &draw);
     }
     
    -inline ERROR acMove(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z = 0) {
    +inline ERR acMove(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z = 0) {
        struct acMove move = { X, Y, Z };
        return ActionMsg(AC_Move, ObjectID, &move);
     }
     
    -inline ERROR acMoveToPoint(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z = 0, MTF Flags = MTF::X|MTF::Y) {
    +inline ERR acMoveToPoint(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z = 0, MTF Flags = MTF::X|MTF::Y) {
        struct acMoveToPoint moveto = { X, Y, Z, Flags };
        return ActionMsg(AC_MoveToPoint, ObjectID, &moveto);
     }
     
    -inline ERROR acRedimension(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE Width, DOUBLE Height, DOUBLE Depth) {
    +inline ERR acRedimension(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z, DOUBLE Width, DOUBLE Height, DOUBLE Depth) {
        struct acRedimension resize = { X, Y, Z, Width, Height, Depth };
        return ActionMsg(AC_Redimension, ObjectID, &resize);
     }
     
    -inline ERROR acResize(OBJECTID ObjectID, DOUBLE Width, DOUBLE Height, DOUBLE Depth) {
    +inline ERR acResize(OBJECTID ObjectID, DOUBLE Width, DOUBLE Height, DOUBLE Depth) {
        struct acResize resize = { Width, Height, Depth };
        return ActionMsg(AC_Resize, ObjectID, &resize);
     }
     
    -inline ERROR acScrollToPoint(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z = 0, STP Flags = STP::X|STP::Y) {
    +inline ERR acScrollToPoint(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z = 0, STP Flags = STP::X|STP::Y) {
        struct acScrollToPoint scroll = { X, Y, Z, Flags };
        return ActionMsg(AC_ScrollToPoint, ObjectID, &scroll);
     }
     
    -inline ERROR acScroll(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z = 0) {
    +inline ERR acScroll(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Z = 0) {
        struct acScroll scroll = { X, Y, Z };
        return ActionMsg(AC_Scroll, ObjectID, &scroll);
     }
     
    -inline ERROR acSelectArea(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) {
    +inline ERR acSelectArea(OBJECTID ObjectID, DOUBLE X, DOUBLE Y, DOUBLE Width, DOUBLE Height) {
        struct acSelectArea area = { X, Y, Width, Height };
        return ActionMsg(AC_SelectArea, ObjectID, &area);
     }
     
    -inline ERROR acActivate(OBJECTID ObjectID) { return ActionMsg(AC_Activate, ObjectID, NULL); }
    -inline ERROR acClear(OBJECTID ObjectID) { return ActionMsg(AC_Clear, ObjectID, NULL); }
    -inline ERROR acDisable(OBJECTID ObjectID) { return ActionMsg(AC_Disable, ObjectID, NULL); }
    -inline ERROR acDraw(OBJECTID ObjectID) { return ActionMsg(AC_Draw, ObjectID, NULL); }
    -inline ERROR acEnable(OBJECTID ObjectID) { return ActionMsg(AC_Enable, ObjectID, NULL); }
    -inline ERROR acFlush(OBJECTID ObjectID) { return ActionMsg(AC_Flush, ObjectID, NULL); }
    -inline ERROR acFocus(OBJECTID ObjectID) { return ActionMsg(AC_Focus, ObjectID, NULL); }
    -inline ERROR acHide(OBJECTID ObjectID) { return ActionMsg(AC_Hide, ObjectID, NULL); }
    -inline ERROR acLostFocus(OBJECTID ObjectID) { return ActionMsg(AC_LostFocus, ObjectID, NULL); }
    -inline ERROR acMoveToBack(OBJECTID ObjectID) { return ActionMsg(AC_MoveToBack, ObjectID, NULL); }
    -inline ERROR acMoveToFront(OBJECTID ObjectID) { return ActionMsg(AC_MoveToFront, ObjectID, NULL); }
    -inline ERROR acQuery(OBJECTID ObjectID) { return ActionMsg(AC_Query, ObjectID, NULL); }
    -inline ERROR acRefresh(OBJECTID ObjectID) { return ActionMsg(AC_Refresh, ObjectID, NULL); }
    -inline ERROR acSaveSettings(OBJECTID ObjectID) { return ActionMsg(AC_SaveSettings, ObjectID, NULL); }
    -inline ERROR acShow(OBJECTID ObjectID) { return ActionMsg(AC_Show, ObjectID, NULL); }
    -
    -inline ERROR acWrite(OBJECTID ObjectID, CPTR Buffer, LONG Bytes) {
    +inline ERR acActivate(OBJECTID ObjectID) { return ActionMsg(AC_Activate, ObjectID, NULL); }
    +inline ERR acClear(OBJECTID ObjectID) { return ActionMsg(AC_Clear, ObjectID, NULL); }
    +inline ERR acDisable(OBJECTID ObjectID) { return ActionMsg(AC_Disable, ObjectID, NULL); }
    +inline ERR acDraw(OBJECTID ObjectID) { return ActionMsg(AC_Draw, ObjectID, NULL); }
    +inline ERR acEnable(OBJECTID ObjectID) { return ActionMsg(AC_Enable, ObjectID, NULL); }
    +inline ERR acFlush(OBJECTID ObjectID) { return ActionMsg(AC_Flush, ObjectID, NULL); }
    +inline ERR acFocus(OBJECTID ObjectID) { return ActionMsg(AC_Focus, ObjectID, NULL); }
    +inline ERR acHide(OBJECTID ObjectID) { return ActionMsg(AC_Hide, ObjectID, NULL); }
    +inline ERR acLostFocus(OBJECTID ObjectID) { return ActionMsg(AC_LostFocus, ObjectID, NULL); }
    +inline ERR acMoveToBack(OBJECTID ObjectID) { return ActionMsg(AC_MoveToBack, ObjectID, NULL); }
    +inline ERR acMoveToFront(OBJECTID ObjectID) { return ActionMsg(AC_MoveToFront, ObjectID, NULL); }
    +inline ERR acQuery(OBJECTID ObjectID) { return ActionMsg(AC_Query, ObjectID, NULL); }
    +inline ERR acRefresh(OBJECTID ObjectID) { return ActionMsg(AC_Refresh, ObjectID, NULL); }
    +inline ERR acSaveSettings(OBJECTID ObjectID) { return ActionMsg(AC_SaveSettings, ObjectID, NULL); }
    +inline ERR acShow(OBJECTID ObjectID) { return ActionMsg(AC_Show, ObjectID, NULL); }
    +
    +inline ERR acWrite(OBJECTID ObjectID, CPTR Buffer, LONG Bytes) {
        struct acWrite write = { (BYTE *)Buffer, Bytes };
        return ActionMsg(AC_Write, ObjectID, &write);
     }
    @@ -2478,17 +2568,17 @@ struct evHotplug {
     
     inline CSTRING flReadLine(OBJECTPTR Object) {
        struct flReadLine args;
    -   if (!Action(MT_FlReadLine, Object, &args)) return args.Result;
    +   if (Action(MT_FlReadLine, Object, &args) IS ERR::Okay) return args.Result;
        else return NULL;
     }
     
     // Read endian values from files and objects.
     
    -template ERROR flReadLE(OBJECTPTR Object, T *Result)
    +template ERR flReadLE(OBJECTPTR Object, T *Result)
     {
        UBYTE data[sizeof(T)];
        struct acRead read = { .Buffer = data, .Length = sizeof(T) };
    -   if (!Action(AC_Read, Object, &read)) {
    +   if (Action(AC_Read, Object, &read) IS ERR::Okay) {
           if (read.Result IS sizeof(T)) {
              if constexpr (std::endian::native == std::endian::little) {
                 *Result = ((T *)data)[0];
    @@ -2501,18 +2591,18 @@ template ERROR flReadLE(OBJECTPTR Object, T *Result)
                    default: *Result = ((T *)data)[0];
                 }
              }
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
    -      else return ERR_Read;
    +      else return ERR::Read;
        }
    -   else return ERR_Read;
    +   else return ERR::Read;
     }
     
    -template ERROR flReadBE(OBJECTPTR Object, T *Result)
    +template ERR flReadBE(OBJECTPTR Object, T *Result)
     {
        UBYTE data[sizeof(T)];
        struct acRead read = { .Buffer = data, .Length = sizeof(T) };
    -   if (!Action(AC_Read, Object, &read)) {
    +   if (Action(AC_Read, Object, &read) IS ERR::Okay) {
           if (read.Result IS sizeof(T)) {
              if constexpr (std::endian::native == std::endian::little) {
                 switch(sizeof(T)) {
    @@ -2525,23 +2615,34 @@ template ERROR flReadBE(OBJECTPTR Object, T *Result)
              else {
                 *Result = ((T *)data)[0];
              }
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
    -      else return ERR_Read;
    +      else return ERR::Read;
        }
    -   else return ERR_Read;
    +   else return ERR::Read;
     }
     
    -template 
    -constexpr FUNCTION make_function_stdc(R Routine, OBJECTPTR Context = CurrentContext()) {
    -   FUNCTION func = { .Type = CALL_STDC, .StdC = { .Context = Context, .Routine = (APTR)Routine } };
    -   return func;
    -}
    +// Function construction (refer types.h)
     
    -inline FUNCTION make_function_script(OBJECTPTR Script, LARGE Procedure) {
    -   FUNCTION func = { .Type = CALL_SCRIPT, .Script = { .Script = (OBJECTPTR)Script, .ProcedureID = Procedure } };
    -   return func;
    -}
    +template  FUNCTION::FUNCTION(T *pRoutine) {
    +   Type = CALL_STDC;
    +   StdC.Context = CurrentContext();
    +   StdC.Routine = (APTR)pRoutine;
    +};
    +
    +template  FUNCTION::FUNCTION(T *pRoutine, OBJECTPTR pContext, APTR pMeta) {
    +   Type = CALL_STDC;
    +   StdC.Context = pContext;
    +   StdC.Routine = (APTR)pRoutine;
    +   StdC.Meta    = pMeta;
    +};
    +
    +template  FUNCTION::FUNCTION(T *pRoutine, APTR pMeta) {
    +   Type = CALL_STDC;
    +   StdC.Context = CurrentContext();
    +   StdC.Routine = (APTR)pRoutine;
    +   StdC.Meta    = pMeta;
    +};
     
     inline CSTRING BaseClass::className() { return Class->ClassName; }
       ]])
    diff --git a/src/core/defs/errors.fdl b/src/core/defs/errors.fdl
    index 60c4b61bc..4eba7c60a 100644
    --- a/src/core/defs/errors.fdl
    +++ b/src/core/defs/errors.fdl
    @@ -3,7 +3,9 @@
     -- Refer to data_errors.c for the official description strings for each error code.
     
     function declareErrors()
    -  enum("ERR", { start=0, comment="Universal error codes" },
    +  cpp_include("")
    +
    +  enum("ERR", { start=0, comment="Universal error codes", type="int32" },
         "Okay|True",
         "False",            -- Non-fatal
         "LimitedSuccess",   -- Limited success.
    @@ -82,12 +84,12 @@ function declareErrors()
         "NoMatchingObject",     -- Unable to find object
         "AccessMemory",
         "MissingPath",
    -    "NotLocked",           -- Attempted to release a lock that doesn't exist or doesn't belong to you
    +    "NotLocked",           -- Attempted to release a lock that doesn't exist or doesn't belong to the caller
         "NoSearchResult",
         "StatementUnsatisfied",
         "ObjectCorrupt",
         "OwnerPassThrough",
    -    "UnsupportedOwner|BadOwner",
    +    "UnsupportedOwner",
         "ExclusiveDenied|AccessObject",
         "AllocMemory",
         "NewObject",
    @@ -131,7 +133,7 @@ function declareErrors()
         "SanityFailure",           -- A sanity check failed
         "OutOfSpace",              -- Run out of space, no room to complete request
         "GetSurfaceInfo",          -- GetSurfaceInfo() failed
    -    "Finished|EOF|EndOfFile|OutOfData", -- Operation or process loop finished
    +    "Finished|EndOfFile|OutOfData", -- Operation or process loop finished
         "Syntax|StringFormat",     -- Invalid syntax detected
         "InvalidState",            -- Object was in an invalid state for processing.
         "HostNotFound",            -- The internet host name could not be resolved
    @@ -195,16 +197,17 @@ function declareErrors()
         "SetValueNotPointer",      -- Attempted to set a pointer field with an incompatible value.
         "SetValueNotArray",        -- Attempted to set an array field with an incompatible value.
         "SetValueNotLookup",       -- Attempted to set a lookup field with an incompatible value.
    -    "END") -- NB: Any new error messages need to be added to data_errors.c manually.
    +    "END",
    +    { Notified = 0x40000000 }
    +  ) -- NB: Any new error messages need to be added to data_errors.c manually.
     
       const("ERF", { comment="Special error flags" }, {
    -    Notified=0x40000000,
    -    Delay=0x20000000
    +    Notified=0x40000000
       })
     end
     
        if (glProgram == "idl-c") then
    -      header({ path="system/errors", copyright="Paul Manias © 1996-2023" }, declareErrors)
    +      header({ path="system/errors", copyright="Paul Manias © 1996-2024" }, declareErrors)
        elseif (glProgram == "idl-def") then
           declareErrors()
        end
    diff --git a/src/core/defs/fields.fdl b/src/core/defs/fields.fdl
    index 9148f6ffb..f63f49850 100644
    --- a/src/core/defs/fields.fdl
    +++ b/src/core/defs/fields.fdl
    @@ -4,7 +4,7 @@
     // itself, generated from StrHash().  Values are 64-bit as the upper 32 bits contain special flags when used with
     // tag-based functions.
     
    -header({ path="system/fields", copyright="Paul Manias © 1996-2023" }, function()
    +header({ path="system/fields", copyright="Paul Manias © 1996-2024" }, function()
       hash("FID", "0x%sLL",
         "Category",
         "FileName",
    @@ -218,7 +218,7 @@ header({ path="system/fields", copyright="Paul Manias © 1996-2023" }, function(
         "ActionScript",
         "LabelWidth",
         "Template",
    -    "FocusFrame",
    +    "FontStyle",
         "Bottom",
         "IgnoreFocus",
         "Header",
    @@ -536,17 +536,14 @@ header({ path="system/fields", copyright="Paul Manias © 1996-2023" }, function(
         "Tabs",
         "Outline",
         "WrapEdge",
    -    "WrapCallback",
         "StrWidth",
         "FixedWidth",
    -    "EscapeChar",
         "Underline",
         "LineSpacing",
         "TotalChars",
         "GlyphSpacing",
         "AlignWidth",
         "TabSize",
    -    "EscapeCallback",
         "Ascent",
         "InputFile",
         "Datatype",
    @@ -860,6 +857,7 @@ header({ path="system/fields", copyright="Paul Manias © 1996-2023" }, function(
         "Degree",
         "DestBitmap",
         "DeviceID",
    +    "DragCallback",
         "EffectXML",
         "EnableBkgd",
         "FX",
    @@ -942,19 +940,25 @@ header({ path="system/fields", copyright="Paul Manias © 1996-2023" }, function(
     
       hash("FID", "0x%sLL",
         "Bias",
    +    "ClipFlags",
         "Constant",
         "Def",
         "Dictionary",
         "Divisor",
         "EdgeMode",
    +    "EventCallback",
    +    "EventMask",
         "Exponent",
    +    "LoopLimit",
         "MatrixRows",
         "MatrixColumns",
         "Matrix",
         "PreserveAlpha",
    +    "Pretext",
         "ResX",
         "ResY",
         "RootModule",
    +    "Rounding",
         "SourceName",
         "Structs",
         "TargetX",
    @@ -984,6 +988,7 @@ header({ path="system/fields", copyright="Paul Manias © 1996-2023" }, function(
         "Created",
         "Numeric",
         "ResizeEvent",
    -    "TabOrder"
    +    "TabOrder",
    +    "TextFlags"
         )
     end)
    diff --git a/src/core/defs/registry.fdl b/src/core/defs/registry.fdl
    index 2e3bf9a66..49ec3538e 100644
    --- a/src/core/defs/registry.fdl
    +++ b/src/core/defs/registry.fdl
    @@ -1,7 +1,7 @@
     --$FLUID:Include
     -- Fluid programs should use mSys.ResolveClassName() to convert class names to identifiers, as these constants are not exported.
     
    -header({ path="system/registry", copyright="Paul Manias 1996-2023" }, function()
    +header({ path="system/registry", copyright="Paul Manias 1996-2024" }, function()
       hash("ID", "0x%sUL",
         "PICTURE",
         "SOUND",
    diff --git a/src/core/fs_folders.cpp b/src/core/fs_folders.cpp
    index 9eb9f350e..12b8d23f6 100644
    --- a/src/core/fs_folders.cpp
    +++ b/src/core/fs_folders.cpp
    @@ -4,7 +4,7 @@ Name: Files
     -END-
     *********************************************************************************************************************/
     
    -static ERROR folder_free(APTR Address)
    +static ERR folder_free(APTR Address)
     {
        pf::Log log("CloseDir");
        auto folder = (DirInfo *)Address;
    @@ -21,7 +21,7 @@ static ERROR folder_free(APTR Address)
        }
     
        fs_closedir(folder);
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     static ResourceManager glResourceFolder = {
    @@ -56,11 +56,11 @@ AllocMemory
     
     *********************************************************************************************************************/
     
    -ERROR OpenDir(CSTRING Path, RDF Flags, DirInfo **Result)
    +ERR OpenDir(CSTRING Path, RDF Flags, DirInfo **Result)
     {
        pf::Log log(__FUNCTION__);
     
    -   if ((!Path) or (!Result)) return log.warning(ERR_NullArgs);
    +   if ((!Path) or (!Result)) return log.warning(ERR::NullArgs);
     
        log.traceBranch("Path: '%s'", Path);
     
    @@ -70,7 +70,7 @@ ERROR OpenDir(CSTRING Path, RDF Flags, DirInfo **Result)
     
        STRING resolved_path;
        if (!Path[0]) Path = ":"; // A path of ':' will return all known volumes.
    -   if (auto error = ResolvePath(Path, RSF::NIL, &resolved_path); !error) {
    +   if (auto error = ResolvePath(Path, RSF::NIL, &resolved_path); error IS ERR::Okay) {
           auto vd = get_fs(resolved_path);
     
           // NB: We use MAX_FILENAME rather than resolve_len in the allocation size because fs_opendir() requires more space.
    @@ -79,9 +79,9 @@ ERROR OpenDir(CSTRING Path, RDF Flags, DirInfo **Result)
           DirInfo *dir;
           // Layout: [DirInfo] [FileInfo] [Driver] [Name] [Path]
           LONG size = sizeof(DirInfo) + sizeof(FileInfo) + vd->DriverSize + MAX_FILENAME + path_len + MAX_FILENAME;
    -      if (AllocMemory(size, MEM::DATA|MEM::MANAGED, (APTR *)&dir, NULL) != ERR_Okay) {
    +      if (AllocMemory(size, MEM::DATA|MEM::MANAGED, (APTR *)&dir, NULL) != ERR::Okay) {
              FreeResource(resolved_path);
    -         return ERR_AllocMemory;
    +         return ERR::AllocMemory;
           }
     
           set_memory_manager(dir, &glResourceFolder);
    @@ -105,27 +105,27 @@ ERROR OpenDir(CSTRING Path, RDF Flags, DirInfo **Result)
           if ((Path[0] IS ':') or (!Path[0])) {
              if ((Flags & RDF::FOLDER) IS RDF::NIL) {
                 FreeResource(dir);
    -            return ERR_DirEmpty;
    +            return ERR::DirEmpty;
              }
              *Result = dir;
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
     
           if (!vd->OpenDir) {
              FreeResource(dir);
    -         return ERR_DirEmpty;
    +         return ERR::DirEmpty;
           }
     
    -      if (!(error = vd->OpenDir(dir))) {
    +      if ((error = vd->OpenDir(dir)) IS ERR::Okay) {
              dir->prvVirtualID = vd->VirtualID;
              *Result = dir;
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
     
           FreeResource(dir);
           return error;
        }
    -   else return log.warning(ERR_ResolvePath);
    +   else return log.warning(ERR::ResolvePath);
     }
     
     /*********************************************************************************************************************
    @@ -165,15 +165,15 @@ DirEmpty: There are no more items to scan.
     
     *********************************************************************************************************************/
     
    -ERROR ScanDir(DirInfo *Dir)
    +ERR ScanDir(DirInfo *Dir)
     {
        pf::Log log(__FUNCTION__);
     
    -   if (!Dir) return log.warning(ERR_NullArgs);
    +   if (!Dir) return log.warning(ERR::NullArgs);
     
        FileInfo *file;
    -   if (!(file = Dir->Info)) { log.trace("Missing Dir->Info"); return log.warning(ERR_InvalidData); }
    -   if (!file->Name) { log.trace("Missing Dir->Info->Name"); return log.warning(ERR_InvalidData); }
    +   if (!(file = Dir->Info)) { log.trace("Missing Dir->Info"); return log.warning(ERR::InvalidData); }
    +   if (!file->Name) { log.trace("Missing Dir->Info->Name"); return log.warning(ERR::InvalidData); }
     
        file->Name[0] = 0;
        file->Flags   = RDF::NIL;
    @@ -208,19 +208,19 @@ ERROR ScanDir(DirInfo *Dir)
                    }
     
                    file->Flags |= RDF::VOLUME;
    -               return ERR_Okay;
    +               return ERR::Okay;
                 }
                 else count++;
              }
     
    -         return ERR_DirEmpty;
    +         return ERR::DirEmpty;
           }
    -      else return log.warning(ERR_SystemLocked);
    +      else return log.warning(ERR::SystemLocked);
        }
     
        // In all other cases, pass functionality to the filesystem driver.
     
    -   ERROR error = ERR_NoSupport;
    +   ERR error = ERR::NoSupport;
        if (Dir->prvVirtualID IS DEFAULT_VIRTUALID) {
           error = fs_scandir(Dir);
        }
    diff --git a/src/core/fs_identify.cpp b/src/core/fs_identify.cpp
    index 725f5e967..ddd218c96 100644
    --- a/src/core/fs_identify.cpp
    +++ b/src/core/fs_identify.cpp
    @@ -32,7 +32,7 @@ not listed in the class dictionary or if it is listed more than once, the first
     loaded and checked against classes that can match against file header information.  If a match is found, the ID of the
     matching class will be returned.
     
    -This function returns an error code of `ERR_Search` in the event that a suitable class is not available to match
    +This function returns an error code of `ERR::Search` in the event that a suitable class is not available to match
     against the given file.
     
     -INPUT-
    @@ -50,42 +50,42 @@ Read
     
     *********************************************************************************************************************/
     
    -ERROR IdentifyFile(CSTRING Path, CLASSID *ClassID, CLASSID *SubClassID)
    +ERR IdentifyFile(CSTRING Path, CLASSID *ClassID, CLASSID *SubClassID)
     {
        pf::Log log(__FUNCTION__);
        LONG i, bytes_read;
        #define HEADER_SIZE 80
     
    -   if ((!Path) or (!ClassID)) return log.warning(ERR_NullArgs);
    +   if ((!Path) or (!ClassID)) return log.warning(ERR::NullArgs);
     
        log.branch("File: %s", Path);
     
        // Determine the class type by examining the Path file name.  If the file extension does not tell us the class
        // that supports the data, we then load the first 256 bytes from the file and then compare file headers.
     
    -   ERROR error = ERR_Okay;
    +   ERR error = ERR::Okay;
        STRING res_path = NULL;
        if (ClassID) *ClassID = 0;
        if (SubClassID) *SubClassID = 0;
        UBYTE buffer[400] = { 0 };
     
    -   if ((error = load_datatypes())) { // Load the associations configuration file
    +   if ((error = load_datatypes()) != ERR::Okay) { // Load the associations configuration file
           return log.warning(error);
        }
     
    -   ERROR reserror;
    -   if ((reserror = ResolvePath(Path, RSF::APPROXIMATE|RSF::PATH|RSF::CHECK_VIRTUAL, &res_path)) != ERR_Okay) {
    -      if (reserror IS ERR_VirtualVolume) {
    +   ERR reserror;
    +   if ((reserror = ResolvePath(Path, RSF::APPROXIMATE|RSF::PATH|RSF::CHECK_VIRTUAL, &res_path)) != ERR::Okay) {
    +      if (reserror IS ERR::VirtualVolume) {
              // Virtual volumes may support the IdentifyFile() request as a means of speeding up file identification.  This
              // is often useful when probing remote file systems.  If the FS doesn't support this option, we can still
              // fall-back to the standard file reading option.
              //
    -         // Note: A virtual volume may return ERR_Okay even without identifying the class of the queried file.  This
    +         // Note: A virtual volume may return ERR::Okay even without identifying the class of the queried file.  This
              // means that the file was analysed but belongs to no known class.
     
              if (auto vd = get_virtual(res_path)) {
                 if (vd->IdentifyFile) {
    -               if (!vd->IdentifyFile(res_path, ClassID, SubClassID)) {
    +               if (vd->IdentifyFile(res_path, ClassID, SubClassID) IS ERR::Okay) {
                       log.trace("Virtual volume identified the target file.");
                       goto class_identified;
                    }
    @@ -99,8 +99,8 @@ ERROR IdentifyFile(CSTRING Path, CLASSID *ClassID, CLASSID *SubClassID)
     
              log.warning("ResolvePath() failed on '%s', error '%s'", Path, GetErrorMsg(reserror));
     
    -         if (!StrCompare("string:", Path, 7)) { // Do not check for '|' when string: is in use
    -            return ERR_FileNotFound;
    +         if (StrCompare("string:", Path, 7) IS ERR::Okay) { // Do not check for '|' when string: is in use
    +            return ERR::FileNotFound;
              }
     
              for (i=0; (Path[i]) and (Path[i] != '|'); i++) {
    @@ -110,13 +110,13 @@ ERROR IdentifyFile(CSTRING Path, CLASSID *ClassID, CLASSID *SubClassID)
              if (Path[i] IS '|') {
                 STRING tmp = StrClone(Path);
                 tmp[i] = 0;
    -            if (ResolvePath(tmp, RSF::APPROXIMATE, &res_path) != ERR_Okay) {
    +            if (ResolvePath(tmp, RSF::APPROXIMATE, &res_path) != ERR::Okay) {
                    FreeResource(tmp);
    -               return ERR_FileNotFound;
    +               return ERR::FileNotFound;
                 }
                 else FreeResource(tmp);
              }
    -         else return ERR_FileNotFound;
    +         else return ERR::FileNotFound;
           }
        }
     
    @@ -132,7 +132,7 @@ ERROR IdentifyFile(CSTRING Path, CLASSID *ClassID, CLASSID *SubClassID)
                 for (auto it = glClassDB.begin(); it != glClassDB.end(); it++) {
                    auto &rec = it->second;
                    if (!rec.Match.empty()) {
    -                  if (!StrCompare(rec.Match.c_str(), filename, 0, STR::WILDCARD)) {
    +                  if (StrCompare(rec.Match.c_str(), filename, 0, STR::WILDCARD) IS ERR::Okay) {
                          if (rec.ParentID) {
                             *ClassID = rec.ParentID;
                             if (SubClassID) *SubClassID = rec.ClassID;
    @@ -151,7 +151,7 @@ ERROR IdentifyFile(CSTRING Path, CLASSID *ClassID, CLASSID *SubClassID)
           if (!*ClassID) {
              log.trace("Loading file header to identify '%s' against class registry", res_path);
     
    -         if ((!ReadFileToBuffer(res_path, buffer, HEADER_SIZE, &bytes_read)) and (bytes_read >= 4)) {
    +         if ((ReadFileToBuffer(res_path, buffer, HEADER_SIZE, &bytes_read) IS ERR::Okay) and (bytes_read >= 4)) {
                 log.trace("Checking file header data (%d bytes) against %d classes....", bytes_read, glClassDB.size());
                 for (auto it = glClassDB.begin(); it != glClassDB.end(); it++) {
                    auto &rec = it->second;
    @@ -228,25 +228,25 @@ ERROR IdentifyFile(CSTRING Path, CLASSID *ClassID, CLASSID *SubClassID)
                    }
                 } // for all classes
              }
    -         else error = log.warning(ERR_Read);
    +         else error = log.warning(ERR::Read);
           }
        }
        else {
           log.warning("Class database not available.");
    -      error = ERR_Search;
    +      error = ERR::Search;
        }
     
     class_identified:
        if (res_path) FreeResource(res_path);
     
    -   if (!error) {
    -      if (*ClassID) log.debug("File belongs to class $%.8x:$%.8x", *ClassID, (SubClassID) ? *SubClassID : 0);
    +   if (error IS ERR::Okay) {
    +      if (*ClassID) log.detail("File belongs to class $%.8x:$%.8x", *ClassID, (SubClassID) ? *SubClassID : 0);
           else {
    -         log.debug("Failed to identify file \"%s\"", Path);
    -         error = ERR_Search;
    +         log.detail("Failed to identify file \"%s\"", Path);
    +         error = ERR::Search;
           }
        }
     
    -   if (!(*ClassID)) return ERR_Search;
    +   if (!(*ClassID)) return ERR::Search;
        else return error;
     }
    diff --git a/src/core/fs_resolution.cpp b/src/core/fs_resolution.cpp
    index e93d26c4d..278741d3c 100644
    --- a/src/core/fs_resolution.cpp
    +++ b/src/core/fs_resolution.cpp
    @@ -58,11 +58,11 @@ Loop:            The volume refers back to itself.
     
     *********************************************************************************************************************/
     
    -static ERROR resolve(STRING, STRING, RSF);
    -static ERROR resolve_path_env(CSTRING RelativePath, STRING *Result);
    +static ERR resolve(STRING, STRING, RSF);
    +static ERR resolve_path_env(CSTRING RelativePath, STRING *Result);
     static THREADVAR bool tlClassLoaded;
     
    -ERROR ResolvePath(CSTRING Path, RSF Flags, STRING *Result)
    +ERR ResolvePath(CSTRING Path, RSF Flags, STRING *Result)
     {
        pf::Log log(__FUNCTION__);
        LONG i, loop;
    @@ -71,7 +71,7 @@ ERROR ResolvePath(CSTRING Path, RSF Flags, STRING *Result)
     
        log.traceBranch("%s, Flags: $%.8x", Path, LONG(Flags));
     
    -   if (!Path) return log.warning(ERR_NullArgs);
    +   if (!Path) return log.warning(ERR::NullArgs);
     
        if (Result) *Result = NULL;
     
    @@ -82,9 +82,9 @@ ERROR ResolvePath(CSTRING Path, RSF Flags, STRING *Result)
           Path++;
        }
     
    -   if (!StrCompare("string:", Path, 7)) {
    -      if ((*Result = StrClone(Path))) return ERR_Okay;
    -      else return log.warning(ERR_AllocMemory);
    +   if (StrCompare("string:", Path, 7) IS ERR::Okay) {
    +      if ((*Result = StrClone(Path))) return ERR::Okay;
    +      else return log.warning(ERR::AllocMemory);
        }
     
        // Check if the Path argument contains a volume character.  If it does not, make a clone of the string and return it.
    @@ -113,7 +113,7 @@ ERROR ResolvePath(CSTRING Path, RSF Flags, STRING *Result)
        // (ideally with no leading folder references).
     
        if ((!resolved) and ((Flags & RSF::PATH) != RSF::NIL)) {
    -      if (!resolve_path_env(Path, Result)) return ERR_Okay;
    +      if (resolve_path_env(Path, Result) IS ERR::Okay) return ERR::Okay;
        }
     
        if (!resolved) {
    @@ -124,19 +124,19 @@ ERROR ResolvePath(CSTRING Path, RSF Flags, STRING *Result)
        if (resolved) {
           if ((Flags & RSF::APPROXIMATE) != RSF::NIL) {
              StrCopy(Path, dest, sizeof(dest));
    -         if (!test_path(dest, RSF::APPROXIMATE)) Path = dest;
    -         else return ERR_FileNotFound;
    +         if (test_path(dest, RSF::APPROXIMATE) IS ERR::Okay) Path = dest;
    +         else return ERR::FileNotFound;
           }
           else if ((Flags & RSF::NO_FILE_CHECK) IS RSF::NIL) {
              StrCopy(Path, dest, sizeof(dest));
    -         if (!test_path(dest, RSF::NIL)) Path = dest;
    -         else return ERR_FileNotFound;
    +         if (test_path(dest, RSF::NIL) IS ERR::Okay) Path = dest;
    +         else return ERR::FileNotFound;
           }
     
    -      if (!Result) return ERR_Okay;
    -      else if ((*Result = cleaned_path(Path))) return ERR_Okay;
    -      else if ((*Result = StrClone(Path))) return ERR_Okay;
    -      else return log.warning(ERR_AllocMemory);
    +      if (!Result) return ERR::Okay;
    +      else if ((*Result = cleaned_path(Path))) return ERR::Okay;
    +      else if ((*Result = StrClone(Path))) return ERR::Okay;
    +      else return log.warning(ERR::AllocMemory);
        }
     
        StrCopy(Path, src, sizeof(src)); // Copy the Path argument to our internal buffer
    @@ -144,28 +144,28 @@ ERROR ResolvePath(CSTRING Path, RSF Flags, STRING *Result)
        // Keep looping until the volume is resolved
     
        dest[0] = 0;
    -   ERROR error = ERR_Failed;
    +   ERR error = ERR::Failed;
        for (loop=10; loop > 0; loop--) {
           error = resolve(src, dest, Flags);
     
    -      if (error IS ERR_VirtualVolume) {
    +      if (error IS ERR::VirtualVolume) {
              log.trace("Detected virtual volume '%s'", dest);
     
    -         // If RSF::CHECK_VIRTUAL is set, return ERR_VirtualVolume for reserved volume names.
    +         // If RSF::CHECK_VIRTUAL is set, return ERR::VirtualVolume for reserved volume names.
     
    -         if ((Flags & RSF::CHECK_VIRTUAL) IS RSF::NIL) error = ERR_Okay;
    +         if ((Flags & RSF::CHECK_VIRTUAL) IS RSF::NIL) error = ERR::Okay;
     
              if (Result) {
                 if ((Flags & RSF::APPROXIMATE) != RSF::NIL) { // Ensure that the resolved path is accurate
    -               if (test_path(dest, RSF::APPROXIMATE)) error = ERR_FileNotFound;
    +               if (test_path(dest, RSF::APPROXIMATE) != ERR::Okay) error = ERR::FileNotFound;
                 }
     
    -            if (!(*Result = StrClone(dest))) error = ERR_AllocMemory;
    +            if (!(*Result = StrClone(dest))) error = ERR::AllocMemory;
              }
     
              break;
           }
    -      else if (error) break;
    +      else if (error != ERR::Okay) break;
           else {
              #ifdef _WIN32 // UNC network path check
                 if (((dest[0] IS '\\') and (dest[1] IS '\\')) or ((dest[0] IS '/') and (dest[1] IS '/'))) {
    @@ -184,7 +184,7 @@ ERROR ResolvePath(CSTRING Path, RSF Flags, STRING *Result)
              #endif
                 // Copy the destination to the source buffer and repeat the resolution process.
     
    -            if ((Flags & RSF::NO_DEEP_SCAN) != RSF::NIL) return ERR_Failed;
    +            if ((Flags & RSF::NO_DEEP_SCAN) != RSF::NIL) return ERR::Failed;
                 StrCopy(dest, src, sizeof(src));
                 continue; // Keep resolving
              }
    @@ -195,7 +195,7 @@ ERROR ResolvePath(CSTRING Path, RSF Flags, STRING *Result)
     #endif
           if (Result) {
              if (!(*Result = cleaned_path(dest))) {
    -            if (!(*Result = StrClone(dest))) error = ERR_AllocMemory;
    +            if (!(*Result = StrClone(dest))) error = ERR::AllocMemory;
              }
           }
     
    @@ -203,10 +203,10 @@ ERROR ResolvePath(CSTRING Path, RSF Flags, STRING *Result)
        } // for()
     
        if (loop > 0) { // Note that loop starts at 10 and decrements to zero
    -      if ((!error) and (!dest[0])) error = ERR_Failed;
    +      if ((error IS ERR::Okay) and (!dest[0])) error = ERR::Failed;
           return error;
        }
    -   else return ERR_Loop;
    +   else return ERR::Loop;
     }
     
     //********************************************************************************************************************
    @@ -214,7 +214,7 @@ ERROR ResolvePath(CSTRING Path, RSF Flags, STRING *Result)
     
     #ifdef __unix__
     
    -static ERROR resolve_path_env(CSTRING RelativePath, STRING *Result)
    +static ERR resolve_path_env(CSTRING RelativePath, STRING *Result)
     {
        pf::Log log("ResolvePath");
        struct stat64 info;
    @@ -236,7 +236,7 @@ static ERROR resolve_path_env(CSTRING RelativePath, STRING *Result)
              if (!stat64(src, &info)) {
                 if (!S_ISDIR(info.st_mode)) { // Successfully identified file location
                    if (Result) *Result = cleaned_path(src);
    -               return ERR_Okay;
    +               return ERR::Okay;
                 }
              }
     
    @@ -246,12 +246,12 @@ static ERROR resolve_path_env(CSTRING RelativePath, STRING *Result)
        }
        else log.trace("Failed to read PATH environment variable.");
     
    -   return ERR_NothingDone;
    +   return ERR::NothingDone;
     }
     
     #elif _WIN32
     
    -static ERROR resolve_path_env(CSTRING RelativePath, STRING *Result)
    +static ERR resolve_path_env(CSTRING RelativePath, STRING *Result)
     {
        pf::Log log("ResolvePath");
        struct stat64 info;
    @@ -276,7 +276,7 @@ static ERROR resolve_path_env(CSTRING RelativePath, STRING *Result)
              if (!stat64(src, &info)) {
                 if (!S_ISDIR(info.st_mode)) { // Successfully identified file location
                    if (Result) *Result = cleaned_path(src);
    -               return ERR_Okay;
    +               return ERR::Okay;
                 }
              }
     
    @@ -285,7 +285,7 @@ static ERROR resolve_path_env(CSTRING RelativePath, STRING *Result)
        }
        else log.trace("Failed to read PATH environment variable.");
     
    -   return ERR_NothingDone;
    +   return ERR::NothingDone;
     }
     
     #endif
    @@ -299,23 +299,23 @@ static ERROR resolve_path_env(CSTRING RelativePath, STRING *Result)
     ** Flags   - Optional RSF flags.
     */
     
    -static ERROR resolve_object_path(STRING, STRING, STRING, LONG);
    +static ERR resolve_object_path(STRING, STRING, STRING, LONG);
     
    -static ERROR resolve(STRING Source, STRING Dest, RSF Flags)
    +static ERR resolve(STRING Source, STRING Dest, RSF Flags)
     {
        pf::Log log("ResolvePath");
        char fullpath[MAX_FILENAME];
        char buffer[MAX_FILENAME];
        LONG j, k, pos, loop;
    -   ERROR error;
    +   ERR error;
     
        if (get_virtual(Source)) {
           StrCopy(Source, Dest);
    -      return ERR_VirtualVolume;
    +      return ERR::VirtualVolume;
        }
     
        for (pos=0; Source[pos] != ':'; pos++) {
    -      if (!Source[pos]) return log.warning(ERR_InvalidData);
    +      if (!Source[pos]) return log.warning(ERR::InvalidData);
        }
        pos++;
     
    @@ -327,12 +327,12 @@ static ERROR resolve(STRING Source, STRING Dest, RSF Flags)
           }
           else fullpath[0] = 0;
        }
    -   else return log.warning(ERR_SystemLocked);
    +   else return log.warning(ERR::SystemLocked);
     
        if (!fullpath[0]) {
           log.msg("No matching volume for \"%s\".", Source);
           Source[pos-1] = ':'; // Put back the volume symbol
    -      return ERR_Search;
    +      return ERR::Search;
        }
     
        Source[pos-1] = ':'; // Restore the volume symbol
    @@ -348,15 +348,15 @@ static ERROR resolve(STRING Source, STRING Dest, RSF Flags)
        // Check if the EXT: reference is used.  If so, respond by loading the module or class that handles the volume.
        // The loaded code should replace the volume with the correct information for discovery on the next resolution phase.
     
    -   if (!StrCompare("EXT:", path, 4, STR::MATCH_CASE)) {
    +   if (StrCompare("EXT:", path, 4, STR::MATCH_CASE) IS ERR::Okay) {
           StrCopy(Source, Dest, MAX_FILENAME); // Return an exact duplicate of the original source string
     
           if (get_virtual(Source)) {
    -         return ERR_VirtualVolume;
    +         return ERR::VirtualVolume;
           }
     
           if (tlClassLoaded) { // Already attempted to load the module on a previous occasion - we must fail
    -         return ERR_Failed;
    +         return ERR::Failed;
           }
     
           // An external reference can refer to a module for auto-loading (preferred) or a class name.
    @@ -365,7 +365,7 @@ static ERROR resolve(STRING Source, STRING Dest, RSF Flags)
           if (!mod.ok()) FindClass(ResolveClassName(path + 4));
     
           tlClassLoaded = true; // This setting will prevent recursion
    -      return ERR_VirtualVolume;
    +      return ERR::VirtualVolume;
        }
     
        while (*path) {
    @@ -400,12 +400,12 @@ static ERROR resolve(STRING Source, STRING Dest, RSF Flags)
              for (j=0; (Dest[j]) and (Dest[j] != ':') and (Dest[j] != '/'); j++);
           #endif
     
    -      error = -1;
    +      error = ERR(-1);
           for (loop=10; loop > 0; loop--) {
              if ((Dest[j] IS ':') and (j > 1)) { // Remaining ':' indicates more path resolution is required.
                 error = resolve(Dest, buffer, Flags);
     
    -            if (!error) {
    +            if (error IS ERR::Okay) {
                    // Copy the result from buffer to Dest.
                    for (j=0; buffer[j]; j++) Dest[j] = buffer[j];
                    Dest[j] = 0;
    @@ -420,21 +420,21 @@ static ERROR resolve(STRING Source, STRING Dest, RSF Flags)
     
           if (loop <= 0) {
              log.warning("Infinite loop on path '%s'", Dest);
    -         return ERR_Loop;
    +         return ERR::Loop;
           }
     
    -      if (!error) return ERR_Okay;
    +      if (error IS ERR::Okay) return ERR::Okay;
     
           // Return now if no file checking is to be performed
     
           if ((Flags & RSF::NO_FILE_CHECK) != RSF::NIL) {
              log.trace("No file check will be performed.");
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
     
    -      if (!test_path(Dest, Flags)) {
    +      if (test_path(Dest, Flags) IS ERR::Okay) {
              log.trace("File found, path resolved successfully.");
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
     
           log.trace("File does not exist at %s", Dest);
    @@ -448,28 +448,28 @@ static ERROR resolve(STRING Source, STRING Dest, RSF Flags)
        }
     
        log.trace("Resolved path but no matching file for %s\"%s\".", ((Flags & RSF::APPROXIMATE) != RSF::NIL) ? "~" : "", Source);
    -   return ERR_FileNotFound;
    +   return ERR::FileNotFound;
     }
     
     //********************************************************************************************************************
     // For cases such as ":SystemIcons", we find the referenced object and ask it to resolve the path for us.  (In effect,
     // the object will be used as a plugin for volume resolution).
     //
    -// If the path is merely ":" or resolve_virtual() returns ERR_VirtualVolume, return the VirtualVolume error code to
    +// If the path is merely ":" or resolve_virtual() returns ERR::VirtualVolume, return the VirtualVolume error code to
     // indicate that no further resolution is required.
     
    -static ERROR resolve_object_path(STRING Path, STRING Source, STRING Dest, LONG PathSize)
    +static ERR resolve_object_path(STRING Path, STRING Source, STRING Dest, LONG PathSize)
     {
        pf::Log log("ResolvePath");
    -   ERROR (*resolve_virtual)(OBJECTPTR, STRING, STRING, LONG);
    -   ERROR error = ERR_VirtualVolume;
    +   ERR (*resolve_virtual)(OBJECTPTR, STRING, STRING, LONG);
    +   ERR error = ERR::VirtualVolume;
     
        if (Path[0]) {
           OBJECTID volume_id;
    -      if (!FindObject(Path, 0, FOF::NIL, &volume_id)) {
    +      if (FindObject(Path, 0, FOF::NIL, &volume_id) IS ERR::Okay) {
              OBJECTPTR object;
    -         if (!AccessObject(volume_id, 5000, &object)) {
    -            if ((!object->getPtr(FID_ResolvePath, &resolve_virtual)) and (resolve_virtual)) {
    +         if (AccessObject(volume_id, 5000, &object) IS ERR::Okay) {
    +            if ((object->getPtr(FID_ResolvePath, &resolve_virtual) IS ERR::Okay) and (resolve_virtual)) {
                    error = resolve_virtual(object, Source, Dest, PathSize);
                 }
                 ReleaseObject(object);
    @@ -477,10 +477,10 @@ static ERROR resolve_object_path(STRING Path, STRING Source, STRING Dest, LONG P
           }
        }
     
    -   if (error IS ERR_VirtualVolume) { // Return an exact duplicate of the original source string
    +   if (error IS ERR::VirtualVolume) { // Return an exact duplicate of the original source string
           StrCopy(Source, Dest);
    -      return ERR_VirtualVolume;
    +      return ERR::VirtualVolume;
        }
    -   else if (error != ERR_Okay) return log.warning(error);
    -   else return ERR_Okay;
    +   else if (error != ERR::Okay) return log.warning(error);
    +   else return ERR::Okay;
     }
    diff --git a/src/core/fs_volumes.cpp b/src/core/fs_volumes.cpp
    index 9b20047f0..509d94039 100644
    --- a/src/core/fs_volumes.cpp
    +++ b/src/core/fs_volumes.cpp
    @@ -26,11 +26,11 @@ NoPermission: An attempt to delete a system volume was denied.
     
     *********************************************************************************************************************/
     
    -ERROR DeleteVolume(CSTRING Name)
    +ERR DeleteVolume(CSTRING Name)
     {
        pf::Log log(__FUNCTION__);
     
    -   if ((!Name) or (!Name[0])) return ERR_NullArgs;
    +   if ((!Name) or (!Name[0])) return ERR::NullArgs;
     
        log.branch("Name: %s", Name);
     
    @@ -40,14 +40,14 @@ ERROR DeleteVolume(CSTRING Name)
           std::string vol(Name, i);
     
           if (glVolumes.contains(vol)) {
    -         if (glVolumes[vol]["System"] == "Yes") return log.warning(ERR_NoPermission);
    +         if (glVolumes[vol]["System"] == "Yes") return log.warning(ERR::NoPermission);
     
              glVolumes.erase(vol);
           }
     
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return log.warning(ERR_SystemLocked);
    +   else return log.warning(ERR::SystemLocked);
     }
     
     /*********************************************************************************************************************
    @@ -58,7 +58,7 @@ RenameVolume: Renames a volume.
     
     *********************************************************************************************************************/
     
    -ERROR RenameVolume(CSTRING Volume, CSTRING Name)
    +ERR RenameVolume(CSTRING Volume, CSTRING Name)
     {
        pf::Log log(__FUNCTION__);
     
    @@ -85,12 +85,12 @@ ERROR RenameVolume(CSTRING Volume, CSTRING Name)
              ((EVENTID *)evcreated.get())[0] = EVID_FILESYSTEM_VOLUME_CREATED;
              CopyMemory(Name, evcreated.get() + sizeof(EVENTID), namelen);
              BroadcastEvent(evcreated.get(), sizeof(EVENTID) + namelen);
    -         return ERR_Okay;
    +         return ERR::Okay;
           }
     
    -      return ERR_Search;
    +      return ERR::Search;
        }
    -   else return log.warning(ERR_LockFailed);
    +   else return log.warning(ERR::LockFailed);
     }
     
     /*********************************************************************************************************************
    @@ -121,11 +121,11 @@ NullArgs: A valid name and path string was not provided.
     
     *********************************************************************************************************************/
     
    -ERROR SetVolume(CSTRING Name, CSTRING Path, CSTRING Icon, CSTRING Label, CSTRING Device, VOLUME Flags)
    +ERR SetVolume(CSTRING Name, CSTRING Path, CSTRING Icon, CSTRING Label, CSTRING Device, VOLUME Flags)
     {
        pf::Log log(__FUNCTION__);
     
    -   if ((!Name) or (!Path)) return log.warning(ERR_NullArgs);
    +   if ((!Name) or (!Path)) return log.warning(ERR::NullArgs);
     
        std::string name;
     
    @@ -145,7 +145,7 @@ ERROR SetVolume(CSTRING Name, CSTRING Path, CSTRING Icon, CSTRING Label, CSTRING
                 auto &keys = glVolumes[name];
                 if ((Flags & VOLUME::PRIORITY) != VOLUME::NIL) keys["Path"] = std::string(Path) + "|" + keys["Path"];
                 else keys["Path"] = keys["Path"] + "|" + Path;
    -            return ERR_Okay;
    +            return ERR::Okay;
              }
           }
     
    @@ -164,9 +164,9 @@ ERROR SetVolume(CSTRING Name, CSTRING Path, CSTRING Icon, CSTRING Label, CSTRING
           ((EVENTID *)evbuf.get())[0] = GetEventID(EVG::FILESYSTEM, "volume", "created");
           CopyMemory(name.c_str(), evbuf.get() + sizeof(EVENTID), name.size() + 1);
           BroadcastEvent(evbuf.get(), sizeof(EVENTID) + name.size() + 1);
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return log.warning(ERR_SystemLocked);
    +   else return log.warning(ERR::SystemLocked);
     }
     
     /*********************************************************************************************************************
    @@ -190,31 +190,31 @@ Exists: The named volume already exists.
     
     *********************************************************************************************************************/
     
    -using CALL_CLOSE_DIR       = ERROR (*)(DirInfo *);
    -using CALL_DELETE          = ERROR (*)(STRING, FUNCTION *);
    -using CALL_GET_INFO        = ERROR (*)(CSTRING, FileInfo*, LONG);
    -using CALL_GET_DEVICE_INFO = ERROR (*)(CSTRING, objStorageDevice*);
    -using CALL_IDENTIFY_FILE   = ERROR (*)(STRING, CLASSID*, CLASSID*);
    +using CALL_CLOSE_DIR       = ERR (*)(DirInfo *);
    +using CALL_DELETE          = ERR (*)(STRING, FUNCTION *);
    +using CALL_GET_INFO        = ERR (*)(CSTRING, FileInfo*, LONG);
    +using CALL_GET_DEVICE_INFO = ERR (*)(CSTRING, objStorageDevice*);
    +using CALL_IDENTIFY_FILE   = ERR (*)(STRING, CLASSID*, CLASSID*);
     using CALL_IGNORE_FILE     = void  (*)(extFile*);
    -using CALL_MAKE_DIR        = ERROR (*)(CSTRING, PERMIT);
    -using CALL_OPEN_DIR        = ERROR (*)(DirInfo*);
    -using CALL_RENAME          = ERROR (*)(STRING, STRING);
    -using CALL_SAME_FILE       = ERROR (*)(CSTRING, CSTRING);
    -using CALL_SCAN_DIR        = ERROR (*)(DirInfo*);
    -using CALL_TEST_PATH       = ERROR (*)(CSTRING, RSF, LOC *);
    -using CALL_WATCH_PATH      = ERROR (*)(extFile*);
    -
    -ERROR VirtualVolume(CSTRING Name, ...)
    +using CALL_MAKE_DIR        = ERR (*)(CSTRING, PERMIT);
    +using CALL_OPEN_DIR        = ERR (*)(DirInfo*);
    +using CALL_RENAME          = ERR (*)(STRING, STRING);
    +using CALL_SAME_FILE       = ERR (*)(CSTRING, CSTRING);
    +using CALL_SCAN_DIR        = ERR (*)(DirInfo*);
    +using CALL_TEST_PATH       = ERR (*)(CSTRING, RSF, LOC *);
    +using CALL_WATCH_PATH      = ERR (*)(extFile*);
    +
    +ERR VirtualVolume(CSTRING Name, ...)
     {
        pf::Log log(__FUNCTION__);
     
    -   if ((!Name) or (!Name[0])) return log.warning(ERR_NullArgs);
    +   if ((!Name) or (!Name[0])) return log.warning(ERR::NullArgs);
     
        log.branch("%s", Name);
     
        auto id = StrHash(Name, FALSE);
     
    -   if (glVirtual.contains(id)) return ERR_Exists;
    +   if (glVirtual.contains(id)) return ERR::Exists;
     
        LONG i = StrCopy(Name, glVirtual[id].Name, sizeof(glVirtual[id].Name)-2);
        glVirtual[id].Name[i++]     = ':';
    @@ -230,7 +230,7 @@ ERROR VirtualVolume(CSTRING Name, ...)
              case VAS::DEREGISTER:
                 glVirtual.erase(id);
                 va_end(list);
    -            return ERR_Okay; // The volume has been removed, so any further tags are redundant.
    +            return ERR::Okay; // The volume has been removed, so any further tags are redundant.
     
              case VAS::DRIVER_SIZE:     glVirtual[id].DriverSize = va_arg(list, LONG); break;
              case VAS::CASE_SENSITIVE:  glVirtual[id].CaseSensitive = va_arg(list, LONG) ? true : false; break;
    @@ -251,11 +251,11 @@ ERROR VirtualVolume(CSTRING Name, ...)
              default:
                 log.warning("Bad VAS tag $%.8x @ pair index %d, aborting.", tagid, arg);
                 va_end(list);
    -            return ERR_Args;
    +            return ERR::Args;
           }
           arg++;
        }
     
        va_end(list);
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
    diff --git a/src/core/fs_watch_path.cpp b/src/core/fs_watch_path.cpp
    index 1c47860f6..a23aff69d 100644
    --- a/src/core/fs_watch_path.cpp
    +++ b/src/core/fs_watch_path.cpp
    @@ -33,7 +33,7 @@ extern "C" void path_monitor(HOSTHANDLE, extFile *);
     
     #ifdef __linux__
     
    -ERROR fs_watch_path(extFile *File)
    +ERR fs_watch_path(extFile *File)
     {
        pf::Log log;
        STRING path;
    @@ -57,33 +57,33 @@ ERROR fs_watch_path(extFile *File)
           if (handle IS -1) {
              log.warning("%s", strerror(errno));
              FreeResource(path);
    -         return ERR_SystemCall;
    +         return ERR::SystemCall;
           }
     
           File->prvWatch->Handle = handle;
     
           FreeResource(path);
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
     
    -   return ERR_AllocMemory;
    +   return ERR::AllocMemory;
     }
     
     #elif _WIN32
     
    -ERROR fs_watch_path(extFile *File)
    +ERR fs_watch_path(extFile *File)
     {
        pf::Log log(__FUNCTION__);
        HOSTHANDLE handle;
        LONG winflags;
    -   ERROR error;
    +   ERR error;
     
        // The path_monitor() function will be called whenever the Path or its content is modified.
     
    -   if (!(error = winWatchFile(LONG(File->prvWatch->Flags), File->prvResolvedPath, (File->prvWatch + 1), &handle, &winflags))) {
    +   if ((error = winWatchFile(LONG(File->prvWatch->Flags), File->prvResolvedPath, (File->prvWatch + 1), &handle, &winflags)) IS ERR::Okay) {
           File->prvWatch->Handle   = handle;
           File->prvWatch->WinFlags = winflags;
    -      if (!(error = RegisterFD(handle, RFD::READ, (void (*)(HOSTHANDLE, void*))&path_monitor, File))) {
    +      if ((error = RegisterFD(handle, RFD::READ, (void (*)(HOSTHANDLE, void*))&path_monitor, File)) IS ERR::Okay) {
           }
           else log.warning("Failed to register folder handle.");
        }
    @@ -94,9 +94,9 @@ ERROR fs_watch_path(extFile *File)
     
     #else
     
    -ERROR fs_watch_path(extFile *File)
    +ERR fs_watch_path(extFile *File)
     {
    -   return ERR_NoSupport;
    +   return ERR::NoSupport;
     }
     
     #endif
    @@ -185,21 +185,15 @@ void path_monitor(HOSTHANDLE FD, extFile *File)
              if (event->mask & IN_ISDIR) flags |= MFF::FOLDER;
              else flags |= MFF::FILE;
     
    -         ERROR error;
    +         ERR error;
              if (flags != MFF::NIL) {
    -            if (glFileMonitor[i].Routine.Type IS CALL_STDC) {
    -               ERROR (*routine)(extFile *File, CSTRING path, LARGE Custom, MFF Flags);
    +            if (glFileMonitor[i].Routine.isC()) {
    +               ERR (*routine)(extFile *, CSTRING path, LARGE Custom, MFF Flags, APTR);
                    routine = glFileMonitor[i].Routine.StdC.Routine;
    -
    -               OBJECTPTR context;
    -               if (glFileMonitor[i].Context) context = SetContext(glFileMonitor[i].Context);
    -               else context = NULL;
    -
    -               error = routine(glFileMonitor[i].File, path, glFileMonitor[i].Custom, flags);
    -
    -               if (context) SetContext(context);
    +               pf::SwitchContext context(glFileMonitor[i].Routine.StdC.Context);
    +               error = routine(glFileMonitor[i].File, path, glFileMonitor[i].Custom, flags, glFileMonitor[i].Routine.StdC.Meta);
                 }
    -            else if (glFileMonitor[i].Routine.Type IS CALL_SCRIPT) {
    +            else if (glFileMonitor[i].Routine.isScript()) {
                    if (auto script = tlFeedback.Script.Script) {
                       const ScriptArg args[] = {
                          { "File",   glFileMonitor[i].File },
    @@ -207,12 +201,12 @@ void path_monitor(HOSTHANDLE FD, extFile *File)
                          { "Custom", glFileMonitor[i].Custom },
                          { "Flags",  LONG(flags) }
                       };
    -                  if (scCallback(script, tlFeedback.Script.ProcedureID, args, ARRAYSIZE(args), &error)) error = ERR_Failed;
    +                  if (scCallback(script, tlFeedback.Script.ProcedureID, args, std::ssize(args), &error)) error = ERR::Failed;
                    }
    -               else error = ERR_Terminate;
    +               else error = ERR::Terminate;
                 }
     
    -            if (error IS ERR_Terminate) Action(MT_FlWatch, glFileMonitor[i].File, NULL);
    +            if (error IS ERR::Terminate) Action(MT_FlWatch, glFileMonitor[i].File, NULL);
              }
              else log.warning("Flags $%.8x not recognised.", LONG(flags));
              break;
    @@ -243,16 +237,15 @@ void path_monitor(HOSTHANDLE Handle, extFile *File)
     {
        pf::Log log(__FUNCTION__);
     
    -   static THREADVAR BYTE recursion = FALSE; // Recursion avoidance is essential for correct queuing
    +   static THREADVAR bool recursion = false; // Recursion avoidance is essential for correct queuing
        if ((recursion) or (!File->prvWatch)) return;
    -   recursion = TRUE;
    +   recursion = true;
     
        AdjustLogLevel(2);
     
        log.branch("File monitoring event received (Handle %p, File #%d).", Handle, File->UID);
     
    -   ERROR error;
    -   ERROR (*routine)(extFile *, CSTRING path, LARGE Custom, LONG Flags);
    +   ERR error;
        if (File->prvWatch->Handle) {
           char path[256];
           LONG status;
    @@ -266,44 +259,35 @@ void path_monitor(HOSTHANDLE Handle, extFile *File)
                 if (path[i] IS '\\') continue;
              }
     
    -         if (File->prvWatch->Routine.StdC.Context) {
    -            pf::SwitchContext context(File->prvWatch->Routine.StdC.Context);
     
    -            if (File->prvWatch->Routine.Type IS CALL_STDC) {
    -               routine = (ERROR (*)(extFile *, CSTRING, LARGE, LONG))File->prvWatch->Routine.StdC.Routine;
    -               error = routine(File, path, File->prvWatch->Custom, status);
    -            }
    -            else if (File->prvWatch->Routine.Type IS CALL_SCRIPT) {
    -               if (auto script = File->prvWatch->Routine.Script.Script) {
    -                  const ScriptArg args[] = {
    -                     { "File",   File, FD_OBJECTPTR },
    -                     { "Path",   path },
    -                     { "Custom", File->prvWatch->Custom },
    -                     { "Flags",  0 }
    -                  };
    -                  if (scCallback(script, File->prvWatch->Routine.Script.ProcedureID, args, ARRAYSIZE(args), &error)) error = ERR_Failed;
    -               }
    -               else error = ERR_Terminate;
    -            }
    -            else error = ERR_Terminate;
    +         if (File->prvWatch->Routine.isC()) {
    +            pf::SwitchContext context(File->prvWatch->Routine.StdC.Context);
    +            auto routine = (ERR (*)(extFile *, CSTRING, LARGE, LONG, APTR))File->prvWatch->Routine.StdC.Routine;
    +            error = routine(File, path, File->prvWatch->Custom, status, File->prvWatch->Routine.StdC.Meta);
              }
    -         else {
    -            routine = (ERROR (*)(extFile *, CSTRING, LARGE, LONG))File->prvWatch->Routine.StdC.Routine;
    -            error = routine(File, path, File->prvWatch->Custom, status);
    +         else if (File->prvWatch->Routine.isScript()) {
    +            if (auto script = File->prvWatch->Routine.Script.Script) {
    +               const ScriptArg args[] = {
    +                  { "File",   File, FD_OBJECTPTR },
    +                  { "Path",   path },
    +                  { "Custom", File->prvWatch->Custom },
    +                  { "Flags",  0 }
    +               };
    +               if (scCallback(script, File->prvWatch->Routine.Script.ProcedureID, args, std::ssize(args), &error) != ERR::Okay) error = ERR::Failed;
    +            }
    +            else error = ERR::Terminate;
              }
    +         else error = ERR::Terminate;
     
    -         if (error IS ERR_Terminate) Action(MT_FlWatch, File, NULL);
    +         if (error IS ERR::Terminate) Action(MT_FlWatch, File, NULL);
           }
        }
        else {
    -      routine = (ERROR (*)(extFile *, CSTRING, LARGE, LONG))File->prvWatch->Routine.StdC.Routine;
    -      if (File->prvWatch->Routine.StdC.Context) {
    -         pf::SwitchContext context(File->prvWatch->Routine.StdC.Context);
    -         error = routine(File, File->Path, File->prvWatch->Custom, 0);
    -      }
    -      else error = routine(File, File->Path, File->prvWatch->Custom, 0);
    +      auto routine = (ERR (*)(extFile *, CSTRING, LARGE, LONG, APTR))File->prvWatch->Routine.StdC.Routine;
    +      pf::SwitchContext context(File->prvWatch->Routine.StdC.Context);
    +      error = routine(File, File->Path, File->prvWatch->Custom, 0, File->prvWatch->Routine.StdC.Meta);
     
    -      if (error IS ERR_Terminate) Action(MT_FlWatch, File, NULL);
    +      if (error IS ERR::Terminate) Action(MT_FlWatch, File, NULL);
        }
     
        winFindNextChangeNotification(Handle);
    diff --git a/src/core/idl.h b/src/core/idl.h
    index 58b0f54b8..735a98eee 100644
    --- a/src/core/idl.h
    +++ b/src/core/idl.h
    @@ -1 +1 @@
    -char glIDL[] = { 115,46,73,110,112,117,116,69,118,101,110,116,58,112,78,101,120,116,58,73,110,112,117,116,69,118,101,110,116,44,100,86,97,108,117,101,44,120,84,105,109,101,115,116,97,109,112,44,108,82,101,99,105,112,105,101,110,116,73,68,44,108,79,118,101,114,73,68,44,100,65,98,115,88,44,100,65,98,115,89,44,100,88,44,100,89,44,108,68,101,118,105,99,101,73,68,44,108,84,121,112,101,44,108,70,108,97,103,115,44,108,77,97,115,107,10,115,46,100,99,82,101,113,117,101,115,116,58,108,73,116,101,109,44,99,80,114,101,102,101,114,101,110,99,101,91,52,93,10,115,46,100,99,65,117,100,105,111,58,108,83,105,122,101,44,108,70,111,114,109,97,116,10,115,46,100,99,75,101,121,69,110,116,114,121,58,108,70,108,97,103,115,44,108,86,97,108,117,101,44,120,84,105,109,101,115,116,97,109,112,44,108,85,110,105,99,111,100,101,10,115,46,100,99,68,101,118,105,99,101,73,110,112,117,116,58,100,86,97,108,117,101,44,120,84,105,109,101,115,116,97,109,112,44,108,68,101,118,105,99,101,73,68,44,108,70,108,97,103,115,44,108,84,121,112,101,10,115,46,68,97,116,101,84,105,109,101,58,108,89,101,97,114,44,108,77,111,110,116,104,44,108,68,97,121,44,108,72,111,117,114,44,108,77,105,110,117,116,101,44,108,83,101,99,111,110,100,44,108,84,105,109,101,90,111,110,101,10,115,46,72,83,86,58,100,72,117,101,44,100,83,97,116,117,114,97,116,105,111,110,44,100,86,97,108,117,101,10,115,46,70,82,71,66,58,102,82,101,100,44,102,71,114,101,101,110,44,102,66,108,117,101,44,102,65,108,112,104,97,10,115,46,82,71,66,56,58,117,99,82,101,100,44,117,99,71,114,101,101,110,44,117,99,66,108,117,101,44,117,99,65,108,112,104,97,10,115,46,82,71,66,49,54,58,117,119,82,101,100,44,117,119,71,114,101,101,110,44,117,119,66,108,117,101,44,117,119,65,108,112,104,97,10,115,46,82,71,66,51,50,58,117,108,82,101,100,44,117,108,71,114,101,101,110,44,117,108,66,108,117,101,44,117,108,65,108,112,104,97,10,115,46,82,71,66,80,97,108,101,116,116,101,58,108,65,109,116,67,111,108,111,117,114,115,44,101,67,111,108,58,82,71,66,56,91,50,53,54,93,10,115,46,67,111,108,111,117,114,70,111,114,109,97,116,58,117,99,82,101,100,83,104,105,102,116,44,117,99,71,114,101,101,110,83,104,105,102,116,44,117,99,66,108,117,101,83,104,105,102,116,44,117,99,65,108,112,104,97,83,104,105,102,116,44,117,99,82,101,100,77,97,115,107,44,117,99,71,114,101,101,110,77,97,115,107,44,117,99,66,108,117,101,77,97,115,107,44,117,99,65,108,112,104,97,77,97,115,107,44,117,99,82,101,100,80,111,115,44,117,99,71,114,101,101,110,80,111,115,44,117,99,66,108,117,101,80,111,115,44,117,99,65,108,112,104,97,80,111,115,44,117,99,66,105,116,115,80,101,114,80,105,120,101,108,10,115,46,67,108,105,112,82,101,99,116,97,110,103,108,101,58,108,76,101,102,116,44,108,84,111,112,44,108,82,105,103,104,116,44,108,66,111,116,116,111,109,10,115,46,69,100,103,101,115,58,108,76,101,102,116,44,108,84,111,112,44,108,82,105,103,104,116,44,108,66,111,116,116,111,109,10,115,46,79,98,106,101,99,116,83,105,103,110,97,108,58,111,79,98,106,101,99,116,10,115,46,112,102,66,97,115,101,54,52,68,101,99,111,100,101,58,117,99,83,116,101,112,44,117,99,80,108,97,105,110,67,104,97,114,44,117,99,66,105,116,10,115,46,112,102,66,97,115,101,54,52,69,110,99,111,100,101,58,117,99,83,116,101,112,44,117,99,82,101,115,117,108,116,44,108,83,116,101,112,67,111,117,110,116,10,115,46,70,117,110,99,116,105,111,110,70,105,101,108,100,58,115,78,97,109,101,44,117,108,84,121,112,101,10,115,46,70,117,110,99,116,105,111,110,58,112,65,100,100,114,101,115,115,44,115,78,97,109,101,44,112,65,114,103,115,58,70,117,110,99,116,105,111,110,70,105,101,108,100,10,115,46,70,105,101,108,100,65,114,114,97,121,58,115,78,97,109,101,44,112,71,101,116,70,105,101,108,100,44,112,83,101,116,70,105,101,108,100,44,109,65,114,103,44,117,108,70,108,97,103,115,10,115,46,70,105,101,108,100,68,101,102,58,115,78,97,109,101,44,108,86,97,108,117,101,10,115,46,83,121,115,116,101,109,83,116,97,116,101,58,115,80,108,97,116,102,111,114,109,44,108,67,111,110,115,111,108,101,70,68,44,108,83,116,97,103,101,10,115,46,86,97,114,105,97,98,108,101,58,117,108,84,121,112,101,44,108,85,110,117,115,101,100,44,120,76,97,114,103,101,44,100,68,111,117,98,108,101,44,112,80,111,105,110,116,101,114,10,115,46,65,99,116,105,111,110,65,114,114,97,121,58,112,82,111,117,116,105,110,101,44,108,65,99,116,105,111,110,67,111,100,101,10,115,46,65,99,116,105,111,110,84,97,98,108,101,58,117,108,72,97,115,104,44,108,83,105,122,101,44,115,78,97,109,101,44,112,65,114,103,115,58,70,117,110,99,116,105,111,110,70,105,101,108,100,10,115,46,67,104,105,108,100,69,110,116,114,121,58,108,79,98,106,101,99,116,73,68,44,117,108,67,108,97,115,115,73,68,10,115,46,77,101,115,115,97,103,101,58,120,84,105,109,101,44,108,85,73,68,44,108,84,121,112,101,44,108,83,105,122,101,10,115,46,77,101,109,73,110,102,111,58,112,83,116,97,114,116,44,108,79,98,106,101,99,116,73,68,44,117,108,83,105,122,101,44,108,70,108,97,103,115,44,108,77,101,109,111,114,121,73,68,44,119,65,99,99,101,115,115,67,111,117,110,116,10,115,46,67,111,109,112,114,101,115,115,105,111,110,70,101,101,100,98,97,99,107,58,108,70,101,101,100,98,97,99,107,73,68,44,108,73,110,100,101,120,44,115,80,97,116,104,44,115,68,101,115,116,44,120,80,114,111,103,114,101,115,115,44,120,79,114,105,103,105,110,97,108,83,105,122,101,44,120,67,111,109,112,114,101,115,115,101,100,83,105,122,101,44,119,89,101,97,114,44,119,77,111,110,116,104,44,119,68,97,121,44,119,72,111,117,114,44,119,77,105,110,117,116,101,44,119,83,101,99,111,110,100,10,115,46,67,111,109,112,114,101,115,115,101,100,73,116,101,109,58,120,79,114,105,103,105,110,97,108,83,105,122,101,44,120,67,111,109,112,114,101,115,115,101,100,83,105,122,101,44,112,78,101,120,116,58,67,111,109,112,114,101,115,115,101,100,73,116,101,109,44,115,80,97,116,104,44,108,80,101,114,109,105,115,115,105,111,110,115,44,108,85,115,101,114,73,68,44,108,71,114,111,117,112,73,68,44,108,79,116,104,101,114,115,73,68,44,108,70,108,97,103,115,44,101,67,114,101,97,116,101,100,58,68,97,116,101,84,105,109,101,44,101,77,111,100,105,102,105,101,100,58,68,97,116,101,84,105,109,101,10,115,46,70,105,108,101,73,110,102,111,58,120,83,105,122,101,44,120,84,105,109,101,83,116,97,109,112,44,112,78,101,120,116,58,70,105,108,101,73,110,102,111,44,115,78,97,109,101,44,108,70,108,97,103,115,44,108,80,101,114,109,105,115,115,105,111,110,115,44,108,85,115,101,114,73,68,44,108,71,114,111,117,112,73,68,44,101,67,114,101,97,116,101,100,58,68,97,116,101,84,105,109,101,44,101,77,111,100,105,102,105,101,100,58,68,97,116,101,84,105,109,101,10,115,46,68,105,114,73,110,102,111,58,112,73,110,102,111,58,70,105,108,101,73,110,102,111,10,115,46,70,105,108,101,70,101,101,100,98,97,99,107,58,120,83,105,122,101,44,120,80,111,115,105,116,105,111,110,44,115,80,97,116,104,44,115,68,101,115,116,44,108,70,101,101,100,98,97,99,107,73,68,44,99,82,101,115,101,114,118,101,100,91,51,50,93,10,115,46,70,105,101,108,100,58,109,65,114,103,44,112,71,101,116,86,97,108,117,101,44,112,83,101,116,86,97,108,117,101,44,112,87,114,105,116,101,86,97,108,117,101,44,115,78,97,109,101,44,117,108,70,105,101,108,100,73,68,44,117,119,79,102,102,115,101,116,44,117,119,73,110,100,101,120,44,117,108,70,108,97,103,115,10,99,46,65,67,58,65,99,116,105,118,97,116,101,61,48,120,50,44,67,108,101,97,114,61,48,120,52,44,67,108,105,112,98,111,97,114,100,61,48,120,50,100,44,67,111,112,121,68,97,116,97,61,48,120,55,44,67,117,115,116,111,109,61,48,120,51,52,44,68,97,116,97,70,101,101,100,61,48,120,56,44,68,101,97,99,116,105,118,97,116,101,61,48,120,57,44,68,105,115,97,98,108,101,61,48,120,50,102,44,68,114,97,103,68,114,111,112,61,48,120,49,48,44,68,114,97,119,61,48,120,97,44,69,78,68,61,48,120,51,53,44,69,110,97,98,108,101,61,48,120,51,48,44,70,108,117,115,104,61,48,120,98,44,70,111,99,117,115,61,48,120,99,44,70,114,101,101,61,48,120,100,44,70,114,101,101,87,97,114,110,105,110,103,61,48,120,53,44,71,101,116,86,97,114,61,48,120,102,44,72,105,100,101,61,48,120,49,49,44,73,110,105,116,61,48,120,49,50,44,76,111,99,107,61,48,120,49,51,44,76,111,115,116,70,111,99,117,115,61,48,120,49,52,44,77,111,118,101,61,48,120,49,53,44,77,111,118,101,84,111,66,97,99,107,61,48,120,49,54,44,77,111,118,101,84,111,70,114,111,110,116,61,48,120,49,55,44,77,111,118,101,84,111,80,111,105,110,116,61,48,120,51,50,44,78,101,119,67,104,105,108,100,61,48,120,49,56,44,78,101,119,79,98,106,101,99,116,61,48,120,49,97,44,78,101,119,79,119,110,101,114,61,48,120,49,57,44,78,101,120,116,61,48,120,50,57,44,80,114,101,118,61,48,120,50,97,44,81,117,101,114,121,61,48,120,49,99,44,82,101,97,100,61,48,120,49,100,44,82,101,100,105,109,101,110,115,105,111,110,61,48,120,51,49,44,82,101,100,111,61,48,120,49,98,44,82,101,102,114,101,115,104,61,48,120,50,101,44,82,101,110,97,109,101,61,48,120,49,101,44,82,101,115,101,116,61,48,120,49,102,44,82,101,115,105,122,101,61,48,120,50,48,44,83,97,118,101,73,109,97,103,101,61,48,120,50,49,44,83,97,118,101,83,101,116,116,105,110,103,115,61,48,120,101,44,83,97,118,101,84,111,79,98,106,101,99,116,61,48,120,50,50,44,83,99,114,111,108,108,61,48,120,50,51,44,83,99,114,111,108,108,84,111,80,111,105,110,116,61,48,120,51,51,44,83,101,101,107,61,48,120,50,52,44,83,101,108,101,99,116,65,114,101,97,61,48,120,51,44,83,101,116,70,105,101,108,100,61,48,120,50,99,44,83,101,116,86,97,114,61,48,120,50,53,44,83,104,111,119,61,48,120,50,54,44,83,105,103,110,97,108,61,48,120,49,44,83,111,114,116,61,48,120,54,44,85,110,100,111,61,48,120,50,55,44,85,110,108,111,99,107,61,48,120,50,56,44,87,114,105,116,101,61,48,120,50,98,10,99,46,65,76,73,71,78,58,66,79,84,84,79,77,61,48,120,50,48,44,67,69,78,84,69,82,61,48,120,99,44,72,79,82,73,90,79,78,84,65,76,61,48,120,52,44,76,69,70,84,61,48,120,49,44,77,73,68,68,76,69,61,48,120,99,44,82,73,71,72,84,61,48,120,50,44,84,79,80,61,48,120,49,48,44,86,69,82,84,73,67,65,76,61,48,120,56,10,99,46,67,67,70,58,65,85,68,73,79,61,48,120,50,48,48,44,67,79,77,77,65,78,68,61,48,120,49,44,68,65,84,65,61,48,120,52,48,48,44,68,82,65,87,65,66,76,69,61,48,120,50,44,69,70,70,69,67,84,61,48,120,52,44,70,73,76,69,83,89,83,84,69,77,61,48,120,56,44,71,82,65,80,72,73,67,83,61,48,120,49,48,44,71,85,73,61,48,120,50,48,44,73,79,61,48,120,52,48,44,77,73,83,67,61,48,120,56,48,48,44,77,85,76,84,73,77,69,68,73,65,61,48,120,50,48,48,48,44,78,69,84,87,79,82,75,61,48,120,49,48,48,48,44,83,89,83,84,69,77,61,48,120,56,48,44,84,79,79,76,61,48,120,49,48,48,10,99,46,67,70,58,68,69,70,76,65,84,69,61,48,120,51,44,71,90,73,80,61,48,120,49,44,90,76,73,66,61,48,120,50,10,99,46,67,76,70,58,78,79,95,79,87,78,69,82,83,72,73,80,61,48,120,50,44,80,82,79,77,79,84,69,95,73,78,84,69,71,82,65,76,61,48,120,49,10,99,46,67,76,73,80,77,79,68,69,58,67,79,80,89,61,48,120,50,44,67,85,84,61,48,120,49,44,80,65,83,84,69,61,48,120,52,10,99,46,67,77,70,58,65,80,80,76,89,95,83,69,67,85,82,73,84,89,61,48,120,50,48,44,67,82,69,65,84,69,95,70,73,76,69,61,48,120,52,44,78,69,87,61,48,120,50,44,78,79,95,76,73,78,75,83,61,48,120,49,48,44,80,65,83,83,87,79,82,68,61,48,120,49,44,82,69,65,68,95,79,78,76,89,61,48,120,56,10,99,46,67,78,70,58,65,85,84,79,95,83,65,86,69,61,48,120,50,44,78,69,87,61,48,120,56,44,79,80,84,73,79,78,65,76,95,70,73,76,69,83,61,48,120,52,44,83,84,82,73,80,95,81,85,79,84,69,83,61,48,120,49,10,99,46,68,65,84,65,58,65,85,68,73,79,61,48,120,53,44,67,79,78,84,69,78,84,61,48,120,98,44,68,69,86,73,67,69,95,73,78,80,85,84,61,48,120,51,44,70,73,76,69,61,48,120,97,44,73,77,65,71,69,61,48,120,55,44,73,78,80,85,84,95,82,69,65,68,89,61,48,120,99,44,82,65,87,61,48,120,50,44,82,69,67,69,73,80,84,61,48,120,57,44,82,69,67,79,82,68,61,48,120,54,44,82,69,81,85,69,83,84,61,48,120,56,44,84,69,88,84,61,48,120,49,44,88,77,76,61,48,120,52,10,99,46,68,69,86,73,67,69,58,67,79,77,80,65,67,84,95,68,73,83,67,61,48,120,49,44,70,76,79,80,80,89,95,68,73,83,75,61,48,120,52,44,72,65,82,68,95,68,73,83,75,61,48,120,50,44,77,69,77,79,82,89,61,48,120,49,48,48,48,44,77,79,68,69,77,61,48,120,50,48,48,48,44,78,69,84,87,79,82,75,61,48,120,56,48,44,80,82,73,78,84,69,82,61,48,120,50,48,48,44,80,82,73,78,84,69,82,95,51,68,61,48,120,56,48,48,48,44,82,69,65,68,61,48,120,56,44,82,69,77,79,86,65,66,76,69,61,48,120,50,48,44,82,69,77,79,86,69,65,66,76,69,61,48,120,50,48,44,83,67,65,78,78,69,82,61,48,120,52,48,48,44,83,67,65,78,78,69,82,95,51,68,61,48,120,49,48,48,48,48,44,83,79,70,84,87,65,82,69,61,48,120,52,48,44,84,65,80,69,61,48,120,49,48,48,44,84,69,77,80,79,82,65,82,89,61,48,120,56,48,48,44,85,83,66,61,48,120,52,48,48,48,44,87,82,73,84,69,61,48,120,49,48,10,99,46,68,77,70,58,70,73,88,69,68,95,67,69,78,84,69,82,95,88,61,48,120,49,48,48,48,48,48,44,70,73,88,69,68,95,67,69,78,84,69,82,95,89,61,48,120,50,48,48,48,48,48,44,70,73,88,69,68,95,68,69,80,84,72,61,48,120,49,48,48,48,44,70,73,88,69,68,95,72,69,73,71,72,84,61,48,120,49,48,48,44,70,73,88,69,68,95,82,65,68,73,85,83,61,48,120,50,48,50,48,48,48,48,44,70,73,88,69,68,95,82,65,68,73,85,83,95,88,61,48,120,50,48,48,48,48,44,70,73,88,69,68,95,82,65,68,73,85,83,95,89,61,48,120,50,48,48,48,48,48,48,44,70,73,88,69,68,95,87,73,68,84,72,61,48,120,50,48,48,44,70,73,88,69,68,95,88,61,48,120,52,44,70,73,88,69,68,95,88,95,79,70,70,83,69,84,61,48,120,52,48,44,70,73,88,69,68,95,89,61,48,120,56,44,70,73,88,69,68,95,89,95,79,70,70,83,69,84,61,48,120,56,48,44,70,73,88,69,68,95,90,61,48,120,52,48,48,48,44,72,69,73,71,72,84,61,48,120,53,48,48,44,72,69,73,71,72,84,95,70,76,65,71,83,61,48,120,53,97,48,44,72,79,82,73,90,79,78,84,65,76,95,70,76,65,71,83,61,48,120,97,53,53,44,82,69,76,65,84,73,86,69,95,67,69,78,84,69,82,95,88,61,48,120,52,48,48,48,48,44,82,69,76,65,84,73,86,69,95,67,69,78,84,69,82,95,89,61,48,120,56,48,48,48,48,44,82,69,76,65,84,73,86,69,95,68,69,80,84,72,61,48,120,50,48,48,48,44,82,69,76,65,84,73,86,69,95,72,69,73,71,72,84,61,48,120,52,48,48,44,82,69,76,65,84,73,86,69,95,82,65,68,73,85,83,61,48,120,49,48,49,48,48,48,48,44,82,69,76,65,84,73,86,69,95,82,65,68,73,85,83,95,88,61,48,120,49,48,48,48,48,44,82,69,76,65,84,73,86,69,95,82,65,68,73,85,83,95,89,61,48,120,49,48,48,48,48,48,48,44,82,69,76,65,84,73,86,69,95,87,73,68,84,72,61,48,120,56,48,48,44,82,69,76,65,84,73,86,69,95,88,61,48,120,49,44,82,69,76,65,84,73,86,69,95,88,95,79,70,70,83,69,84,61,48,120,49,48,44,82,69,76,65,84,73,86,69,95,89,61,48,120,50,44,82,69,76,65,84,73,86,69,95,89,95,79,70,70,83,69,84,61,48,120,50,48,44,82,69,76,65,84,73,86,69,95,90,61,48,120,56,48,48,48,44,83,84,65,84,85,83,95,67,72,65,78,71,69,61,48,120,99,48,48,48,48,48,44,83,84,65,84,85,83,95,67,72,65,78,71,69,95,72,61,48,120,52,48,48,48,48,48,44,83,84,65,84,85,83,95,67,72,65,78,71,69,95,86,61,48,120,56,48,48,48,48,48,44,86,69,82,84,73,67,65,76,95,70,76,65,71,83,61,48,120,53,97,97,44,87,73,68,84,72,61,48,120,97,48,48,44,87,73,68,84,72,95,70,76,65,71,83,61,48,120,97,53,48,44,88,61,48,120,53,44,88,95,79,70,70,83,69,84,61,48,120,53,48,44,89,61,48,120,97,44,89,95,79,70,70,83,69,84,61,48,120,97,48,10,99,46,68,82,76,58,68,79,87,78,61,48,120,49,44,69,65,83,84,61,48,120,50,44,76,69,70,84,61,48,120,51,44,78,79,82,84,72,61,48,120,48,44,78,79,82,84,72,95,69,65,83,84,61,48,120,52,44,78,79,82,84,72,95,87,69,83,84,61,48,120,53,44,82,73,71,72,84,61,48,120,50,44,83,79,85,84,72,61,48,120,49,44,83,79,85,84,72,95,69,65,83,84,61,48,120,54,44,83,79,85,84,72,95,87,69,83,84,61,48,120,55,44,85,80,61,48,120,48,44,87,69,83,84,61,48,120,51,10,99,46,69,68,71,69,58,65,76,76,61,48,120,102,102,44,66,79,84,84,79,77,61,48,120,56,44,66,79,84,84,79,77,95,76,69,70,84,61,48,120,52,48,44,66,79,84,84,79,77,95,82,73,71,72,84,61,48,120,56,48,44,76,69,70,84,61,48,120,50,44,82,73,71,72,84,61,48,120,52,44,84,79,80,61,48,120,49,44,84,79,80,95,76,69,70,84,61,48,120,49,48,44,84,79,80,95,82,73,71,72,84,61,48,120,50,48,10,99,46,69,82,70,58,68,101,108,97,121,61,48,120,50,48,48,48,48,48,48,48,44,78,111,116,105,102,105,101,100,61,48,120,52,48,48,48,48,48,48,48,10,99,46,69,82,82,58,65,99,99,101,115,115,77,101,109,111,114,121,61,48,120,52,98,44,65,99,99,101,115,115,79,98,106,101,99,116,61,48,120,53,51,44,65,99,99,101,115,115,83,101,109,97,112,104,111,114,101,61,48,120,55,51,44,65,99,116,105,118,97,116,101,61,48,120,52,50,44,65,100,100,67,108,97,115,115,61,48,120,52,49,44,65,108,108,111,99,77,101,109,111,114,121,61,48,120,53,52,44,65,108,108,111,99,83,101,109,97,112,104,111,114,101,61,48,120,55,50,44,65,108,114,101,97,100,121,68,101,102,105,110,101,100,61,48,120,98,54,44,65,108,114,101,97,100,121,76,111,99,107,101,100,61,48,120,57,99,44,65,114,103,115,61,48,120,49,52,44,65,114,114,97,121,70,117,108,108,61,48,120,50,100,44,66,97,100,79,119,110,101,114,61,48,120,53,50,44,66,117,102,102,101,114,79,118,101,114,102,108,111,119,61,48,120,53,99,44,66,117,115,121,61,48,120,56,98,44,67,97,110,99,101,108,108,101,100,61,48,120,51,44,67,97,114,100,82,101,97,100,101,114,85,110,97,118,97,105,108,97,98,108,101,61,48,120,57,102,44,67,97,114,100,82,101,97,100,101,114,85,110,107,110,111,119,110,61,48,120,57,100,44,67,111,109,112,114,101,115,115,105,111,110,61,48,120,97,100,44,67,111,110,110,101,99,116,105,111,110,65,98,111,114,116,101,100,61,48,120,56,99,44,67,111,110,110,101,99,116,105,111,110,82,101,102,117,115,101,100,61,48,120,56,51,44,67,111,110,115,116,114,97,105,110,116,86,105,111,108,97,116,105,111,110,61,48,120,56,56,44,67,111,110,116,105,110,117,101,61,48,120,53,44,67,111,114,101,86,101,114,115,105,111,110,61,48,120,50,54,44,67,114,101,97,116,101,70,105,108,101,61,48,120,55,52,44,67,114,101,97,116,101,79,98,106,101,99,116,61,48,120,54,53,44,67,114,101,97,116,101,82,101,115,111,117,114,99,101,61,48,120,98,50,44,68,97,116,97,83,105,122,101,61,48,120,56,97,44,68,101,97,99,116,105,118,97,116,101,100,61,48,120,57,97,44,68,101,97,100,76,111,99,107,61,48,120,51,101,44,68,101,99,111,109,112,114,101,115,115,105,111,110,61,48,120,97,99,44,68,101,108,101,116,101,70,105,108,101,61,48,120,55,53,44,68,105,114,69,109,112,116,121,61,48,120,56,44,68,105,115,99,111,110,110,101,99,116,101,100,61,48,120,56,54,44,68,111,78,111,116,69,120,112,117,110,103,101,61,48,120,51,48,44,68,111,101,115,78,111,116,69,120,105,115,116,61,48,120,55,56,44,68,111,117,98,108,101,73,110,105,116,61,48,120,52,51,44,68,114,97,119,61,48,120,52,56,44,69,78,68,61,48,120,98,101,44,69,79,70,61,48,120,55,101,44,69,109,112,116,121,83,116,114,105,110,103,61,48,120,54,100,44,69,110,100,79,102,70,105,108,101,61,48,120,55,101,44,69,110,116,114,121,77,105,115,115,105,110,103,72,101,97,100,101,114,61,48,120,51,97,44,69,120,97,109,105,110,101,70,97,105,108,101,100,61,48,120,49,57,44,69,120,99,101,112,116,105,111,110,61,48,120,97,51,44,69,120,99,101,112,116,105,111,110,84,104,114,101,115,104,111,108,100,61,48,120,57,44,69,120,99,108,117,115,105,118,101,68,101,110,105,101,100,61,48,120,53,51,44,69,120,101,99,86,105,111,108,97,116,105,111,110,61,48,120,56,102,44,69,120,105,115,116,115,61,48,120,55,97,44,69,120,112,101,99,116,101,100,70,105,108,101,61,48,120,54,102,44,69,120,112,101,99,116,101,100,70,111,108,100,101,114,61,48,120,97,101,44,70,97,105,108,101,100,61,48,120,100,44,70,97,108,115,101,61,48,120,49,44,70,105,101,108,100,78,111,116,83,101,116,61,48,120,52,52,44,70,105,101,108,100,83,101,97,114,99,104,61,48,120,51,50,44,70,105,101,108,100,84,121,112,101,77,105,115,109,97,116,99,104,61,48,120,53,97,44,70,105,108,101,61,48,120,101,44,70,105,108,101,68,111,101,115,78,111,116,69,120,105,115,116,61,48,120,49,50,44,70,105,108,101,69,120,105,115,116,115,61,48,120,54,51,44,70,105,108,101,78,111,116,70,111,117,110,100,61,48,120,49,50,44,70,105,108,101,82,101,97,100,70,108,97,103,61,48,120,52,54,44,70,105,108,101,87,114,105,116,101,70,108,97,103,61,48,120,52,55,44,70,105,110,105,115,104,101,100,61,48,120,55,101,44,70,117,110,99,116,105,111,110,61,48,120,98,53,44,71,101,116,70,105,101,108,100,61,48,120,53,54,44,71,101,116,83,117,114,102,97,99,101,73,110,102,111,61,48,120,55,100,44,72,111,115,116,78,111,116,70,111,117,110,100,61,48,120,56,49,44,72,111,115,116,85,110,114,101,97,99,104,97,98,108,101,61,48,120,56,53,44,73,100,101,110,116,105,99,97,108,80,97,116,104,115,61,48,120,55,57,44,73,108,108,101,103,97,108,65,99,116,105,111,110,65,116,116,101,109,112,116,61,48,120,51,57,44,73,108,108,101,103,97,108,65,99,116,105,111,110,73,68,61,48,120,51,55,44,73,108,108,101,103,97,108,65,100,100,114,101,115,115,61,48,120,57,49,44,73,108,108,101,103,97,108,77,101,116,104,111,100,73,68,61,48,120,51,54,44,73,109,109,117,116,97,98,108,101,61,48,120,97,102,44,73,110,85,115,101,61,48,120,99,44,73,110,105,116,61,48,120,50,49,44,73,110,105,116,77,111,100,117,108,101,61,48,120,49,49,44,73,110,112,117,116,79,117,116,112,117,116,61,48,120,57,52,44,73,110,116,101,103,114,105,116,121,86,105,111,108,97,116,105,111,110,61,48,120,56,56,44,73,110,118,97,108,105,100,68,97,116,97,61,48,120,102,44,73,110,118,97,108,105,100,68,105,109,101,110,115,105,111,110,61,48,120,53,57,44,73,110,118,97,108,105,100,72,84,84,80,82,101,115,112,111,110,115,101,61,48,120,97,49,44,73,110,118,97,108,105,100,72,97,110,100,108,101,61,48,120,57,54,44,73,110,118,97,108,105,100,79,98,106,101,99,116,61,48,120,56,101,44,73,110,118,97,108,105,100,80,97,116,104,61,48,120,51,51,44,73,110,118,97,108,105,100,82,101,102,101,114,101,110,99,101,61,48,120,97,50,44,73,110,118,97,108,105,100,83,116,97,116,101,61,48,120,56,48,44,73,110,118,97,108,105,100,85,82,73,61,48,120,56,50,44,73,110,118,97,108,105,100,86,97,108,117,101,61,48,120,57,56,44,76,105,109,105,116,101,100,83,117,99,99,101,115,115,61,48,120,50,44,76,105,115,116,67,104,105,108,100,114,101,110,61,48,120,54,97,44,76,111,97,100,77,111,100,117,108,101,61,48,120,57,53,44,76,111,99,107,61,48,120,49,56,44,76,111,99,107,70,97,105,108,101,100,61,48,120,49,56,44,76,111,99,107,77,117,116,101,120,61,48,120,97,97,44,76,111,99,107,82,101,113,117,105,114,101,100,61,48,120,57,98,44,76,111,99,107,101,100,61,48,120,57,99,44,76,111,111,112,61,48,120,54,50,44,76,111,115,116,67,108,97,115,115,61,48,120,49,97,44,76,111,115,116,79,119,110,101,114,61,48,120,50,102,44,76,111,119,67,97,112,97,99,105,116,121,61,48,120,50,48,44,77,97,114,107,101,100,70,111,114,68,101,108,101,116,105,111,110,61,48,120,51,53,44,77,101,109,111,114,121,61,48,120,49,100,44,77,101,109,111,114,121,67,111,114,114,117,112,116,61,48,120,51,49,44,77,101,109,111,114,121,68,111,101,115,78,111,116,69,120,105,115,116,61,48,120,51,100,44,77,101,109,111,114,121,73,110,102,111,61,48,120,54,54,44,77,105,115,109,97,116,99,104,61,48,120,53,101,44,77,105,115,115,105,110,103,67,108,97,115,115,61,48,120,52,53,44,77,105,115,115,105,110,103,67,108,97,115,115,78,97,109,101,61,48,120,50,97,44,77,105,115,115,105,110,103,80,97,116,104,61,48,120,52,99,44,77,111,100,117,108,101,73,110,105,116,70,97,105,108,101,100,61,48,120,51,99,44,77,111,100,117,108,101,77,105,115,115,105,110,103,73,110,105,116,61,48,120,51,98,44,77,111,100,117,108,101,77,105,115,115,105,110,103,78,97,109,101,61,48,120,52,48,44,77,111,100,117,108,101,79,112,101,110,70,97,105,108,101,100,61,48,120,51,56,44,78,101,101,100,79,119,110,101,114,61,48,120,50,52,44,78,101,101,100,87,105,100,116,104,72,101,105,103,104,116,61,48,120,50,55,44,78,101,103,97,116,105,118,101,67,108,97,115,115,73,68,61,48,120,50,57,44,78,101,103,97,116,105,118,101,83,117,98,67,108,97,115,115,73,68,61,48,120,50,56,44,78,101,116,119,111,114,107,85,110,114,101,97,99,104,97,98,108,101,61,48,120,56,52,44,78,101,119,79,98,106,101,99,116,61,48,120,53,53,44,78,111,65,99,116,105,111,110,61,48,120,49,98,44,78,111,68,97,116,97,61,48,120,49,53,44,78,111,70,105,101,108,100,65,99,99,101,115,115,61,48,120,53,55,44,78,111,77,97,116,99,104,105,110,103,79,98,106,101,99,116,61,48,120,52,97,44,78,111,77,101,100,105,97,73,110,115,101,114,116,101,100,61,48,120,57,101,44,78,111,77,101,109,111,114,121,61,48,120,97,44,78,111,77,101,116,104,111,100,115,61,48,120,52,57,44,78,111,80,101,114,109,105,115,115,105,111,110,61,48,120,50,50,44,78,111,80,111,105,110,116,101,114,61,48,120,98,44,78,111,83,101,97,114,99,104,82,101,115,117,108,116,61,48,120,52,101,44,78,111,83,116,97,116,115,61,48,120,49,102,44,78,111,83,117,112,112,111,114,116,61,48,120,49,99,44,78,111,116,70,111,117,110,100,61,48,120,49,48,44,78,111,116,73,110,105,116,105,97,108,105,115,101,100,61,48,120,54,55,44,78,111,116,76,111,99,107,101,100,61,48,120,52,100,44,78,111,116,80,111,115,115,105,98,108,101,61,48,120,98,51,44,78,111,116,104,105,110,103,68,111,110,101,61,48,120,52,44,78,117,108,108,65,114,103,115,61,48,120,56,100,44,79,98,106,101,99,116,67,111,114,114,117,112,116,61,48,120,53,48,44,79,98,106,101,99,116,69,120,105,115,116,115,61,48,120,54,101,44,79,98,115,111,108,101,116,101,61,48,120,98,49,44,79,98,116,97,105,110,77,101,116,104,111,100,61,48,120,50,99,44,79,107,97,121,61,48,120,48,44,79,112,101,110,70,105,108,101,61,48,120,55,54,44,79,112,101,110,71,76,61,48,120,97,53,44,79,117,116,79,102,66,111,117,110,100,115,61,48,120,53,102,44,79,117,116,79,102,68,97,116,97,61,48,120,55,101,44,79,117,116,79,102,82,97,110,103,101,61,48,120,50,98,44,79,117,116,79,102,83,112,97,99,101,61,48,120,55,99,44,79,117,116,115,105,100,101,77,97,105,110,84,104,114,101,97,100,61,48,120,97,54,44,79,119,110,101,114,78,101,101,100,115,66,105,116,109,97,112,61,48,120,50,53,44,79,119,110,101,114,80,97,115,115,84,104,114,111,117,103,104,61,48,120,53,49,44,80,101,114,109,105,115,115,105,111,110,68,101,110,105,101,100,61,48,120,50,50,44,80,101,114,109,105,115,115,105,111,110,115,61,48,120,50,50,44,80,114,111,120,121,83,83,76,84,117,110,110,101,108,61,48,120,97,48,44,81,117,101,114,121,61,48,120,50,101,44,82,101,97,100,61,48,120,49,54,44,82,101,97,100,70,105,108,101,84,111,66,117,102,102,101,114,61,48,120,98,48,44,82,101,97,100,79,110,108,121,61,48,120,55,55,44,82,101,97,108,108,111,99,77,101,109,111,114,121,61,48,120,54,49,44,82,101,99,117,114,115,105,111,110,61,48,120,57,48,44,82,101,100,105,109,101,110,115,105,111,110,61,48,120,55,49,44,82,101,102,114,101,115,104,61,48,120,54,57,44,82,101,115,105,122,101,61,48,120,55,48,44,82,101,115,111,108,118,101,80,97,116,104,61,48,120,54,52,44,82,101,115,111,108,118,101,83,121,109,98,111,108,61,48,120,98,52,44,82,101,115,111,117,114,99,101,69,120,105,115,116,115,61,48,120,54,56,44,82,101,116,114,121,61,48,120,55,44,83,97,110,105,116,121,70,97,105,108,117,114,101,61,48,120,55,98,44,83,99,104,101,109,97,86,105,111,108,97,116,105,111,110,61,48,120,56,57,44,83,101,97,114,99,104,61,48,120,49,48,44,83,101,99,117,114,105,116,121,61,48,120,57,55,44,83,101,101,107,61,48,120,54,48,44,83,101,114,118,105,99,101,85,110,97,118,97,105,108,97,98,108,101,61,48,120,57,57,44,83,101,116,70,105,101,108,100,61,48,120,51,52,44,83,101,116,86,97,108,117,101,78,111,116,65,114,114,97,121,61,48,120,98,99,44,83,101,116,86,97,108,117,101,78,111,116,70,117,110,99,116,105,111,110,61,48,120,98,97,44,83,101,116,86,97,108,117,101,78,111,116,76,111,111,107,117,112,61,48,120,98,100,44,83,101,116,86,97,108,117,101,78,111,116,78,117,109,101,114,105,99,61,48,120,98,55,44,83,101,116,86,97,108,117,101,78,111,116,79,98,106,101,99,116,61,48,120,98,57,44,83,101,116,86,97,108,117,101,78,111,116,80,111,105,110,116,101,114,61,48,120,98,98,44,83,101,116,86,97,108,117,101,78,111,116,83,116,114,105,110,103,61,48,120,98,56,44,83,101,116,86,111,108,117,109,101,61,48,120,97,98,44,83,107,105,112,61,48,120,54,44,83,109,97,108,108,77,97,115,107,61,48,120,54,99,44,83,116,97,116,101,109,101,110,116,85,110,115,97,116,105,115,102,105,101,100,61,48,120,52,102,44,83,116,114,105,110,103,70,111,114,109,97,116,61,48,120,55,102,44,83,121,110,116,97,120,61,48,120,55,102,44,83,121,115,116,101,109,67,97,108,108,61,48,120,54,98,44,83,121,115,116,101,109,67,111,114,114,117,112,116,61,48,120,50,51,44,83,121,115,116,101,109,76,111,99,107,101,100,61,48,120,51,102,44,84,97,115,107,83,116,105,108,108,69,120,105,115,116,115,61,48,120,56,55,44,84,101,114,109,105,110,97,116,101,61,48,120,57,44,84,104,114,101,97,100,65,108,114,101,97,100,121,65,99,116,105,118,101,61,48,120,97,52,44,84,104,114,101,97,100,78,111,116,76,111,99,107,101,100,61,48,120,97,57,44,84,105,109,101,79,117,116,61,48,120,49,101,44,84,114,117,101,61,48,120,48,44,85,110,98,97,108,97,110,99,101,100,88,77,76,61,48,120,57,50,44,85,110,100,101,102,105,110,101,100,70,105,101,108,100,61,48,120,52,52,44,85,110,114,101,99,111,103,110,105,115,101,100,70,105,101,108,100,84,121,112,101,61,48,120,53,98,44,85,110,115,117,112,112,111,114,116,101,100,70,105,101,108,100,61,48,120,53,100,44,85,110,115,117,112,112,111,114,116,101,100,79,119,110,101,114,61,48,120,53,50,44,85,115,101,83,117,98,67,108,97,115,115,61,48,120,97,55,44,86,105,114,116,117,97,108,86,111,108,117,109,101,61,48,120,53,56,44,87,111,117,108,100,66,108,111,99,107,61,48,120,57,51,44,87,114,105,116,101,61,48,120,49,55,44,87,114,111,110,103,67,108,97,115,115,61,48,120,56,101,44,87,114,111,110,103,79,98,106,101,99,116,84,121,112,101,61,48,120,56,101,44,87,114,111,110,103,84,121,112,101,61,48,120,97,56,44,87,114,111,110,103,86,101,114,115,105,111,110,61,48,120,49,51,10,99,46,69,86,71,58,65,78,68,82,79,73,68,61,48,120,100,44,65,80,80,61,48,120,99,44,65,85,68,73,79,61,48,120,56,44,67,76,65,83,83,61,48,120,98,44,68,73,83,80,76,65,89,61,48,120,53,44,69,78,68,61,48,120,101,44,70,73,76,69,83,89,83,84,69,77,61,48,120,49,44,71,85,73,61,48,120,52,44,72,65,82,68,87,65,82,69,61,48,120,55,44,73,79,61,48,120,54,44,78,69,84,87,79,82,75,61,48,120,50,44,80,79,87,69,82,61,48,120,97,44,83,89,83,84,69,77,61,48,120,51,44,85,83,69,82,61,48,120,57,10,99,46,70,66,75,58,67,79,80,89,95,70,73,76,69,61,48,120,50,44,68,69,76,69,84,69,95,70,73,76,69,61,48,120,51,44,77,79,86,69,95,70,73,76,69,61,48,120,49,10,99,46,70,68,58,65,76,76,79,67,61,48,120,50,48,44,65,82,82,65,89,61,48,120,49,48,48,48,44,65,82,82,65,89,83,73,90,69,61,48,120,56,48,44,66,85,70,70,69,82,61,48,120,50,48,48,44,66,85,70,83,73,90,69,61,48,120,56,48,44,66,89,84,69,61,48,120,49,48,48,48,48,48,48,44,67,80,80,61,48,120,52,48,48,48,44,67,85,83,84,79,77,61,48,120,56,48,48,48,44,68,79,85,66,76,69,61,48,120,56,48,48,48,48,48,48,48,44,68,79,85,66,76,69,82,69,83,85,76,84,61,48,120,56,48,48,48,48,49,48,48,44,69,82,82,79,82,61,48,120,56,48,48,44,70,76,65,71,83,61,48,120,52,48,44,70,76,79,65,84,61,48,120,49,48,48,48,48,48,48,48,44,70,85,78,67,84,73,79,78,61,48,120,50,48,48,48,48,48,48,44,70,85,78,67,84,73,79,78,80,84,82,61,48,120,97,48,48,48,48,48,48,44,73,61,48,120,52,48,48,44,73,78,73,84,61,48,120,52,48,48,44,73,78,84,69,71,82,65,76,61,48,120,50,44,76,65,82,71,69,61,48,120,52,48,48,48,48,48,48,44,76,65,82,71,69,82,69,83,85,76,84,61,48,120,52,48,48,48,49,48,48,44,76,79,78,71,61,48,120,52,48,48,48,48,48,48,48,44,76,79,78,71,82,69,83,85,76,84,61,48,120,52,48,48,48,48,49,48,48,44,76,79,79,75,85,80,61,48,120,56,48,44,79,66,74,69,67,84,61,48,120,49,44,79,66,74,69,67,84,73,68,61,48,120,52,48,48,48,48,48,48,49,44,79,66,74,69,67,84,80,84,82,61,48,120,56,48,48,48,48,48,49,44,80,69,82,67,69,78,84,65,71,69,61,48,120,50,48,48,48,48,48,44,80,79,73,78,84,69,82,61,48,120,56,48,48,48,48,48,48,44,80,82,73,86,65,84,69,61,48,120,49,48,48,48,48,44,80,84,82,61,48,120,56,48,48,48,48,48,48,44,80,84,82,66,85,70,70,69,82,61,48,120,56,48,48,48,50,48,48,44,80,84,82,82,69,83,85,76,84,61,48,120,56,48,48,48,49,48,48,44,80,84,82,83,73,90,69,61,48,120,56,48,44,80,84,82,95,68,79,85,66,76,69,82,69,83,85,76,84,61,48,120,56,56,48,48,48,49,48,48,44,80,84,82,95,76,65,82,71,69,82,69,83,85,76,84,61,48,120,99,48,48,48,49,48,48,44,80,84,82,95,76,79,78,71,82,69,83,85,76,84,61,48,120,52,56,48,48,48,49,48,48,44,82,61,48,120,49,48,48,44,82,69,65,68,61,48,120,49,48,48,44,82,69,81,85,73,82,69,68,61,48,120,52,44,82,69,83,79,85,82,67,69,61,48,120,50,48,48,48,44,82,69,83,85,76,84,61,48,120,49,48,48,44,82,71,66,61,48,120,56,48,48,48,48,44,82,73,61,48,120,53,48,48,44,82,87,61,48,120,51,48,48,44,83,84,82,61,48,120,56,48,48,48,48,48,44,83,84,82,73,78,71,61,48,120,56,48,48,48,48,48,44,83,84,82,82,69,83,85,76,84,61,48,120,56,48,48,49,48,48,44,83,84,82,85,67,84,61,48,120,49,48,44,83,89,78,79,78,89,77,61,48,120,50,48,48,48,48,44,83,89,83,84,69,77,61,48,120,49,48,48,48,48,44,84,65,71,83,61,48,120,52,48,48,44,85,78,83,73,71,78,69,68,61,48,120,52,48,48,48,48,44,86,65,82,73,65,66,76,69,61,48,120,50,48,48,48,48,48,48,48,44,86,65,82,84,65,71,83,61,48,120,52,48,44,86,73,82,84,85,65,76,61,48,120,56,44,86,79,73,68,61,48,120,48,44,86,79,76,65,84,73,76,69,61,48,120,48,44,87,61,48,120,50,48,48,44,87,79,82,68,61,48,120,52,48,48,48,48,48,44,87,82,73,84,69,61,48,120,50,48,48,10,99,46,70,68,66,58,67,79,77,80,82,69,83,83,95,70,73,76,69,61,48,120,50,44,68,69,67,79,77,80,82,69,83,83,95,70,73,76,69,61,48,120,49,44,68,69,67,79,77,80,82,69,83,83,95,79,66,74,69,67,84,61,48,120,52,44,82,69,77,79,86,69,95,70,73,76,69,61,48,120,51,10,99,46,70,68,76,58,70,69,69,68,66,65,67,75,61,48,120,49,10,99,46,70,68,84,58,65,67,67,69,83,83,69,68,61,48,120,50,44,65,82,67,72,73,86,69,68,61,48,120,51,44,67,82,69,65,84,69,68,61,48,120,49,44,77,79,68,73,70,73,69,68,61,48,120,48,10,99,46,70,70,82,58,65,66,79,82,84,61,48,120,50,44,67,79,78,84,73,78,85,69,61,48,120,48,44,79,75,65,89,61,48,120,48,44,83,75,73,80,61,48,120,49,10,99,46,70,76,58,65,80,80,82,79,88,73,77,65,84,69,61,48,120,49,48,44,66,85,70,70,69,82,61,48,120,52,48,44,68,69,86,73,67,69,61,48,120,52,48,48,44,68,73,82,69,67,84,79,82,89,61,48,120,56,44,69,88,67,76,85,68,69,95,70,73,76,69,83,61,48,120,49,48,48,48,44,69,88,67,76,85,68,69,95,70,79,76,68,69,82,83,61,48,120,50,48,48,48,44,70,73,76,69,61,48,120,49,48,48,44,70,79,76,68,69,82,61,48,120,56,44,76,73,78,75,61,48,120,50,48,44,76,79,79,80,61,48,120,56,48,44,78,69,87,61,48,120,50,44,82,69,65,68,61,48,120,52,44,82,69,83,69,84,95,68,65,84,69,61,48,120,50,48,48,44,83,84,82,69,65,77,61,48,120,56,48,48,44,87,82,73,84,69,61,48,120,49,10,99,46,70,79,70,58,83,77,65,82,84,95,78,65,77,69,83,61,48,120,49,10,99,46,73,68,84,89,80,69,58,70,85,78,67,84,73,79,78,61,48,120,51,44,71,76,79,66,65,76,61,48,120,50,44,77,69,83,83,65,71,69,61,48,120,49,10,99,46,74,69,84,58,65,66,83,95,88,61,48,120,49,102,44,65,66,83,95,89,61,48,120,50,48,44,65,78,65,76,79,71,50,95,88,61,48,120,49,56,44,65,78,65,76,79,71,50,95,89,61,48,120,49,57,44,65,78,65,76,79,71,50,95,90,61,48,120,49,97,44,65,78,65,76,79,71,95,88,61,48,120,49,53,44,65,78,65,76,79,71,95,89,61,48,120,49,54,44,65,78,65,76,79,71,95,90,61,48,120,49,55,44,66,85,84,84,79,78,95,49,61,48,120,51,44,66,85,84,84,79,78,95,49,48,61,48,120,99,44,66,85,84,84,79,78,95,50,61,48,120,52,44,66,85,84,84,79,78,95,51,61,48,120,53,44,66,85,84,84,79,78,95,52,61,48,120,54,44,66,85,84,84,79,78,95,53,61,48,120,55,44,66,85,84,84,79,78,95,54,61,48,120,56,44,66,85,84,84,79,78,95,55,61,48,120,57,44,66,85,84,84,79,78,95,56,61,48,120,97,44,66,85,84,84,79,78,95,57,61,48,120,98,44,66,85,84,84,79,78,95,83,69,76,69,67,84,61,48,120,49,48,44,66,85,84,84,79,78,95,83,84,65,82,84,61,48,120,102,44,68,69,86,73,67,69,95,84,73,76,84,95,88,61,48,120,50,52,44,68,69,86,73,67,69,95,84,73,76,84,95,89,61,48,120,50,53,44,68,69,86,73,67,69,95,84,73,76,84,95,90,61,48,120,50,54,44,68,73,71,73,84,65,76,95,88,61,48,120,49,44,68,73,71,73,84,65,76,95,89,61,48,120,50,44,68,73,83,80,76,65,89,95,69,68,71,69,61,48,120,50,55,44,69,78,68,61,48,120,50,56,44,69,78,84,69,82,69,68,61,48,120,50,49,44,69,78,84,69,82,69,68,95,83,85,82,70,65,67,69,61,48,120,50,49,44,76,69,70,84,61,48,120,50,50,44,76,69,70,84,95,66,85,77,80,69,82,95,49,61,48,120,49,49,44,76,69,70,84,95,66,85,77,80,69,82,95,50,61,48,120,49,50,44,76,69,70,84,95,83,85,82,70,65,67,69,61,48,120,50,50,44,76,77,66,61,48,120,51,44,77,77,66,61,48,120,53,44,80,69,78,95,84,73,76,84,95,72,79,82,73,90,79,78,84,65,76,61,48,120,49,101,44,80,69,78,95,84,73,76,84,95,86,69,82,84,73,67,65,76,61,48,120,49,100,44,80,82,69,83,83,85,82,69,61,48,120,50,51,44,82,73,71,72,84,95,66,85,77,80,69,82,95,49,61,48,120,49,51,44,82,73,71,72,84,95,66,85,77,80,69,82,95,50,61,48,120,49,52,44,82,77,66,61,48,120,52,44,84,82,73,71,71,69,82,95,76,69,70,84,61,48,120,100,44,84,82,73,71,71,69,82,95,82,73,71,72,84,61,48,120,101,44,87,72,69,69,76,61,48,120,49,98,44,87,72,69,69,76,95,84,73,76,84,61,48,120,49,99,10,99,46,74,84,89,80,69,58,65,78,65,76,79,71,61,48,120,50,48,44,65,78,67,72,79,82,69,68,61,48,120,50,44,66,85,84,84,79,78,61,48,120,56,48,44,68,66,76,95,67,76,73,67,75,61,48,120,50,48,48,44,68,73,71,73,84,65,76,61,48,120,49,48,44,68,82,65,71,71,69,68,61,48,120,52,44,68,82,65,71,95,73,84,69,77,61,48,120,56,48,48,44,69,88,84,95,77,79,86,69,77,69,78,84,61,48,120,52,48,44,70,69,69,68,66,65,67,75,61,48,120,56,44,77,79,86,69,77,69,78,84,61,48,120,49,48,48,44,82,69,80,69,65,84,69,68,61,48,120,52,48,48,44,83,69,67,79,78,68,65,82,89,61,48,120,49,10,99,46,75,69,89,58,65,61,48,120,49,44,65,80,79,83,84,82,79,80,72,69,61,48,120,50,98,44,65,84,61,48,120,56,97,44,66,61,48,120,50,44,66,65,67,75,61,48,120,56,54,44,66,65,67,75,83,80,65,67,69,61,48,120,54,57,44,66,65,67,75,95,83,76,65,83,72,61,48,120,50,102,44,66,82,69,65,75,61,48,120,55,98,44,67,61,48,120,51,44,67,65,76,76,61,48,120,56,55,44,67,65,77,69,82,65,61,48,120,56,57,44,67,65,78,67,69,76,61,48,120,55,97,44,67,65,80,83,95,76,79,67,75,61,48,120,52,54,44,67,76,69,65,82,61,48,120,54,101,44,67,79,77,77,65,61,48,120,50,99,44,68,61,48,120,52,44,68,69,76,69,84,69,61,48,120,54,100,44,68,79,84,61,48,120,50,100,44,68,79,87,78,61,48,120,54,49,44,69,61,48,120,53,44,69,73,71,72,84,61,48,120,50,50,44,69,78,68,61,48,120,55,50,44,69,78,68,95,67,65,76,76,61,48,120,56,56,44,69,78,84,69,82,61,48,120,54,98,44,69,81,85,65,76,83,61,48,120,50,55,44,69,83,67,65,80,69,61,48,120,54,99,44,69,88,69,67,85,84,69,61,48,120,55,52,44,70,61,48,120,54,44,70,49,61,48,120,52,99,44,70,49,48,61,48,120,53,53,44,70,49,49,61,48,120,53,54,44,70,49,50,61,48,120,53,55,44,70,49,51,61,48,120,53,56,44,70,49,52,61,48,120,53,57,44,70,49,53,61,48,120,53,97,44,70,49,54,61,48,120,53,98,44,70,49,55,61,48,120,53,99,44,70,49,56,61,48,120,56,48,44,70,49,57,61,48,120,56,49,44,70,50,61,48,120,52,100,44,70,50,48,61,48,120,56,50,44,70,51,61,48,120,52,101,44,70,52,61,48,120,52,102,44,70,53,61,48,120,53,48,44,70,54,61,48,120,53,49,44,70,55,61,48,120,53,50,44,70,56,61,48,120,53,51,44,70,57,61,48,120,53,52,44,70,73,78,68,61,48,120,55,57,44,70,73,86,69,61,48,120,49,102,44,70,79,82,87,65,82,68,61,48,120,57,48,44,70,79,85,82,61,48,120,49,101,44,71,61,48,120,55,44,72,61,48,120,56,44,72,69,76,80,61,48,120,52,51,44,72,79,77,69,61,48,120,54,102,44,73,61,48,120,57,44,73,78,83,69,82,84,61,48,120,55,53,44,74,61,48,120,97,44,75,61,48,120,98,44,76,61,48,120,99,44,76,69,70,84,61,48,120,54,51,44,76,69,78,83,95,70,79,67,85,83,61,48,120,56,99,44,76,69,83,83,95,71,82,69,65,84,69,82,61,48,120,53,102,44,76,73,83,84,95,69,78,68,61,48,120,57,54,44,76,95,65,76,84,61,48,120,52,56,44,76,95,67,79,77,77,65,78,68,61,48,120,52,97,44,76,95,67,79,78,84,82,79,76,61,48,120,52,49,44,76,95,83,72,73,70,84,61,48,120,52,52,44,76,95,83,81,85,65,82,69,61,48,120,50,56,44,77,61,48,120,100,44,77,65,67,82,79,61,48,120,53,100,44,77,69,78,85,61,48,120,55,56,44,77,73,78,85,83,61,48,120,50,54,44,77,85,84,69,61,48,120,57,50,44,78,61,48,120,101,44,78,69,88,84,61,48,120,56,101,44,78,73,78,69,61,48,120,50,51,44,78,80,95,48,61,48,120,51,49,44,78,80,95,49,61,48,120,51,50,44,78,80,95,50,61,48,120,51,51,44,78,80,95,51,61,48,120,51,52,44,78,80,95,52,61,48,120,51,53,44,78,80,95,53,61,48,120,51,54,44,78,80,95,54,61,48,120,51,55,44,78,80,95,55,61,48,120,51,56,44,78,80,95,56,61,48,120,51,57,44,78,80,95,57,61,48,120,51,97,44,78,80,95,66,65,82,61,48,120,51,100,44,78,80,95,68,69,67,73,77,65,76,61,48,120,51,102,44,78,80,95,68,73,86,73,68,69,61,48,120,52,48,44,78,80,95,68,79,84,61,48,120,51,102,44,78,80,95,69,78,84,69,82,61,48,120,55,101,44,78,80,95,77,73,78,85,83,61,48,120,51,101,44,78,80,95,77,85,76,84,73,80,76,89,61,48,120,51,98,44,78,80,95,80,76,85,83,61,48,120,51,99,44,78,80,95,80,76,85,83,95,77,73,78,85,83,61,48,120,53,101,44,78,80,95,83,69,80,65,82,65,84,79,82,61,48,120,51,100,44,78,85,77,95,76,79,67,75,61,48,120,55,99,44,79,61,48,120,102,44,79,78,69,61,48,120,49,98,44,80,61,48,120,49,48,44,80,65,71,69,95,68,79,87,78,61,48,120,55,49,44,80,65,71,69,95,85,80,61,48,120,55,48,44,80,65,85,83,69,61,48,120,54,53,44,80,69,82,73,79,68,61,48,120,50,100,44,80,76,65,89,61,48,120,57,53,44,80,76,85,83,61,48,120,56,98,44,80,79,85,78,68,61,48,120,57,52,44,80,79,87,69,82,61,48,120,54,56,44,80,82,69,86,73,79,85,83,61,48,120,56,102,44,80,82,73,78,84,61,48,120,52,55,44,80,82,84,95,83,67,82,61,48,120,55,100,44,81,61,48,120,49,49,44,82,61,48,120,49,50,44,82,69,68,79,61,48,120,55,55,44,82,69,86,69,82,83,69,95,81,85,79,84,69,61,48,120,50,53,44,82,69,87,73,78,68,61,48,120,57,49,44,82,73,71,72,84,61,48,120,54,50,44,82,95,65,76,84,61,48,120,52,57,44,82,95,67,79,77,77,65,78,68,61,48,120,52,98,44,82,95,67,79,78,84,82,79,76,61,48,120,52,50,44,82,95,83,72,73,70,84,61,48,120,52,53,44,82,95,83,81,85,65,82,69,61,48,120,50,57,44,83,61,48,120,49,51,44,83,67,82,95,76,79,67,75,61,48,120,54,52,44,83,69,76,69,67,84,61,48,120,55,51,44,83,69,77,73,95,67,79,76,79,78,61,48,120,50,97,44,83,69,86,69,78,61,48,120,50,49,44,83,73,88,61,48,120,50,48,44,83,76,65,83,72,61,48,120,50,101,44,83,76,69,69,80,61,48,120,54,55,44,83,80,65,67,69,61,48,120,51,48,44,83,84,65,82,61,48,120,57,51,44,83,84,79,80,61,48,120,56,100,44,83,89,83,82,81,61,48,120,55,102,44,84,61,48,120,49,52,44,84,65,66,61,48,120,54,97,44,84,72,82,69,69,61,48,120,49,100,44,84,87,79,61,48,120,49,99,44,85,61,48,120,49,53,44,85,78,68,79,61,48,120,55,54,44,85,80,61,48,120,54,48,44,86,61,48,120,49,54,44,86,79,76,85,77,69,95,68,79,87,78,61,48,120,56,53,44,86,79,76,85,77,69,95,85,80,61,48,120,56,52,44,87,61,48,120,49,55,44,87,65,75,69,61,48,120,54,54,44,87,73,78,95,67,79,78,84,82,79,76,61,48,120,56,51,44,88,61,48,120,49,56,44,89,61,48,120,49,57,44,90,61,48,120,49,97,44,90,69,82,79,61,48,120,50,52,10,99,46,75,81,58,65,76,84,61,48,120,54,48,44,65,76,84,71,82,61,48,120,52,48,44,67,65,80,83,95,76,79,67,75,61,48,120,52,44,67,79,77,77,65,78,68,61,48,120,49,56,48,44,67,79,78,84,82,79,76,61,48,120,49,56,44,67,84,82,76,61,48,120,49,56,44,68,69,65,68,95,75,69,89,61,48,120,49,48,48,48,48,44,73,78,70,79,61,48,120,51,99,48,52,44,73,78,83,84,82,85,67,84,73,79,78,95,75,69,89,83,61,48,120,55,56,44,76,95,65,76,84,61,48,120,50,48,44,76,95,67,79,77,77,65,78,68,61,48,120,56,48,44,76,95,67,79,78,84,82,79,76,61,48,120,56,44,76,95,67,84,82,76,61,48,120,56,44,76,95,83,72,73,70,84,61,48,120,49,44,78,79,84,95,80,82,73,78,84,65,66,76,69,61,48,120,50,48,48,48,44,78,85,77,95,76,79,67,75,61,48,120,56,48,48,48,44,78,85,77,95,80,65,68,61,48,120,50,48,48,44,80,82,69,83,83,69,68,61,48,120,49,48,48,48,44,81,85,65,76,73,70,73,69,82,83,61,48,120,49,102,98,44,82,69,76,69,65,83,69,68,61,48,120,56,48,48,44,82,69,80,69,65,84,61,48,120,52,48,48,44,82,95,65,76,84,61,48,120,52,48,44,82,95,67,79,77,77,65,78,68,61,48,120,49,48,48,44,82,95,67,79,78,84,82,79,76,61,48,120,49,48,44,82,95,67,84,82,76,61,48,120,49,48,44,82,95,83,72,73,70,84,61,48,120,50,44,83,67,82,95,76,79,67,75,61,48,120,52,48,48,48,44,83,72,73,70,84,61,48,120,51,44,87,73,78,95,67,79,78,84,82,79,76,61,48,120,50,48,48,48,48,10,99,46,76,65,89,79,85,84,58,66,65,67,75,71,82,79,85,78,68,61,48,120,56,44,69,77,66,69,68,68,69,68,61,48,120,50,48,44,70,79,82,69,71,82,79,85,78,68,61,48,120,49,48,44,73,71,78,79,82,69,95,67,85,82,83,79,82,61,48,120,56,48,44,76,69,70,84,61,48,120,50,44,76,79,67,75,61,48,120,52,48,44,82,73,71,72,84,61,48,120,52,44,83,81,85,65,82,69,61,48,120,48,44,84,73,71,72,84,61,48,120,49,44,84,73,76,69,61,48,120,49,48,48,44,87,73,68,69,61,48,120,54,10,99,46,76,68,70,58,67,72,69,67,75,95,69,88,73,83,84,83,61,48,120,49,10,99,46,76,79,67,58,68,73,82,69,67,84,79,82,89,61,48,120,49,44,70,73,76,69,61,48,120,51,44,70,79,76,68,69,82,61,48,120,49,44,86,79,76,85,77,69,61,48,120,50,10,99,46,77,65,88,58,78,65,77,69,95,76,69,78,61,48,120,50,48,10,99,46,77,69,77,58,65,85,68,73,79,61,48,120,56,44,67,65,76,76,69,82,61,48,120,56,48,48,48,48,48,44,67,79,68,69,61,48,120,49,48,44,68,65,84,65,61,48,120,48,44,68,69,76,69,84,69,61,48,120,49,48,48,48,44,69,88,67,76,85,83,73,86,69,61,48,120,56,48,48,44,72,73,68,68,69,78,61,48,120,49,48,48,48,48,48,44,77,65,78,65,71,69,68,61,48,120,49,44,78,79,95,66,76,79,67,75,61,48,120,50,48,48,48,44,78,79,95,66,76,79,67,75,73,78,71,61,48,120,50,48,48,48,44,78,79,95,67,76,69,65,82,61,48,120,52,48,48,48,48,44,78,79,95,76,79,67,75,61,48,120,52,48,48,44,78,79,95,80,79,79,76,61,48,120,50,48,44,79,66,74,69,67,84,61,48,120,50,48,48,44,82,69,65,68,61,48,120,49,48,48,48,48,44,82,69,65,68,95,87,82,73,84,69,61,48,120,51,48,48,48,48,44,83,84,82,73,78,71,61,48,120,49,48,48,44,84,69,88,84,85,82,69,61,48,120,52,44,84,77,80,95,76,79,67,75,61,48,120,52,48,44,85,78,84,82,65,67,75,69,68,61,48,120,56,48,44,86,73,68,69,79,61,48,120,50,44,87,82,73,84,69,61,48,120,50,48,48,48,48,10,99,46,77,70,70,58,65,84,84,82,73,66,61,48,120,50,48,44,67,76,79,83,69,68,61,48,120,56,48,44,67,82,69,65,84,69,61,48,120,52,44,68,69,69,80,61,48,120,49,48,48,48,44,68,69,76,69,84,69,61,48,120,56,44,70,73,76,69,61,48,120,52,48,48,44,70,79,76,68,69,82,61,48,120,50,48,48,44,77,79,68,73,70,89,61,48,120,50,44,77,79,86,69,68,61,48,120,49,48,44,79,80,69,78,69,68,61,48,120,52,48,44,82,69,65,68,61,48,120,49,44,82,69,78,65,77,69,61,48,120,49,48,44,83,69,76,70,61,48,120,56,48,48,44,85,78,77,79,85,78,84,61,48,120,49,48,48,44,87,82,73,84,69,61,48,120,50,10,99,46,77,72,70,58,68,69,70,65,85,76,84,61,48,120,50,44,83,84,65,84,73,67,61,48,120,49,44,83,84,82,85,67,84,85,82,69,61,48,120,50,10,99,46,77,79,70,58,76,73,78,75,95,76,73,66,82,65,82,89,61,48,120,49,44,83,84,65,84,73,67,61,48,120,50,44,83,89,83,84,69,77,95,80,82,79,66,69,61,48,120,52,10,99,46,77,79,86,69,58,65,76,76,61,48,120,102,44,68,79,87,78,61,48,120,49,44,76,69,70,84,61,48,120,52,44,82,73,71,72,84,61,48,120,56,44,85,80,61,48,120,50,10,99,46,77,83,70,58,65,68,68,61,48,120,56,44,65,68,68,82,69,83,83,61,48,120,49,48,44,77,69,83,83,65,71,69,95,73,68,61,48,120,50,48,44,78,79,95,68,85,80,76,73,67,65,84,69,61,48,120,52,44,85,80,68,65,84,69,61,48,120,50,44,87,65,73,84,61,48,120,49,10,99,46,77,83,71,73,68,58,65,67,84,73,79,78,61,48,120,54,51,44,66,82,69,65,75,61,48,120,54,52,44,67,79,77,77,65,78,68,61,48,120,54,53,44,67,79,82,69,95,69,78,68,61,48,120,54,52,44,68,69,66,85,71,61,48,120,53,102,44,69,86,69,78,84,61,48,120,53,101,44,70,82,69,69,61,48,120,54,50,44,81,85,73,84,61,48,120,51,101,56,44,84,72,82,69,65,68,95,65,67,84,73,79,78,61,48,120,53,98,44,84,72,82,69,65,68,95,67,65,76,76,66,65,67,75,61,48,120,53,99,44,86,65,76,73,68,65,84,69,95,80,82,79,67,69,83,83,61,48,120,53,100,44,87,65,73,84,95,70,79,82,95,79,66,74,69,67,84,83,61,48,120,53,97,10,99,46,77,84,70,58,65,78,73,77,61,48,120,56,44,82,69,76,65,84,73,86,69,61,48,120,49,48,44,88,61,48,120,49,44,89,61,48,120,50,44,90,61,48,120,52,10,99,46,78,69,84,77,83,71,58,69,78,68,61,48,120,49,44,83,84,65,82,84,61,48,120,48,10,99,46,78,70,58,67,79,76,76,69,67,84,61,48,120,56,48,44,70,82,69,69,61,48,120,49,48,44,70,82,69,69,95,79,78,95,85,78,76,79,67,75,61,48,120,56,44,73,78,73,84,73,65,76,73,83,69,68,61,48,120,50,44,73,78,84,69,71,82,65,76,61,48,120,52,44,77,69,83,83,65,71,69,61,48,120,50,48,48,44,78,65,77,69,61,48,120,56,48,48,48,48,48,48,48,44,80,82,73,86,65,84,69,61,48,120,48,44,82,69,67,76,65,83,83,69,68,61,48,120,49,48,48,44,83,73,71,78,65,76,76,69,68,61,48,120,52,48,48,44,83,85,80,80,82,69,83,83,95,76,79,71,61,48,120,52,48,44,84,73,77,69,82,95,83,85,66,61,48,120,50,48,44,85,78,73,81,85,69,61,48,120,52,48,48,48,48,48,48,48,44,85,78,84,82,65,67,75,69,68,61,48,120,49,10,99,46,79,80,70,58,65,82,71,83,61,48,120,52,48,44,68,69,84,65,73,76,61,48,120,52,44,69,82,82,79,82,61,48,120,56,48,44,77,65,88,95,68,69,80,84,72,61,48,120,50,44,77,79,68,85,76,69,95,80,65,84,72,61,48,120,52,48,48,44,79,80,84,73,79,78,83,61,48,120,49,44,80,82,73,86,73,76,69,71,69,68,61,48,120,49,48,48,44,82,79,79,84,95,80,65,84,72,61,48,120,56,48,48,44,83,67,65,78,95,77,79,68,85,76,69,83,61,48,120,49,48,48,48,44,83,72,79,87,95,69,82,82,79,82,83,61,48,120,50,48,44,83,72,79,87,95,73,79,61,48,120,49,48,44,83,72,79,87,95,77,69,77,79,82,89,61,48,120,56,44,83,89,83,84,69,77,95,80,65,84,72,61,48,120,50,48,48,10,99,46,80,69,82,77,73,84,58,65,76,76,95,68,69,76,69,84,69,61,48,120,56,56,56,44,65,76,76,95,69,88,69,67,61,48,120,52,52,52,44,65,76,76,95,82,69,65,68,61,48,120,49,49,49,44,65,76,76,95,87,82,73,84,69,61,48,120,50,50,50,44,65,82,67,72,73,86,69,61,48,120,50,48,48,48,44,68,69,76,69,84,69,61,48,120,56,44,69,86,69,82,89,79,78,69,95,65,67,67,69,83,83,61,48,120,102,102,102,44,69,86,69,82,89,79,78,69,95,68,69,76,69,84,69,61,48,120,56,56,56,44,69,86,69,82,89,79,78,69,95,69,88,69,67,61,48,120,52,52,52,44,69,86,69,82,89,79,78,69,95,82,69,65,68,61,48,120,49,49,49,44,69,86,69,82,89,79,78,69,95,82,69,65,68,87,82,73,84,69,61,48,120,51,51,51,44,69,86,69,82,89,79,78,69,95,87,82,73,84,69,61,48,120,50,50,50,44,69,88,69,67,61,48,120,52,44,71,82,79,85,80,61,48,120,102,48,44,71,82,79,85,80,73,68,61,48,120,49,48,48,48,48,44,71,82,79,85,80,95,68,69,76,69,84,69,61,48,120,56,48,44,71,82,79,85,80,95,69,88,69,67,61,48,120,52,48,44,71,82,79,85,80,95,82,69,65,68,61,48,120,49,48,44,71,82,79,85,80,95,87,82,73,84,69,61,48,120,50,48,44,72,73,68,68,69,78,61,48,120,49,48,48,48,44,73,78,72,69,82,73,84,61,48,120,50,48,48,48,48,44,78,69,84,87,79,82,75,61,48,120,56,48,48,48,48,44,79,70,70,76,73,78,69,61,48,120,52,48,48,48,48,44,79,84,72,69,82,83,61,48,120,102,48,48,44,79,84,72,69,82,83,95,68,69,76,69,84,69,61,48,120,56,48,48,44,79,84,72,69,82,83,95,69,88,69,67,61,48,120,52,48,48,44,79,84,72,69,82,83,95,82,69,65,68,61,48,120,49,48,48,44,79,84,72,69,82,83,95,87,82,73,84,69,61,48,120,50,48,48,44,80,65,83,83,87,79,82,68,61,48,120,52,48,48,48,44,82,69,65,68,61,48,120,49,44,85,83,69,82,61,48,120,102,44,85,83,69,82,73,68,61,48,120,56,48,48,48,44,85,83,69,82,95,69,88,69,67,61,48,120,52,44,85,83,69,82,95,82,69,65,68,61,48,120,49,44,85,83,69,82,95,87,82,73,84,69,61,48,120,50,44,87,82,73,84,69,61,48,120,50,10,99,46,80,77,70,58,83,89,83,84,69,77,95,78,79,95,66,82,69,65,75,61,48,120,49,10,99,46,80,84,67,58,67,82,79,83,83,72,65,73,82,61,48,120,97,44,67,85,83,84,79,77,61,48,120,49,55,44,68,69,70,65,85,76,84,61,48,120,49,44,68,82,65,71,71,65,66,76,69,61,48,120,49,56,44,69,78,68,61,48,120,49,57,44,72,65,78,68,61,48,120,49,48,44,72,65,78,68,95,76,69,70,84,61,48,120,49,49,44,72,65,78,68,95,82,73,71,72,84,61,48,120,49,50,44,73,78,86,73,83,73,66,76,69,61,48,120,49,54,44,77,65,71,78,73,70,73,69,82,61,48,120,102,44,78,79,95,67,72,65,78,71,69,61,48,120,48,44,80,65,73,78,84,66,82,85,83,72,61,48,120,49,52,44,83,73,90,69,95,66,79,84,84,79,77,61,48,120,57,44,83,73,90,69,95,66,79,84,84,79,77,95,76,69,70,84,61,48,120,50,44,83,73,90,69,95,66,79,84,84,79,77,95,82,73,71,72,84,61,48,120,51,44,83,73,90,69,95,76,69,70,84,61,48,120,54,44,83,73,90,69,95,82,73,71,72,84,61,48,120,55,44,83,73,90,69,95,84,79,80,61,48,120,56,44,83,73,90,69,95,84,79,80,95,76,69,70,84,61,48,120,52,44,83,73,90,69,95,84,79,80,95,82,73,71,72,84,61,48,120,53,44,83,73,90,73,78,71,61,48,120,99,44,83,76,69,69,80,61,48,120,98,44,83,80,76,73,84,95,72,79,82,73,90,79,78,84,65,76,61,48,120,101,44,83,80,76,73,84,95,86,69,82,84,73,67,65,76,61,48,120,100,44,83,84,79,80,61,48,120,49,53,44,84,69,88,84,61,48,120,49,51,10,99,46,82,68,70,58,65,82,67,72,73,86,69,61,48,120,50,48,48,48,44,68,65,84,69,61,48,120,50,44,70,73,76,69,61,48,120,56,44,70,73,76,69,83,61,48,120,56,44,70,79,76,68,69,82,61,48,120,49,48,44,70,79,76,68,69,82,83,61,48,120,49,48,44,72,73,68,68,69,78,61,48,120,49,48,48,44,76,73,78,75,61,48,120,52,48,44,79,80,69,78,68,73,82,61,48,120,52,48,48,48,44,80,69,82,77,73,83,83,73,79,78,83,61,48,120,52,44,81,85,65,76,73,70,73,69,68,61,48,120,50,48,48,44,81,85,65,76,73,70,89,61,48,120,50,48,48,44,82,69,65,68,95,65,76,76,61,48,120,49,102,44,82,69,65,68,95,79,78,76,89,61,48,120,49,48,48,48,44,83,73,90,69,61,48,120,49,44,83,84,82,69,65,77,61,48,120,56,48,48,44,84,65,71,83,61,48,120,56,48,44,84,73,77,69,61,48,120,50,44,86,73,82,84,85,65,76,61,48,120,52,48,48,44,86,79,76,85,77,69,61,48,120,50,48,10,99,46,82,69,83,58,67,79,78,83,79,76,69,95,70,68,61,48,120,50,44,67,79,82,69,95,73,68,76,61,48,120,56,44,67,80,85,95,83,80,69,69,68,61,48,120,49,54,44,68,73,83,80,76,65,89,95,68,82,73,86,69,82,61,48,120,53,44,69,88,67,69,80,84,73,79,78,95,72,65,78,68,76,69,82,61,48,120,49,49,44,70,82,69,69,95,77,69,77,79,82,89,61,48,120,49,55,44,70,82,69,69,95,83,87,65,80,61,48,120,49,44,74,78,73,95,69,78,86,61,48,120,101,44,75,69,89,95,83,84,65,84,69,61,48,120,51,44,76,79,71,95,68,69,80,84,72,61,48,120,100,44,76,79,71,95,76,69,86,69,76,61,48,120,97,44,77,65,88,95,80,82,79,67,69,83,83,69,83,61,48,120,99,44,78,69,84,95,80,82,79,67,69,83,83,73,78,71,61,48,120,49,50,44,79,80,69,78,95,73,78,70,79,61,48,120,49,48,44,80,65,82,69,78,84,95,67,79,78,84,69,88,84,61,48,120,57,44,80,82,73,86,73,76,69,71,69,68,61,48,120,55,44,80,82,73,86,73,76,69,71,69,68,95,85,83,69,82,61,48,120,54,44,80,82,79,67,69,83,83,95,83,84,65,84,69,61,48,120,49,51,44,83,84,65,84,73,67,95,66,85,73,76,68,61,48,120,49,56,44,84,72,82,69,65,68,95,73,68,61,48,120,102,44,84,79,84,65,76,95,77,69,77,79,82,89,61,48,120,49,52,44,84,79,84,65,76,95,83,72,65,82,69,68,95,77,69,77,79,82,89,61,48,120,98,44,84,79,84,65,76,95,83,87,65,80,61,48,120,49,53,44,85,83,69,82,95,73,68,61,48,120,52,10,99,46,82,70,68,58,65,76,76,79,87,95,82,69,67,85,82,83,73,79,78,61,48,120,50,48,44,65,76,87,65,89,83,95,67,65,76,76,61,48,120,49,48,48,44,69,88,67,69,80,84,61,48,120,50,44,82,69,65,68,61,48,120,52,44,82,69,67,65,76,76,61,48,120,56,48,44,82,69,77,79,86,69,61,48,120,56,44,83,79,67,75,69,84,61,48,120,52,48,44,83,84,79,80,95,82,69,67,85,82,83,69,61,48,120,49,48,44,87,82,73,84,69,61,48,120,49,10,99,46,82,80,58,77,79,68,85,76,69,95,80,65,84,72,61,48,120,49,44,82,79,79,84,95,80,65,84,72,61,48,120,51,44,83,89,83,84,69,77,95,80,65,84,72,61,48,120,50,10,99,46,82,83,70,58,65,80,80,82,79,88,73,77,65,84,69,61,48,120,52,44,67,65,83,69,95,83,69,78,83,73,84,73,86,69,61,48,120,50,48,44,67,72,69,67,75,95,86,73,82,84,85,65,76,61,48,120,50,44,78,79,95,68,69,69,80,95,83,67,65,78,61,48,120,56,44,78,79,95,70,73,76,69,95,67,72,69,67,75,61,48,120,49,44,80,65,84,72,61,48,120,49,48,10,99,46,83,67,70,58,69,88,73,84,95,79,78,95,69,82,82,79,82,61,48,120,49,44,76,79,71,95,65,76,76,61,48,120,50,10,99,46,83,69,69,75,58,67,85,82,82,69,78,84,61,48,120,49,44,69,78,68,61,48,120,50,44,82,69,76,65,84,73,86,69,61,48,120,51,44,83,84,65,82,84,61,48,120,48,10,99,46,83,84,80,58,65,78,73,77,61,48,120,56,44,88,61,48,120,49,44,89,61,48,120,50,44,90,61,48,120,52,10,99,46,83,84,82,58,67,65,83,69,61,48,120,49,44,77,65,84,67,72,95,67,65,83,69,61,48,120,49,44,77,65,84,67,72,95,76,69,78,61,48,120,50,44,87,73,76,68,67,65,82,68,61,48,120,52,10,99,46,83,84,84,58,70,76,79,65,84,61,48,120,50,44,72,69,88,61,48,120,51,44,78,85,77,66,69,82,61,48,120,49,44,83,84,82,73,78,71,61,48,120,52,10,99,46,84,72,70,58,65,85,84,79,95,70,82,69,69,61,48,120,49,10,99,46,84,79,73,58,65,78,68,82,79,73,68,95,65,83,83,69,84,77,71,82,61,48,120,52,44,65,78,68,82,79,73,68,95,67,76,65,83,83,61,48,120,51,44,65,78,68,82,79,73,68,95,69,78,86,61,48,120,50,44,76,79,67,65,76,95,67,65,67,72,69,61,48,120,48,44,76,79,67,65,76,95,83,84,79,82,65,71,69,61,48,120,49,10,99,46,84,83,70,58,65,84,84,65,67,72,69,68,61,48,120,49,48,48,44,68,69,84,65,67,72,69,68,61,48,120,56,48,44,70,79,82,69,73,71,78,61,48,120,49,44,76,79,71,95,65,76,76,61,48,120,50,48,44,80,73,80,69,61,48,120,50,48,48,44,80,82,73,86,73,76,69,71,69,68,61,48,120,56,44,81,85,73,69,84,61,48,120,52,48,44,82,69,83,69,84,95,80,65,84,72,61,48,120,52,44,83,72,69,76,76,61,48,120,49,48,44,87,65,73,84,61,48,120,50,10,99,46,84,83,84,65,84,69,58,80,65,85,83,69,68,61,48,120,49,44,82,85,78,78,73,78,71,61,48,120,48,44,83,84,79,80,80,73,78,71,61,48,120,50,44,84,69,82,77,73,78,65,84,69,68,61,48,120,51,10,99,46,86,65,83,58,67,65,83,69,95,83,69,78,83,73,84,73,86,69,61,48,120,102,44,67,76,79,83,69,95,68,73,82,61,48,120,54,44,67,82,69,65,84,69,95,76,73,78,75,61,48,120,49,49,44,68,69,76,69,84,69,61,48,120,51,44,68,69,82,69,71,73,83,84,69,82,61,48,120,49,44,68,82,73,86,69,82,95,83,73,90,69,61,48,120,49,50,44,71,69,84,95,68,69,86,73,67,69,95,73,78,70,79,61,48,120,98,44,71,69,84,95,73,78,70,79,61,48,120,97,44,73,68,69,78,84,73,70,89,95,70,73,76,69,61,48,120,99,44,73,71,78,79,82,69,95,70,73,76,69,61,48,120,57,44,77,65,75,69,95,68,73,82,61,48,120,100,44,79,80,69,78,95,68,73,82,61,48,120,53,44,82,69,65,68,95,76,73,78,75,61,48,120,49,48,44,82,69,78,65,77,69,61,48,120,52,44,83,65,77,69,95,70,73,76,69,61,48,120,101,44,83,67,65,78,95,68,73,82,61,48,120,50,44,84,69,83,84,95,80,65,84,72,61,48,120,55,44,87,65,84,67,72,95,80,65,84,72,61,48,120,56,10,99,46,86,76,70,58,65,80,73,61,48,120,50,48,44,66,82,65,78,67,72,61,48,120,49,44,67,82,73,84,73,67,65,76,61,48,120,56,44,68,69,66,85,71,61,48,120,56,48,44,69,82,82,79,82,61,48,120,50,44,69,88,84,65,80,73,61,48,120,52,48,44,70,85,78,67,84,73,79,78,61,48,120,50,48,48,44,73,78,70,79,61,48,120,49,48,44,84,82,65,67,69,61,48,120,49,48,48,44,87,65,82,78,73,78,71,61,48,120,52,10,99,46,86,79,76,85,77,69,58,72,73,68,68,69,78,61,48,120,52,44,80,82,73,79,82,73,84,89,61,48,120,50,44,82,69,80,76,65,67,69,61,48,120,49,44,83,89,83,84,69,77,61,48,120,56,10,0 };
    +char glIDL[] = { 115,46,73,110,112,117,116,69,118,101,110,116,58,112,78,101,120,116,58,73,110,112,117,116,69,118,101,110,116,44,100,86,97,108,117,101,44,120,84,105,109,101,115,116,97,109,112,44,108,82,101,99,105,112,105,101,110,116,73,68,44,108,79,118,101,114,73,68,44,100,65,98,115,88,44,100,65,98,115,89,44,100,88,44,100,89,44,108,68,101,118,105,99,101,73,68,44,108,84,121,112,101,44,108,70,108,97,103,115,44,108,77,97,115,107,10,115,46,100,99,82,101,113,117,101,115,116,58,108,73,116,101,109,44,99,80,114,101,102,101,114,101,110,99,101,91,52,93,10,115,46,100,99,65,117,100,105,111,58,108,83,105,122,101,44,108,70,111,114,109,97,116,10,115,46,100,99,75,101,121,69,110,116,114,121,58,108,70,108,97,103,115,44,108,86,97,108,117,101,44,120,84,105,109,101,115,116,97,109,112,44,108,85,110,105,99,111,100,101,10,115,46,100,99,68,101,118,105,99,101,73,110,112,117,116,58,100,86,97,108,117,101,115,91,50,93,44,120,84,105,109,101,115,116,97,109,112,44,108,68,101,118,105,99,101,73,68,44,108,70,108,97,103,115,44,108,84,121,112,101,10,115,46,68,97,116,101,84,105,109,101,58,119,89,101,97,114,44,99,77,111,110,116,104,44,99,68,97,121,44,99,72,111,117,114,44,99,77,105,110,117,116,101,44,99,83,101,99,111,110,100,44,99,84,105,109,101,90,111,110,101,10,115,46,72,83,86,58,100,72,117,101,44,100,83,97,116,117,114,97,116,105,111,110,44,100,86,97,108,117,101,10,115,46,70,82,71,66,58,102,82,101,100,44,102,71,114,101,101,110,44,102,66,108,117,101,44,102,65,108,112,104,97,10,115,46,82,71,66,56,58,117,99,82,101,100,44,117,99,71,114,101,101,110,44,117,99,66,108,117,101,44,117,99,65,108,112,104,97,10,115,46,82,71,66,49,54,58,117,119,82,101,100,44,117,119,71,114,101,101,110,44,117,119,66,108,117,101,44,117,119,65,108,112,104,97,10,115,46,82,71,66,51,50,58,117,108,82,101,100,44,117,108,71,114,101,101,110,44,117,108,66,108,117,101,44,117,108,65,108,112,104,97,10,115,46,82,71,66,80,97,108,101,116,116,101,58,108,65,109,116,67,111,108,111,117,114,115,44,101,67,111,108,58,82,71,66,56,91,50,53,54,93,10,115,46,67,111,108,111,117,114,70,111,114,109,97,116,58,117,99,82,101,100,83,104,105,102,116,44,117,99,71,114,101,101,110,83,104,105,102,116,44,117,99,66,108,117,101,83,104,105,102,116,44,117,99,65,108,112,104,97,83,104,105,102,116,44,117,99,82,101,100,77,97,115,107,44,117,99,71,114,101,101,110,77,97,115,107,44,117,99,66,108,117,101,77,97,115,107,44,117,99,65,108,112,104,97,77,97,115,107,44,117,99,82,101,100,80,111,115,44,117,99,71,114,101,101,110,80,111,115,44,117,99,66,108,117,101,80,111,115,44,117,99,65,108,112,104,97,80,111,115,44,117,99,66,105,116,115,80,101,114,80,105,120,101,108,10,115,46,67,108,105,112,82,101,99,116,97,110,103,108,101,58,108,76,101,102,116,44,108,84,111,112,44,108,82,105,103,104,116,44,108,66,111,116,116,111,109,10,115,46,69,100,103,101,115,58,108,76,101,102,116,44,108,84,111,112,44,108,82,105,103,104,116,44,108,66,111,116,116,111,109,10,115,46,79,98,106,101,99,116,83,105,103,110,97,108,58,111,79,98,106,101,99,116,10,115,46,112,102,66,97,115,101,54,52,68,101,99,111,100,101,58,117,99,83,116,101,112,44,117,99,80,108,97,105,110,67,104,97,114,44,117,99,66,105,116,10,115,46,112,102,66,97,115,101,54,52,69,110,99,111,100,101,58,117,99,83,116,101,112,44,117,99,82,101,115,117,108,116,44,108,83,116,101,112,67,111,117,110,116,10,115,46,70,117,110,99,116,105,111,110,70,105,101,108,100,58,115,78,97,109,101,44,117,108,84,121,112,101,10,115,46,70,117,110,99,116,105,111,110,58,112,65,100,100,114,101,115,115,44,115,78,97,109,101,44,112,65,114,103,115,58,70,117,110,99,116,105,111,110,70,105,101,108,100,10,115,46,70,105,101,108,100,65,114,114,97,121,58,115,78,97,109,101,44,112,71,101,116,70,105,101,108,100,44,112,83,101,116,70,105,101,108,100,44,109,65,114,103,44,117,108,70,108,97,103,115,10,115,46,70,105,101,108,100,68,101,102,58,115,78,97,109,101,44,108,86,97,108,117,101,10,115,46,83,121,115,116,101,109,83,116,97,116,101,58,115,80,108,97,116,102,111,114,109,44,108,67,111,110,115,111,108,101,70,68,44,108,83,116,97,103,101,10,115,46,86,97,114,105,97,98,108,101,58,117,108,84,121,112,101,44,108,85,110,117,115,101,100,44,120,76,97,114,103,101,44,100,68,111,117,98,108,101,44,112,80,111,105,110,116,101,114,10,115,46,65,99,116,105,111,110,65,114,114,97,121,58,112,82,111,117,116,105,110,101,44,108,65,99,116,105,111,110,67,111,100,101,10,115,46,65,99,116,105,111,110,84,97,98,108,101,58,117,108,72,97,115,104,44,108,83,105,122,101,44,115,78,97,109,101,44,112,65,114,103,115,58,70,117,110,99,116,105,111,110,70,105,101,108,100,10,115,46,67,104,105,108,100,69,110,116,114,121,58,108,79,98,106,101,99,116,73,68,44,117,108,67,108,97,115,115,73,68,10,115,46,77,101,115,115,97,103,101,58,120,84,105,109,101,44,108,85,73,68,44,108,84,121,112,101,44,108,83,105,122,101,10,115,46,77,101,109,73,110,102,111,58,112,83,116,97,114,116,44,108,79,98,106,101,99,116,73,68,44,117,108,83,105,122,101,44,108,70,108,97,103,115,44,108,77,101,109,111,114,121,73,68,44,119,65,99,99,101,115,115,67,111,117,110,116,10,115,46,67,111,109,112,114,101,115,115,105,111,110,70,101,101,100,98,97,99,107,58,108,70,101,101,100,98,97,99,107,73,68,44,108,73,110,100,101,120,44,115,80,97,116,104,44,115,68,101,115,116,44,120,80,114,111,103,114,101,115,115,44,120,79,114,105,103,105,110,97,108,83,105,122,101,44,120,67,111,109,112,114,101,115,115,101,100,83,105,122,101,44,119,89,101,97,114,44,119,77,111,110,116,104,44,119,68,97,121,44,119,72,111,117,114,44,119,77,105,110,117,116,101,44,119,83,101,99,111,110,100,10,115,46,67,111,109,112,114,101,115,115,101,100,73,116,101,109,58,120,79,114,105,103,105,110,97,108,83,105,122,101,44,120,67,111,109,112,114,101,115,115,101,100,83,105,122,101,44,112,78,101,120,116,58,67,111,109,112,114,101,115,115,101,100,73,116,101,109,44,115,80,97,116,104,44,108,80,101,114,109,105,115,115,105,111,110,115,44,108,85,115,101,114,73,68,44,108,71,114,111,117,112,73,68,44,108,79,116,104,101,114,115,73,68,44,108,70,108,97,103,115,44,101,67,114,101,97,116,101,100,58,68,97,116,101,84,105,109,101,44,101,77,111,100,105,102,105,101,100,58,68,97,116,101,84,105,109,101,10,115,46,70,105,108,101,73,110,102,111,58,120,83,105,122,101,44,120,84,105,109,101,83,116,97,109,112,44,112,78,101,120,116,58,70,105,108,101,73,110,102,111,44,115,78,97,109,101,44,108,70,108,97,103,115,44,108,80,101,114,109,105,115,115,105,111,110,115,44,108,85,115,101,114,73,68,44,108,71,114,111,117,112,73,68,44,101,67,114,101,97,116,101,100,58,68,97,116,101,84,105,109,101,44,101,77,111,100,105,102,105,101,100,58,68,97,116,101,84,105,109,101,10,115,46,68,105,114,73,110,102,111,58,112,73,110,102,111,58,70,105,108,101,73,110,102,111,10,115,46,70,105,108,101,70,101,101,100,98,97,99,107,58,120,83,105,122,101,44,120,80,111,115,105,116,105,111,110,44,115,80,97,116,104,44,115,68,101,115,116,44,108,70,101,101,100,98,97,99,107,73,68,44,99,82,101,115,101,114,118,101,100,91,51,50,93,10,115,46,70,105,101,108,100,58,109,65,114,103,44,112,71,101,116,86,97,108,117,101,44,112,83,101,116,86,97,108,117,101,44,112,87,114,105,116,101,86,97,108,117,101,44,115,78,97,109,101,44,117,108,70,105,101,108,100,73,68,44,117,119,79,102,102,115,101,116,44,117,119,73,110,100,101,120,44,117,108,70,108,97,103,115,10,99,46,65,67,58,65,99,116,105,118,97,116,101,61,48,120,50,44,67,108,101,97,114,61,48,120,52,44,67,108,105,112,98,111,97,114,100,61,48,120,50,100,44,67,111,112,121,68,97,116,97,61,48,120,55,44,67,117,115,116,111,109,61,48,120,51,52,44,68,97,116,97,70,101,101,100,61,48,120,56,44,68,101,97,99,116,105,118,97,116,101,61,48,120,57,44,68,105,115,97,98,108,101,61,48,120,50,102,44,68,114,97,103,68,114,111,112,61,48,120,49,48,44,68,114,97,119,61,48,120,97,44,69,78,68,61,48,120,51,53,44,69,110,97,98,108,101,61,48,120,51,48,44,70,108,117,115,104,61,48,120,98,44,70,111,99,117,115,61,48,120,99,44,70,114,101,101,61,48,120,100,44,70,114,101,101,87,97,114,110,105,110,103,61,48,120,53,44,71,101,116,86,97,114,61,48,120,102,44,72,105,100,101,61,48,120,49,49,44,73,110,105,116,61,48,120,49,50,44,76,111,99,107,61,48,120,49,51,44,76,111,115,116,70,111,99,117,115,61,48,120,49,52,44,77,111,118,101,61,48,120,49,53,44,77,111,118,101,84,111,66,97,99,107,61,48,120,49,54,44,77,111,118,101,84,111,70,114,111,110,116,61,48,120,49,55,44,77,111,118,101,84,111,80,111,105,110,116,61,48,120,51,50,44,78,101,119,67,104,105,108,100,61,48,120,49,56,44,78,101,119,79,98,106,101,99,116,61,48,120,49,97,44,78,101,119,79,119,110,101,114,61,48,120,49,57,44,78,101,120,116,61,48,120,50,57,44,80,114,101,118,61,48,120,50,97,44,81,117,101,114,121,61,48,120,49,99,44,82,101,97,100,61,48,120,49,100,44,82,101,100,105,109,101,110,115,105,111,110,61,48,120,51,49,44,82,101,100,111,61,48,120,49,98,44,82,101,102,114,101,115,104,61,48,120,50,101,44,82,101,110,97,109,101,61,48,120,49,101,44,82,101,115,101,116,61,48,120,49,102,44,82,101,115,105,122,101,61,48,120,50,48,44,83,97,118,101,73,109,97,103,101,61,48,120,50,49,44,83,97,118,101,83,101,116,116,105,110,103,115,61,48,120,101,44,83,97,118,101,84,111,79,98,106,101,99,116,61,48,120,50,50,44,83,99,114,111,108,108,61,48,120,50,51,44,83,99,114,111,108,108,84,111,80,111,105,110,116,61,48,120,51,51,44,83,101,101,107,61,48,120,50,52,44,83,101,108,101,99,116,65,114,101,97,61,48,120,51,44,83,101,116,70,105,101,108,100,61,48,120,50,99,44,83,101,116,86,97,114,61,48,120,50,53,44,83,104,111,119,61,48,120,50,54,44,83,105,103,110,97,108,61,48,120,49,44,83,111,114,116,61,48,120,54,44,85,110,100,111,61,48,120,50,55,44,85,110,108,111,99,107,61,48,120,50,56,44,87,114,105,116,101,61,48,120,50,98,10,99,46,65,76,73,71,78,58,66,79,84,84,79,77,61,48,120,50,48,44,67,69,78,84,69,82,61,48,120,99,44,72,79,82,73,90,79,78,84,65,76,61,48,120,52,44,76,69,70,84,61,48,120,49,44,77,73,68,68,76,69,61,48,120,99,44,82,73,71,72,84,61,48,120,50,44,84,79,80,61,48,120,49,48,44,86,69,82,84,73,67,65,76,61,48,120,56,10,99,46,67,67,70,58,65,85,68,73,79,61,48,120,50,48,48,44,67,79,77,77,65,78,68,61,48,120,49,44,68,65,84,65,61,48,120,52,48,48,44,68,82,65,87,65,66,76,69,61,48,120,50,44,69,70,70,69,67,84,61,48,120,52,44,70,73,76,69,83,89,83,84,69,77,61,48,120,56,44,71,82,65,80,72,73,67,83,61,48,120,49,48,44,71,85,73,61,48,120,50,48,44,73,79,61,48,120,52,48,44,77,73,83,67,61,48,120,56,48,48,44,77,85,76,84,73,77,69,68,73,65,61,48,120,50,48,48,48,44,78,69,84,87,79,82,75,61,48,120,49,48,48,48,44,83,89,83,84,69,77,61,48,120,56,48,44,84,79,79,76,61,48,120,49,48,48,10,99,46,67,70,58,68,69,70,76,65,84,69,61,48,120,51,44,71,90,73,80,61,48,120,49,44,90,76,73,66,61,48,120,50,10,99,46,67,76,70,58,78,79,95,79,87,78,69,82,83,72,73,80,61,48,120,50,44,80,82,79,77,79,84,69,95,73,78,84,69,71,82,65,76,61,48,120,49,10,99,46,67,76,73,80,77,79,68,69,58,67,79,80,89,61,48,120,50,44,67,85,84,61,48,120,49,44,80,65,83,84,69,61,48,120,52,10,99,46,67,77,70,58,65,80,80,76,89,95,83,69,67,85,82,73,84,89,61,48,120,50,48,44,67,82,69,65,84,69,95,70,73,76,69,61,48,120,52,44,78,69,87,61,48,120,50,44,78,79,95,76,73,78,75,83,61,48,120,49,48,44,80,65,83,83,87,79,82,68,61,48,120,49,44,82,69,65,68,95,79,78,76,89,61,48,120,56,10,99,46,67,78,70,58,65,85,84,79,95,83,65,86,69,61,48,120,50,44,78,69,87,61,48,120,56,44,79,80,84,73,79,78,65,76,95,70,73,76,69,83,61,48,120,52,44,83,84,82,73,80,95,81,85,79,84,69,83,61,48,120,49,10,99,46,68,65,84,65,58,65,85,68,73,79,61,48,120,53,44,67,79,78,84,69,78,84,61,48,120,98,44,68,69,86,73,67,69,95,73,78,80,85,84,61,48,120,51,44,70,73,76,69,61,48,120,97,44,73,77,65,71,69,61,48,120,55,44,73,78,80,85,84,95,82,69,65,68,89,61,48,120,99,44,82,65,87,61,48,120,50,44,82,69,67,69,73,80,84,61,48,120,57,44,82,69,67,79,82,68,61,48,120,54,44,82,69,81,85,69,83,84,61,48,120,56,44,84,69,88,84,61,48,120,49,44,88,77,76,61,48,120,52,10,99,46,68,69,86,73,67,69,58,67,79,77,80,65,67,84,95,68,73,83,67,61,48,120,49,44,70,76,79,80,80,89,95,68,73,83,75,61,48,120,52,44,72,65,82,68,95,68,73,83,75,61,48,120,50,44,77,69,77,79,82,89,61,48,120,49,48,48,48,44,77,79,68,69,77,61,48,120,50,48,48,48,44,78,69,84,87,79,82,75,61,48,120,56,48,44,80,82,73,78,84,69,82,61,48,120,50,48,48,44,80,82,73,78,84,69,82,95,51,68,61,48,120,56,48,48,48,44,82,69,65,68,61,48,120,56,44,82,69,77,79,86,65,66,76,69,61,48,120,50,48,44,82,69,77,79,86,69,65,66,76,69,61,48,120,50,48,44,83,67,65,78,78,69,82,61,48,120,52,48,48,44,83,67,65,78,78,69,82,95,51,68,61,48,120,49,48,48,48,48,44,83,79,70,84,87,65,82,69,61,48,120,52,48,44,84,65,80,69,61,48,120,49,48,48,44,84,69,77,80,79,82,65,82,89,61,48,120,56,48,48,44,85,83,66,61,48,120,52,48,48,48,44,87,82,73,84,69,61,48,120,49,48,10,99,46,68,77,70,58,70,73,88,69,68,95,67,69,78,84,69,82,95,88,61,48,120,49,48,48,48,48,48,44,70,73,88,69,68,95,67,69,78,84,69,82,95,89,61,48,120,50,48,48,48,48,48,44,70,73,88,69,68,95,68,69,80,84,72,61,48,120,49,48,48,48,44,70,73,88,69,68,95,72,69,73,71,72,84,61,48,120,49,48,48,44,70,73,88,69,68,95,82,65,68,73,85,83,61,48,120,50,48,50,48,48,48,48,44,70,73,88,69,68,95,82,65,68,73,85,83,95,88,61,48,120,50,48,48,48,48,44,70,73,88,69,68,95,82,65,68,73,85,83,95,89,61,48,120,50,48,48,48,48,48,48,44,70,73,88,69,68,95,87,73,68,84,72,61,48,120,50,48,48,44,70,73,88,69,68,95,88,61,48,120,52,44,70,73,88,69,68,95,88,95,79,70,70,83,69,84,61,48,120,52,48,44,70,73,88,69,68,95,89,61,48,120,56,44,70,73,88,69,68,95,89,95,79,70,70,83,69,84,61,48,120,56,48,44,70,73,88,69,68,95,90,61,48,120,52,48,48,48,44,72,69,73,71,72,84,61,48,120,53,48,48,44,72,69,73,71,72,84,95,70,76,65,71,83,61,48,120,53,97,48,44,72,79,82,73,90,79,78,84,65,76,95,70,76,65,71,83,61,48,120,97,53,53,44,83,67,65,76,69,68,95,67,69,78,84,69,82,95,88,61,48,120,52,48,48,48,48,44,83,67,65,76,69,68,95,67,69,78,84,69,82,95,89,61,48,120,56,48,48,48,48,44,83,67,65,76,69,68,95,68,69,80,84,72,61,48,120,50,48,48,48,44,83,67,65,76,69,68,95,72,69,73,71,72,84,61,48,120,52,48,48,44,83,67,65,76,69,68,95,82,65,68,73,85,83,61,48,120,49,48,49,48,48,48,48,44,83,67,65,76,69,68,95,82,65,68,73,85,83,95,88,61,48,120,49,48,48,48,48,44,83,67,65,76,69,68,95,82,65,68,73,85,83,95,89,61,48,120,49,48,48,48,48,48,48,44,83,67,65,76,69,68,95,87,73,68,84,72,61,48,120,56,48,48,44,83,67,65,76,69,68,95,88,61,48,120,49,44,83,67,65,76,69,68,95,88,95,79,70,70,83,69,84,61,48,120,49,48,44,83,67,65,76,69,68,95,89,61,48,120,50,44,83,67,65,76,69,68,95,89,95,79,70,70,83,69,84,61,48,120,50,48,44,83,67,65,76,69,68,95,90,61,48,120,56,48,48,48,44,83,84,65,84,85,83,95,67,72,65,78,71,69,61,48,120,99,48,48,48,48,48,44,83,84,65,84,85,83,95,67,72,65,78,71,69,95,72,61,48,120,52,48,48,48,48,48,44,83,84,65,84,85,83,95,67,72,65,78,71,69,95,86,61,48,120,56,48,48,48,48,48,44,86,69,82,84,73,67,65,76,95,70,76,65,71,83,61,48,120,53,97,97,44,87,73,68,84,72,61,48,120,97,48,48,44,87,73,68,84,72,95,70,76,65,71,83,61,48,120,97,53,48,44,88,61,48,120,53,44,88,95,79,70,70,83,69,84,61,48,120,53,48,44,89,61,48,120,97,44,89,95,79,70,70,83,69,84,61,48,120,97,48,10,99,46,68,82,76,58,68,79,87,78,61,48,120,49,44,69,65,83,84,61,48,120,50,44,76,69,70,84,61,48,120,51,44,78,79,82,84,72,61,48,120,48,44,78,79,82,84,72,95,69,65,83,84,61,48,120,52,44,78,79,82,84,72,95,87,69,83,84,61,48,120,53,44,82,73,71,72,84,61,48,120,50,44,83,79,85,84,72,61,48,120,49,44,83,79,85,84,72,95,69,65,83,84,61,48,120,54,44,83,79,85,84,72,95,87,69,83,84,61,48,120,55,44,85,80,61,48,120,48,44,87,69,83,84,61,48,120,51,10,99,46,69,68,71,69,58,65,76,76,61,48,120,102,102,44,66,79,84,84,79,77,61,48,120,56,44,66,79,84,84,79,77,95,76,69,70,84,61,48,120,52,48,44,66,79,84,84,79,77,95,82,73,71,72,84,61,48,120,56,48,44,76,69,70,84,61,48,120,50,44,82,73,71,72,84,61,48,120,52,44,84,79,80,61,48,120,49,44,84,79,80,95,76,69,70,84,61,48,120,49,48,44,84,79,80,95,82,73,71,72,84,61,48,120,50,48,10,99,46,69,82,70,58,78,111,116,105,102,105,101,100,61,48,120,52,48,48,48,48,48,48,48,10,99,46,69,82,82,58,65,99,99,101,115,115,77,101,109,111,114,121,61,48,120,52,98,44,65,99,99,101,115,115,79,98,106,101,99,116,61,48,120,53,51,44,65,99,99,101,115,115,83,101,109,97,112,104,111,114,101,61,48,120,55,51,44,65,99,116,105,118,97,116,101,61,48,120,52,50,44,65,100,100,67,108,97,115,115,61,48,120,52,49,44,65,108,108,111,99,77,101,109,111,114,121,61,48,120,53,52,44,65,108,108,111,99,83,101,109,97,112,104,111,114,101,61,48,120,55,50,44,65,108,114,101,97,100,121,68,101,102,105,110,101,100,61,48,120,98,54,44,65,108,114,101,97,100,121,76,111,99,107,101,100,61,48,120,57,99,44,65,114,103,115,61,48,120,49,52,44,65,114,114,97,121,70,117,108,108,61,48,120,50,100,44,66,117,102,102,101,114,79,118,101,114,102,108,111,119,61,48,120,53,99,44,66,117,115,121,61,48,120,56,98,44,67,97,110,99,101,108,108,101,100,61,48,120,51,44,67,97,114,100,82,101,97,100,101,114,85,110,97,118,97,105,108,97,98,108,101,61,48,120,57,102,44,67,97,114,100,82,101,97,100,101,114,85,110,107,110,111,119,110,61,48,120,57,100,44,67,111,109,112,114,101,115,115,105,111,110,61,48,120,97,100,44,67,111,110,110,101,99,116,105,111,110,65,98,111,114,116,101,100,61,48,120,56,99,44,67,111,110,110,101,99,116,105,111,110,82,101,102,117,115,101,100,61,48,120,56,51,44,67,111,110,115,116,114,97,105,110,116,86,105,111,108,97,116,105,111,110,61,48,120,56,56,44,67,111,110,116,105,110,117,101,61,48,120,53,44,67,111,114,101,86,101,114,115,105,111,110,61,48,120,50,54,44,67,114,101,97,116,101,70,105,108,101,61,48,120,55,52,44,67,114,101,97,116,101,79,98,106,101,99,116,61,48,120,54,53,44,67,114,101,97,116,101,82,101,115,111,117,114,99,101,61,48,120,98,50,44,68,97,116,97,83,105,122,101,61,48,120,56,97,44,68,101,97,99,116,105,118,97,116,101,100,61,48,120,57,97,44,68,101,97,100,76,111,99,107,61,48,120,51,101,44,68,101,99,111,109,112,114,101,115,115,105,111,110,61,48,120,97,99,44,68,101,108,101,116,101,70,105,108,101,61,48,120,55,53,44,68,105,114,69,109,112,116,121,61,48,120,56,44,68,105,115,99,111,110,110,101,99,116,101,100,61,48,120,56,54,44,68,111,78,111,116,69,120,112,117,110,103,101,61,48,120,51,48,44,68,111,101,115,78,111,116,69,120,105,115,116,61,48,120,55,56,44,68,111,117,98,108,101,73,110,105,116,61,48,120,52,51,44,68,114,97,119,61,48,120,52,56,44,69,78,68,61,48,120,98,101,44,69,109,112,116,121,83,116,114,105,110,103,61,48,120,54,100,44,69,110,100,79,102,70,105,108,101,61,48,120,55,101,44,69,110,116,114,121,77,105,115,115,105,110,103,72,101,97,100,101,114,61,48,120,51,97,44,69,120,97,109,105,110,101,70,97,105,108,101,100,61,48,120,49,57,44,69,120,99,101,112,116,105,111,110,61,48,120,97,51,44,69,120,99,101,112,116,105,111,110,84,104,114,101,115,104,111,108,100,61,48,120,57,44,69,120,99,108,117,115,105,118,101,68,101,110,105,101,100,61,48,120,53,51,44,69,120,101,99,86,105,111,108,97,116,105,111,110,61,48,120,56,102,44,69,120,105,115,116,115,61,48,120,55,97,44,69,120,112,101,99,116,101,100,70,105,108,101,61,48,120,54,102,44,69,120,112,101,99,116,101,100,70,111,108,100,101,114,61,48,120,97,101,44,70,97,105,108,101,100,61,48,120,100,44,70,97,108,115,101,61,48,120,49,44,70,105,101,108,100,78,111,116,83,101,116,61,48,120,52,52,44,70,105,101,108,100,83,101,97,114,99,104,61,48,120,51,50,44,70,105,101,108,100,84,121,112,101,77,105,115,109,97,116,99,104,61,48,120,53,97,44,70,105,108,101,61,48,120,101,44,70,105,108,101,68,111,101,115,78,111,116,69,120,105,115,116,61,48,120,49,50,44,70,105,108,101,69,120,105,115,116,115,61,48,120,54,51,44,70,105,108,101,78,111,116,70,111,117,110,100,61,48,120,49,50,44,70,105,108,101,82,101,97,100,70,108,97,103,61,48,120,52,54,44,70,105,108,101,87,114,105,116,101,70,108,97,103,61,48,120,52,55,44,70,105,110,105,115,104,101,100,61,48,120,55,101,44,70,117,110,99,116,105,111,110,61,48,120,98,53,44,71,101,116,70,105,101,108,100,61,48,120,53,54,44,71,101,116,83,117,114,102,97,99,101,73,110,102,111,61,48,120,55,100,44,72,111,115,116,78,111,116,70,111,117,110,100,61,48,120,56,49,44,72,111,115,116,85,110,114,101,97,99,104,97,98,108,101,61,48,120,56,53,44,73,100,101,110,116,105,99,97,108,80,97,116,104,115,61,48,120,55,57,44,73,108,108,101,103,97,108,65,99,116,105,111,110,65,116,116,101,109,112,116,61,48,120,51,57,44,73,108,108,101,103,97,108,65,99,116,105,111,110,73,68,61,48,120,51,55,44,73,108,108,101,103,97,108,65,100,100,114,101,115,115,61,48,120,57,49,44,73,108,108,101,103,97,108,77,101,116,104,111,100,73,68,61,48,120,51,54,44,73,109,109,117,116,97,98,108,101,61,48,120,97,102,44,73,110,85,115,101,61,48,120,99,44,73,110,105,116,61,48,120,50,49,44,73,110,105,116,77,111,100,117,108,101,61,48,120,49,49,44,73,110,112,117,116,79,117,116,112,117,116,61,48,120,57,52,44,73,110,116,101,103,114,105,116,121,86,105,111,108,97,116,105,111,110,61,48,120,56,56,44,73,110,118,97,108,105,100,68,97,116,97,61,48,120,102,44,73,110,118,97,108,105,100,68,105,109,101,110,115,105,111,110,61,48,120,53,57,44,73,110,118,97,108,105,100,72,84,84,80,82,101,115,112,111,110,115,101,61,48,120,97,49,44,73,110,118,97,108,105,100,72,97,110,100,108,101,61,48,120,57,54,44,73,110,118,97,108,105,100,79,98,106,101,99,116,61,48,120,56,101,44,73,110,118,97,108,105,100,80,97,116,104,61,48,120,51,51,44,73,110,118,97,108,105,100,82,101,102,101,114,101,110,99,101,61,48,120,97,50,44,73,110,118,97,108,105,100,83,116,97,116,101,61,48,120,56,48,44,73,110,118,97,108,105,100,85,82,73,61,48,120,56,50,44,73,110,118,97,108,105,100,86,97,108,117,101,61,48,120,57,56,44,76,105,109,105,116,101,100,83,117,99,99,101,115,115,61,48,120,50,44,76,105,115,116,67,104,105,108,100,114,101,110,61,48,120,54,97,44,76,111,97,100,77,111,100,117,108,101,61,48,120,57,53,44,76,111,99,107,61,48,120,49,56,44,76,111,99,107,70,97,105,108,101,100,61,48,120,49,56,44,76,111,99,107,77,117,116,101,120,61,48,120,97,97,44,76,111,99,107,82,101,113,117,105,114,101,100,61,48,120,57,98,44,76,111,99,107,101,100,61,48,120,57,99,44,76,111,111,112,61,48,120,54,50,44,76,111,115,116,67,108,97,115,115,61,48,120,49,97,44,76,111,115,116,79,119,110,101,114,61,48,120,50,102,44,76,111,119,67,97,112,97,99,105,116,121,61,48,120,50,48,44,77,97,114,107,101,100,70,111,114,68,101,108,101,116,105,111,110,61,48,120,51,53,44,77,101,109,111,114,121,61,48,120,49,100,44,77,101,109,111,114,121,67,111,114,114,117,112,116,61,48,120,51,49,44,77,101,109,111,114,121,68,111,101,115,78,111,116,69,120,105,115,116,61,48,120,51,100,44,77,101,109,111,114,121,73,110,102,111,61,48,120,54,54,44,77,105,115,109,97,116,99,104,61,48,120,53,101,44,77,105,115,115,105,110,103,67,108,97,115,115,61,48,120,52,53,44,77,105,115,115,105,110,103,67,108,97,115,115,78,97,109,101,61,48,120,50,97,44,77,105,115,115,105,110,103,80,97,116,104,61,48,120,52,99,44,77,111,100,117,108,101,73,110,105,116,70,97,105,108,101,100,61,48,120,51,99,44,77,111,100,117,108,101,77,105,115,115,105,110,103,73,110,105,116,61,48,120,51,98,44,77,111,100,117,108,101,77,105,115,115,105,110,103,78,97,109,101,61,48,120,52,48,44,77,111,100,117,108,101,79,112,101,110,70,97,105,108,101,100,61,48,120,51,56,44,78,101,101,100,79,119,110,101,114,61,48,120,50,52,44,78,101,101,100,87,105,100,116,104,72,101,105,103,104,116,61,48,120,50,55,44,78,101,103,97,116,105,118,101,67,108,97,115,115,73,68,61,48,120,50,57,44,78,101,103,97,116,105,118,101,83,117,98,67,108,97,115,115,73,68,61,48,120,50,56,44,78,101,116,119,111,114,107,85,110,114,101,97,99,104,97,98,108,101,61,48,120,56,52,44,78,101,119,79,98,106,101,99,116,61,48,120,53,53,44,78,111,65,99,116,105,111,110,61,48,120,49,98,44,78,111,68,97,116,97,61,48,120,49,53,44,78,111,70,105,101,108,100,65,99,99,101,115,115,61,48,120,53,55,44,78,111,77,97,116,99,104,105,110,103,79,98,106,101,99,116,61,48,120,52,97,44,78,111,77,101,100,105,97,73,110,115,101,114,116,101,100,61,48,120,57,101,44,78,111,77,101,109,111,114,121,61,48,120,97,44,78,111,77,101,116,104,111,100,115,61,48,120,52,57,44,78,111,80,101,114,109,105,115,115,105,111,110,61,48,120,50,50,44,78,111,80,111,105,110,116,101,114,61,48,120,98,44,78,111,83,101,97,114,99,104,82,101,115,117,108,116,61,48,120,52,101,44,78,111,83,116,97,116,115,61,48,120,49,102,44,78,111,83,117,112,112,111,114,116,61,48,120,49,99,44,78,111,116,70,111,117,110,100,61,48,120,49,48,44,78,111,116,73,110,105,116,105,97,108,105,115,101,100,61,48,120,54,55,44,78,111,116,76,111,99,107,101,100,61,48,120,52,100,44,78,111,116,80,111,115,115,105,98,108,101,61,48,120,98,51,44,78,111,116,104,105,110,103,68,111,110,101,61,48,120,52,44,78,111,116,105,102,105,101,100,61,48,120,52,48,48,48,48,48,48,48,44,78,117,108,108,65,114,103,115,61,48,120,56,100,44,79,98,106,101,99,116,67,111,114,114,117,112,116,61,48,120,53,48,44,79,98,106,101,99,116,69,120,105,115,116,115,61,48,120,54,101,44,79,98,115,111,108,101,116,101,61,48,120,98,49,44,79,98,116,97,105,110,77,101,116,104,111,100,61,48,120,50,99,44,79,107,97,121,61,48,120,48,44,79,112,101,110,70,105,108,101,61,48,120,55,54,44,79,112,101,110,71,76,61,48,120,97,53,44,79,117,116,79,102,66,111,117,110,100,115,61,48,120,53,102,44,79,117,116,79,102,68,97,116,97,61,48,120,55,101,44,79,117,116,79,102,82,97,110,103,101,61,48,120,50,98,44,79,117,116,79,102,83,112,97,99,101,61,48,120,55,99,44,79,117,116,115,105,100,101,77,97,105,110,84,104,114,101,97,100,61,48,120,97,54,44,79,119,110,101,114,78,101,101,100,115,66,105,116,109,97,112,61,48,120,50,53,44,79,119,110,101,114,80,97,115,115,84,104,114,111,117,103,104,61,48,120,53,49,44,80,101,114,109,105,115,115,105,111,110,68,101,110,105,101,100,61,48,120,50,50,44,80,101,114,109,105,115,115,105,111,110,115,61,48,120,50,50,44,80,114,111,120,121,83,83,76,84,117,110,110,101,108,61,48,120,97,48,44,81,117,101,114,121,61,48,120,50,101,44,82,101,97,100,61,48,120,49,54,44,82,101,97,100,70,105,108,101,84,111,66,117,102,102,101,114,61,48,120,98,48,44,82,101,97,100,79,110,108,121,61,48,120,55,55,44,82,101,97,108,108,111,99,77,101,109,111,114,121,61,48,120,54,49,44,82,101,99,117,114,115,105,111,110,61,48,120,57,48,44,82,101,100,105,109,101,110,115,105,111,110,61,48,120,55,49,44,82,101,102,114,101,115,104,61,48,120,54,57,44,82,101,115,105,122,101,61,48,120,55,48,44,82,101,115,111,108,118,101,80,97,116,104,61,48,120,54,52,44,82,101,115,111,108,118,101,83,121,109,98,111,108,61,48,120,98,52,44,82,101,115,111,117,114,99,101,69,120,105,115,116,115,61,48,120,54,56,44,82,101,116,114,121,61,48,120,55,44,83,97,110,105,116,121,70,97,105,108,117,114,101,61,48,120,55,98,44,83,99,104,101,109,97,86,105,111,108,97,116,105,111,110,61,48,120,56,57,44,83,101,97,114,99,104,61,48,120,49,48,44,83,101,99,117,114,105,116,121,61,48,120,57,55,44,83,101,101,107,61,48,120,54,48,44,83,101,114,118,105,99,101,85,110,97,118,97,105,108,97,98,108,101,61,48,120,57,57,44,83,101,116,70,105,101,108,100,61,48,120,51,52,44,83,101,116,86,97,108,117,101,78,111,116,65,114,114,97,121,61,48,120,98,99,44,83,101,116,86,97,108,117,101,78,111,116,70,117,110,99,116,105,111,110,61,48,120,98,97,44,83,101,116,86,97,108,117,101,78,111,116,76,111,111,107,117,112,61,48,120,98,100,44,83,101,116,86,97,108,117,101,78,111,116,78,117,109,101,114,105,99,61,48,120,98,55,44,83,101,116,86,97,108,117,101,78,111,116,79,98,106,101,99,116,61,48,120,98,57,44,83,101,116,86,97,108,117,101,78,111,116,80,111,105,110,116,101,114,61,48,120,98,98,44,83,101,116,86,97,108,117,101,78,111,116,83,116,114,105,110,103,61,48,120,98,56,44,83,101,116,86,111,108,117,109,101,61,48,120,97,98,44,83,107,105,112,61,48,120,54,44,83,109,97,108,108,77,97,115,107,61,48,120,54,99,44,83,116,97,116,101,109,101,110,116,85,110,115,97,116,105,115,102,105,101,100,61,48,120,52,102,44,83,116,114,105,110,103,70,111,114,109,97,116,61,48,120,55,102,44,83,121,110,116,97,120,61,48,120,55,102,44,83,121,115,116,101,109,67,97,108,108,61,48,120,54,98,44,83,121,115,116,101,109,67,111,114,114,117,112,116,61,48,120,50,51,44,83,121,115,116,101,109,76,111,99,107,101,100,61,48,120,51,102,44,84,97,115,107,83,116,105,108,108,69,120,105,115,116,115,61,48,120,56,55,44,84,101,114,109,105,110,97,116,101,61,48,120,57,44,84,104,114,101,97,100,65,108,114,101,97,100,121,65,99,116,105,118,101,61,48,120,97,52,44,84,104,114,101,97,100,78,111,116,76,111,99,107,101,100,61,48,120,97,57,44,84,105,109,101,79,117,116,61,48,120,49,101,44,84,114,117,101,61,48,120,48,44,85,110,98,97,108,97,110,99,101,100,88,77,76,61,48,120,57,50,44,85,110,100,101,102,105,110,101,100,70,105,101,108,100,61,48,120,52,52,44,85,110,114,101,99,111,103,110,105,115,101,100,70,105,101,108,100,84,121,112,101,61,48,120,53,98,44,85,110,115,117,112,112,111,114,116,101,100,70,105,101,108,100,61,48,120,53,100,44,85,110,115,117,112,112,111,114,116,101,100,79,119,110,101,114,61,48,120,53,50,44,85,115,101,83,117,98,67,108,97,115,115,61,48,120,97,55,44,86,105,114,116,117,97,108,86,111,108,117,109,101,61,48,120,53,56,44,87,111,117,108,100,66,108,111,99,107,61,48,120,57,51,44,87,114,105,116,101,61,48,120,49,55,44,87,114,111,110,103,67,108,97,115,115,61,48,120,56,101,44,87,114,111,110,103,79,98,106,101,99,116,84,121,112,101,61,48,120,56,101,44,87,114,111,110,103,84,121,112,101,61,48,120,97,56,44,87,114,111,110,103,86,101,114,115,105,111,110,61,48,120,49,51,10,99,46,69,86,71,58,65,78,68,82,79,73,68,61,48,120,100,44,65,80,80,61,48,120,99,44,65,85,68,73,79,61,48,120,56,44,67,76,65,83,83,61,48,120,98,44,68,73,83,80,76,65,89,61,48,120,53,44,69,78,68,61,48,120,101,44,70,73,76,69,83,89,83,84,69,77,61,48,120,49,44,71,85,73,61,48,120,52,44,72,65,82,68,87,65,82,69,61,48,120,55,44,73,79,61,48,120,54,44,78,69,84,87,79,82,75,61,48,120,50,44,80,79,87,69,82,61,48,120,97,44,83,89,83,84,69,77,61,48,120,51,44,85,83,69,82,61,48,120,57,10,99,46,70,66,75,58,67,79,80,89,95,70,73,76,69,61,48,120,50,44,68,69,76,69,84,69,95,70,73,76,69,61,48,120,51,44,77,79,86,69,95,70,73,76,69,61,48,120,49,10,99,46,70,68,58,65,76,76,79,67,61,48,120,50,48,44,65,82,82,65,89,61,48,120,49,48,48,48,44,65,82,82,65,89,83,73,90,69,61,48,120,56,48,44,66,85,70,70,69,82,61,48,120,50,48,48,44,66,85,70,83,73,90,69,61,48,120,56,48,44,66,89,84,69,61,48,120,49,48,48,48,48,48,48,44,67,80,80,61,48,120,52,48,48,48,44,67,85,83,84,79,77,61,48,120,56,48,48,48,44,68,79,85,66,76,69,61,48,120,56,48,48,48,48,48,48,48,44,68,79,85,66,76,69,82,69,83,85,76,84,61,48,120,56,48,48,48,48,49,48,48,44,69,82,82,79,82,61,48,120,56,48,48,44,70,76,65,71,83,61,48,120,52,48,44,70,76,79,65,84,61,48,120,49,48,48,48,48,48,48,48,44,70,85,78,67,84,73,79,78,61,48,120,50,48,48,48,48,48,48,44,70,85,78,67,84,73,79,78,80,84,82,61,48,120,97,48,48,48,48,48,48,44,73,61,48,120,52,48,48,44,73,78,73,84,61,48,120,52,48,48,44,73,78,84,69,71,82,65,76,61,48,120,50,44,76,65,82,71,69,61,48,120,52,48,48,48,48,48,48,44,76,65,82,71,69,82,69,83,85,76,84,61,48,120,52,48,48,48,49,48,48,44,76,79,78,71,61,48,120,52,48,48,48,48,48,48,48,44,76,79,78,71,82,69,83,85,76,84,61,48,120,52,48,48,48,48,49,48,48,44,76,79,79,75,85,80,61,48,120,56,48,44,79,66,74,69,67,84,61,48,120,49,44,79,66,74,69,67,84,73,68,61,48,120,52,48,48,48,48,48,48,49,44,79,66,74,69,67,84,80,84,82,61,48,120,56,48,48,48,48,48,49,44,80,79,73,78,84,69,82,61,48,120,56,48,48,48,48,48,48,44,80,82,73,86,65,84,69,61,48,120,49,48,48,48,48,44,80,84,82,61,48,120,56,48,48,48,48,48,48,44,80,84,82,66,85,70,70,69,82,61,48,120,56,48,48,48,50,48,48,44,80,84,82,82,69,83,85,76,84,61,48,120,56,48,48,48,49,48,48,44,80,84,82,83,73,90,69,61,48,120,56,48,44,80,84,82,95,68,79,85,66,76,69,82,69,83,85,76,84,61,48,120,56,56,48,48,48,49,48,48,44,80,84,82,95,76,65,82,71,69,82,69,83,85,76,84,61,48,120,99,48,48,48,49,48,48,44,80,84,82,95,76,79,78,71,82,69,83,85,76,84,61,48,120,52,56,48,48,48,49,48,48,44,82,61,48,120,49,48,48,44,82,69,65,68,61,48,120,49,48,48,44,82,69,81,85,73,82,69,68,61,48,120,52,44,82,69,83,79,85,82,67,69,61,48,120,50,48,48,48,44,82,69,83,85,76,84,61,48,120,49,48,48,44,82,71,66,61,48,120,56,48,48,48,48,44,82,73,61,48,120,53,48,48,44,82,87,61,48,120,51,48,48,44,83,67,65,76,69,68,61,48,120,50,48,48,48,48,48,44,83,84,82,61,48,120,56,48,48,48,48,48,44,83,84,82,73,78,71,61,48,120,56,48,48,48,48,48,44,83,84,82,82,69,83,85,76,84,61,48,120,56,48,48,49,48,48,44,83,84,82,85,67,84,61,48,120,49,48,44,83,89,78,79,78,89,77,61,48,120,50,48,48,48,48,44,83,89,83,84,69,77,61,48,120,49,48,48,48,48,44,84,65,71,83,61,48,120,52,48,48,44,85,78,83,73,71,78,69,68,61,48,120,52,48,48,48,48,44,86,65,82,73,65,66,76,69,61,48,120,50,48,48,48,48,48,48,48,44,86,65,82,84,65,71,83,61,48,120,52,48,44,86,73,82,84,85,65,76,61,48,120,56,44,86,79,73,68,61,48,120,48,44,86,79,76,65,84,73,76,69,61,48,120,48,44,87,61,48,120,50,48,48,44,87,79,82,68,61,48,120,52,48,48,48,48,48,44,87,82,73,84,69,61,48,120,50,48,48,10,99,46,70,68,66,58,67,79,77,80,82,69,83,83,95,70,73,76,69,61,48,120,50,44,68,69,67,79,77,80,82,69,83,83,95,70,73,76,69,61,48,120,49,44,68,69,67,79,77,80,82,69,83,83,95,79,66,74,69,67,84,61,48,120,52,44,82,69,77,79,86,69,95,70,73,76,69,61,48,120,51,10,99,46,70,68,76,58,70,69,69,68,66,65,67,75,61,48,120,49,10,99,46,70,68,84,58,65,67,67,69,83,83,69,68,61,48,120,50,44,65,82,67,72,73,86,69,68,61,48,120,51,44,67,82,69,65,84,69,68,61,48,120,49,44,77,79,68,73,70,73,69,68,61,48,120,48,10,99,46,70,70,82,58,65,66,79,82,84,61,48,120,50,44,67,79,78,84,73,78,85,69,61,48,120,48,44,79,75,65,89,61,48,120,48,44,83,75,73,80,61,48,120,49,10,99,46,70,76,58,65,80,80,82,79,88,73,77,65,84,69,61,48,120,49,48,44,66,85,70,70,69,82,61,48,120,52,48,44,68,69,86,73,67,69,61,48,120,52,48,48,44,68,73,82,69,67,84,79,82,89,61,48,120,56,44,69,88,67,76,85,68,69,95,70,73,76,69,83,61,48,120,49,48,48,48,44,69,88,67,76,85,68,69,95,70,79,76,68,69,82,83,61,48,120,50,48,48,48,44,70,73,76,69,61,48,120,49,48,48,44,70,79,76,68,69,82,61,48,120,56,44,76,73,78,75,61,48,120,50,48,44,76,79,79,80,61,48,120,56,48,44,78,69,87,61,48,120,50,44,82,69,65,68,61,48,120,52,44,82,69,83,69,84,95,68,65,84,69,61,48,120,50,48,48,44,83,84,82,69,65,77,61,48,120,56,48,48,44,87,82,73,84,69,61,48,120,49,10,99,46,70,79,70,58,83,77,65,82,84,95,78,65,77,69,83,61,48,120,49,10,99,46,73,68,84,89,80,69,58,70,85,78,67,84,73,79,78,61,48,120,51,44,71,76,79,66,65,76,61,48,120,50,44,77,69,83,83,65,71,69,61,48,120,49,10,99,46,74,69,84,58,65,66,83,95,88,89,61,48,120,49,98,44,65,78,65,76,79,71,50,95,88,89,61,48,120,49,54,44,65,78,65,76,79,71,50,95,90,61,48,120,49,55,44,65,78,65,76,79,71,95,88,89,61,48,120,49,52,44,65,78,65,76,79,71,95,90,61,48,120,49,53,44,66,85,84,84,79,78,95,49,61,48,120,50,44,66,85,84,84,79,78,95,49,48,61,48,120,98,44,66,85,84,84,79,78,95,50,61,48,120,51,44,66,85,84,84,79,78,95,51,61,48,120,52,44,66,85,84,84,79,78,95,52,61,48,120,53,44,66,85,84,84,79,78,95,53,61,48,120,54,44,66,85,84,84,79,78,95,54,61,48,120,55,44,66,85,84,84,79,78,95,55,61,48,120,56,44,66,85,84,84,79,78,95,56,61,48,120,57,44,66,85,84,84,79,78,95,57,61,48,120,97,44,66,85,84,84,79,78,95,83,69,76,69,67,84,61,48,120,102,44,66,85,84,84,79,78,95,83,84,65,82,84,61,48,120,101,44,67,82,79,83,83,69,68,95,73,78,61,48,120,49,99,44,67,82,79,83,83,69,68,95,79,85,84,61,48,120,49,100,44,68,69,86,73,67,69,95,84,73,76,84,95,88,89,61,48,120,49,102,44,68,69,86,73,67,69,95,84,73,76,84,95,90,61,48,120,50,48,44,68,73,71,73,84,65,76,95,88,89,61,48,120,49,44,68,73,83,80,76,65,89,95,69,68,71,69,61,48,120,50,49,44,69,78,68,61,48,120,50,50,44,76,69,70,84,95,66,85,77,80,69,82,95,49,61,48,120,49,48,44,76,69,70,84,95,66,85,77,80,69,82,95,50,61,48,120,49,49,44,76,77,66,61,48,120,50,44,77,77,66,61,48,120,52,44,80,69,78,95,84,73,76,84,95,88,89,61,48,120,49,97,44,80,82,69,83,83,85,82,69,61,48,120,49,101,44,82,73,71,72,84,95,66,85,77,80,69,82,95,49,61,48,120,49,50,44,82,73,71,72,84,95,66,85,77,80,69,82,95,50,61,48,120,49,51,44,82,77,66,61,48,120,51,44,84,82,73,71,71,69,82,95,76,69,70,84,61,48,120,99,44,84,82,73,71,71,69,82,95,82,73,71,72,84,61,48,120,100,44,87,72,69,69,76,61,48,120,49,56,44,87,72,69,69,76,95,84,73,76,84,61,48,120,49,57,10,99,46,74,84,89,80,69,58,65,78,65,76,79,71,61,48,120,50,48,44,65,78,67,72,79,82,69,68,61,48,120,50,44,66,85,84,84,79,78,61,48,120,56,48,44,67,82,79,83,83,73,78,71,61,48,120,56,44,68,66,76,95,67,76,73,67,75,61,48,120,50,48,48,44,68,73,71,73,84,65,76,61,48,120,49,48,44,68,82,65,71,71,69,68,61,48,120,52,44,68,82,65,71,95,73,84,69,77,61,48,120,56,48,48,44,69,88,84,95,77,79,86,69,77,69,78,84,61,48,120,52,48,44,77,79,86,69,77,69,78,84,61,48,120,49,48,48,44,82,69,80,69,65,84,69,68,61,48,120,52,48,48,44,83,69,67,79,78,68,65,82,89,61,48,120,49,10,99,46,75,69,89,58,65,61,48,120,49,44,65,80,79,83,84,82,79,80,72,69,61,48,120,50,98,44,65,84,61,48,120,56,97,44,66,61,48,120,50,44,66,65,67,75,61,48,120,56,54,44,66,65,67,75,83,80,65,67,69,61,48,120,54,57,44,66,65,67,75,95,83,76,65,83,72,61,48,120,50,102,44,66,82,69,65,75,61,48,120,55,98,44,67,61,48,120,51,44,67,65,76,76,61,48,120,56,55,44,67,65,77,69,82,65,61,48,120,56,57,44,67,65,78,67,69,76,61,48,120,55,97,44,67,65,80,83,95,76,79,67,75,61,48,120,52,54,44,67,76,69,65,82,61,48,120,54,101,44,67,79,77,77,65,61,48,120,50,99,44,68,61,48,120,52,44,68,69,76,69,84,69,61,48,120,54,100,44,68,79,84,61,48,120,50,100,44,68,79,87,78,61,48,120,54,49,44,69,61,48,120,53,44,69,73,71,72,84,61,48,120,50,50,44,69,78,68,61,48,120,55,50,44,69,78,68,95,67,65,76,76,61,48,120,56,56,44,69,78,84,69,82,61,48,120,54,98,44,69,81,85,65,76,83,61,48,120,50,55,44,69,83,67,65,80,69,61,48,120,54,99,44,69,88,69,67,85,84,69,61,48,120,55,52,44,70,61,48,120,54,44,70,49,61,48,120,52,99,44,70,49,48,61,48,120,53,53,44,70,49,49,61,48,120,53,54,44,70,49,50,61,48,120,53,55,44,70,49,51,61,48,120,53,56,44,70,49,52,61,48,120,53,57,44,70,49,53,61,48,120,53,97,44,70,49,54,61,48,120,53,98,44,70,49,55,61,48,120,53,99,44,70,49,56,61,48,120,56,48,44,70,49,57,61,48,120,56,49,44,70,50,61,48,120,52,100,44,70,50,48,61,48,120,56,50,44,70,51,61,48,120,52,101,44,70,52,61,48,120,52,102,44,70,53,61,48,120,53,48,44,70,54,61,48,120,53,49,44,70,55,61,48,120,53,50,44,70,56,61,48,120,53,51,44,70,57,61,48,120,53,52,44,70,73,78,68,61,48,120,55,57,44,70,73,86,69,61,48,120,49,102,44,70,79,82,87,65,82,68,61,48,120,57,48,44,70,79,85,82,61,48,120,49,101,44,71,61,48,120,55,44,72,61,48,120,56,44,72,69,76,80,61,48,120,52,51,44,72,79,77,69,61,48,120,54,102,44,73,61,48,120,57,44,73,78,83,69,82,84,61,48,120,55,53,44,74,61,48,120,97,44,75,61,48,120,98,44,76,61,48,120,99,44,76,69,70,84,61,48,120,54,51,44,76,69,78,83,95,70,79,67,85,83,61,48,120,56,99,44,76,69,83,83,95,71,82,69,65,84,69,82,61,48,120,53,102,44,76,73,83,84,95,69,78,68,61,48,120,57,54,44,76,95,65,76,84,61,48,120,52,56,44,76,95,67,79,77,77,65,78,68,61,48,120,52,97,44,76,95,67,79,78,84,82,79,76,61,48,120,52,49,44,76,95,83,72,73,70,84,61,48,120,52,52,44,76,95,83,81,85,65,82,69,61,48,120,50,56,44,77,61,48,120,100,44,77,65,67,82,79,61,48,120,53,100,44,77,69,78,85,61,48,120,55,56,44,77,73,78,85,83,61,48,120,50,54,44,77,85,84,69,61,48,120,57,50,44,78,61,48,120,101,44,78,69,88,84,61,48,120,56,101,44,78,73,78,69,61,48,120,50,51,44,78,80,95,48,61,48,120,51,49,44,78,80,95,49,61,48,120,51,50,44,78,80,95,50,61,48,120,51,51,44,78,80,95,51,61,48,120,51,52,44,78,80,95,52,61,48,120,51,53,44,78,80,95,53,61,48,120,51,54,44,78,80,95,54,61,48,120,51,55,44,78,80,95,55,61,48,120,51,56,44,78,80,95,56,61,48,120,51,57,44,78,80,95,57,61,48,120,51,97,44,78,80,95,66,65,82,61,48,120,51,100,44,78,80,95,68,69,67,73,77,65,76,61,48,120,51,102,44,78,80,95,68,73,86,73,68,69,61,48,120,52,48,44,78,80,95,68,79,84,61,48,120,51,102,44,78,80,95,69,78,84,69,82,61,48,120,55,101,44,78,80,95,77,73,78,85,83,61,48,120,51,101,44,78,80,95,77,85,76,84,73,80,76,89,61,48,120,51,98,44,78,80,95,80,76,85,83,61,48,120,51,99,44,78,80,95,80,76,85,83,95,77,73,78,85,83,61,48,120,53,101,44,78,80,95,83,69,80,65,82,65,84,79,82,61,48,120,51,100,44,78,85,77,95,76,79,67,75,61,48,120,55,99,44,79,61,48,120,102,44,79,78,69,61,48,120,49,98,44,80,61,48,120,49,48,44,80,65,71,69,95,68,79,87,78,61,48,120,55,49,44,80,65,71,69,95,85,80,61,48,120,55,48,44,80,65,85,83,69,61,48,120,54,53,44,80,69,82,73,79,68,61,48,120,50,100,44,80,76,65,89,61,48,120,57,53,44,80,76,85,83,61,48,120,56,98,44,80,79,85,78,68,61,48,120,57,52,44,80,79,87,69,82,61,48,120,54,56,44,80,82,69,86,73,79,85,83,61,48,120,56,102,44,80,82,73,78,84,61,48,120,52,55,44,80,82,84,95,83,67,82,61,48,120,55,100,44,81,61,48,120,49,49,44,82,61,48,120,49,50,44,82,69,68,79,61,48,120,55,55,44,82,69,86,69,82,83,69,95,81,85,79,84,69,61,48,120,50,53,44,82,69,87,73,78,68,61,48,120,57,49,44,82,73,71,72,84,61,48,120,54,50,44,82,95,65,76,84,61,48,120,52,57,44,82,95,67,79,77,77,65,78,68,61,48,120,52,98,44,82,95,67,79,78,84,82,79,76,61,48,120,52,50,44,82,95,83,72,73,70,84,61,48,120,52,53,44,82,95,83,81,85,65,82,69,61,48,120,50,57,44,83,61,48,120,49,51,44,83,67,82,95,76,79,67,75,61,48,120,54,52,44,83,69,76,69,67,84,61,48,120,55,51,44,83,69,77,73,95,67,79,76,79,78,61,48,120,50,97,44,83,69,86,69,78,61,48,120,50,49,44,83,73,88,61,48,120,50,48,44,83,76,65,83,72,61,48,120,50,101,44,83,76,69,69,80,61,48,120,54,55,44,83,80,65,67,69,61,48,120,51,48,44,83,84,65,82,61,48,120,57,51,44,83,84,79,80,61,48,120,56,100,44,83,89,83,82,81,61,48,120,55,102,44,84,61,48,120,49,52,44,84,65,66,61,48,120,54,97,44,84,72,82,69,69,61,48,120,49,100,44,84,87,79,61,48,120,49,99,44,85,61,48,120,49,53,44,85,78,68,79,61,48,120,55,54,44,85,80,61,48,120,54,48,44,86,61,48,120,49,54,44,86,79,76,85,77,69,95,68,79,87,78,61,48,120,56,53,44,86,79,76,85,77,69,95,85,80,61,48,120,56,52,44,87,61,48,120,49,55,44,87,65,75,69,61,48,120,54,54,44,87,73,78,95,67,79,78,84,82,79,76,61,48,120,56,51,44,88,61,48,120,49,56,44,89,61,48,120,49,57,44,90,61,48,120,49,97,44,90,69,82,79,61,48,120,50,52,10,99,46,75,81,58,65,76,84,61,48,120,54,48,44,65,76,84,71,82,61,48,120,52,48,44,67,65,80,83,95,76,79,67,75,61,48,120,52,44,67,79,77,77,65,78,68,61,48,120,49,56,48,44,67,79,78,84,82,79,76,61,48,120,49,56,44,67,84,82,76,61,48,120,49,56,44,68,69,65,68,95,75,69,89,61,48,120,49,48,48,48,48,44,73,78,70,79,61,48,120,51,99,48,52,44,73,78,83,84,82,85,67,84,73,79,78,95,75,69,89,83,61,48,120,55,56,44,76,95,65,76,84,61,48,120,50,48,44,76,95,67,79,77,77,65,78,68,61,48,120,56,48,44,76,95,67,79,78,84,82,79,76,61,48,120,56,44,76,95,67,84,82,76,61,48,120,56,44,76,95,83,72,73,70,84,61,48,120,49,44,78,79,84,95,80,82,73,78,84,65,66,76,69,61,48,120,50,48,48,48,44,78,85,77,95,76,79,67,75,61,48,120,56,48,48,48,44,78,85,77,95,80,65,68,61,48,120,50,48,48,44,80,82,69,83,83,69,68,61,48,120,49,48,48,48,44,81,85,65,76,73,70,73,69,82,83,61,48,120,49,102,98,44,82,69,76,69,65,83,69,68,61,48,120,56,48,48,44,82,69,80,69,65,84,61,48,120,52,48,48,44,82,95,65,76,84,61,48,120,52,48,44,82,95,67,79,77,77,65,78,68,61,48,120,49,48,48,44,82,95,67,79,78,84,82,79,76,61,48,120,49,48,44,82,95,67,84,82,76,61,48,120,49,48,44,82,95,83,72,73,70,84,61,48,120,50,44,83,67,82,95,76,79,67,75,61,48,120,52,48,48,48,44,83,72,73,70,84,61,48,120,51,44,87,73,78,95,67,79,78,84,82,79,76,61,48,120,50,48,48,48,48,10,99,46,76,65,89,79,85,84,58,66,65,67,75,71,82,79,85,78,68,61,48,120,56,44,69,77,66,69,68,68,69,68,61,48,120,50,48,44,70,79,82,69,71,82,79,85,78,68,61,48,120,49,48,44,73,71,78,79,82,69,95,67,85,82,83,79,82,61,48,120,56,48,44,76,69,70,84,61,48,120,50,44,76,79,67,75,61,48,120,52,48,44,82,73,71,72,84,61,48,120,52,44,83,81,85,65,82,69,61,48,120,48,44,84,73,71,72,84,61,48,120,49,44,84,73,76,69,61,48,120,49,48,48,44,87,73,68,69,61,48,120,54,10,99,46,76,68,70,58,67,72,69,67,75,95,69,88,73,83,84,83,61,48,120,49,10,99,46,76,79,67,58,68,73,82,69,67,84,79,82,89,61,48,120,49,44,70,73,76,69,61,48,120,51,44,70,79,76,68,69,82,61,48,120,49,44,86,79,76,85,77,69,61,48,120,50,10,99,46,77,65,88,58,78,65,77,69,95,76,69,78,61,48,120,50,48,10,99,46,77,69,77,58,65,85,68,73,79,61,48,120,56,44,67,65,76,76,69,82,61,48,120,56,48,48,48,48,48,44,67,79,68,69,61,48,120,49,48,44,68,65,84,65,61,48,120,48,44,68,69,76,69,84,69,61,48,120,49,48,48,48,44,69,88,67,76,85,83,73,86,69,61,48,120,56,48,48,44,72,73,68,68,69,78,61,48,120,49,48,48,48,48,48,44,77,65,78,65,71,69,68,61,48,120,49,44,78,79,95,66,76,79,67,75,61,48,120,50,48,48,48,44,78,79,95,66,76,79,67,75,73,78,71,61,48,120,50,48,48,48,44,78,79,95,67,76,69,65,82,61,48,120,52,48,48,48,48,44,78,79,95,76,79,67,75,61,48,120,52,48,48,44,78,79,95,80,79,79,76,61,48,120,50,48,44,79,66,74,69,67,84,61,48,120,50,48,48,44,82,69,65,68,61,48,120,49,48,48,48,48,44,82,69,65,68,95,87,82,73,84,69,61,48,120,51,48,48,48,48,44,83,84,82,73,78,71,61,48,120,49,48,48,44,84,69,88,84,85,82,69,61,48,120,52,44,84,77,80,95,76,79,67,75,61,48,120,52,48,44,85,78,84,82,65,67,75,69,68,61,48,120,56,48,44,86,73,68,69,79,61,48,120,50,44,87,82,73,84,69,61,48,120,50,48,48,48,48,10,99,46,77,70,70,58,65,84,84,82,73,66,61,48,120,50,48,44,67,76,79,83,69,68,61,48,120,56,48,44,67,82,69,65,84,69,61,48,120,52,44,68,69,69,80,61,48,120,49,48,48,48,44,68,69,76,69,84,69,61,48,120,56,44,70,73,76,69,61,48,120,52,48,48,44,70,79,76,68,69,82,61,48,120,50,48,48,44,77,79,68,73,70,89,61,48,120,50,44,77,79,86,69,68,61,48,120,49,48,44,79,80,69,78,69,68,61,48,120,52,48,44,82,69,65,68,61,48,120,49,44,82,69,78,65,77,69,61,48,120,49,48,44,83,69,76,70,61,48,120,56,48,48,44,85,78,77,79,85,78,84,61,48,120,49,48,48,44,87,82,73,84,69,61,48,120,50,10,99,46,77,72,70,58,68,69,70,65,85,76,84,61,48,120,50,44,83,84,65,84,73,67,61,48,120,49,44,83,84,82,85,67,84,85,82,69,61,48,120,50,10,99,46,77,79,70,58,76,73,78,75,95,76,73,66,82,65,82,89,61,48,120,49,44,83,84,65,84,73,67,61,48,120,50,44,83,89,83,84,69,77,95,80,82,79,66,69,61,48,120,52,10,99,46,77,79,86,69,58,65,76,76,61,48,120,102,44,68,79,87,78,61,48,120,49,44,76,69,70,84,61,48,120,52,44,82,73,71,72,84,61,48,120,56,44,85,80,61,48,120,50,10,99,46,77,83,70,58,65,68,68,61,48,120,56,44,65,68,68,82,69,83,83,61,48,120,49,48,44,77,69,83,83,65,71,69,95,73,68,61,48,120,50,48,44,78,79,95,68,85,80,76,73,67,65,84,69,61,48,120,52,44,85,80,68,65,84,69,61,48,120,50,44,87,65,73,84,61,48,120,49,10,99,46,77,83,71,73,68,58,65,67,84,73,79,78,61,48,120,54,51,44,66,82,69,65,75,61,48,120,54,52,44,67,79,77,77,65,78,68,61,48,120,54,53,44,67,79,82,69,95,69,78,68,61,48,120,54,52,44,68,69,66,85,71,61,48,120,53,102,44,69,86,69,78,84,61,48,120,53,101,44,70,82,69,69,61,48,120,54,50,44,81,85,73,84,61,48,120,51,101,56,44,84,72,82,69,65,68,95,65,67,84,73,79,78,61,48,120,53,98,44,84,72,82,69,65,68,95,67,65,76,76,66,65,67,75,61,48,120,53,99,44,86,65,76,73,68,65,84,69,95,80,82,79,67,69,83,83,61,48,120,53,100,44,87,65,73,84,95,70,79,82,95,79,66,74,69,67,84,83,61,48,120,53,97,10,99,46,77,84,70,58,65,78,73,77,61,48,120,56,44,82,69,76,65,84,73,86,69,61,48,120,49,48,44,88,61,48,120,49,44,89,61,48,120,50,44,90,61,48,120,52,10,99,46,78,69,84,77,83,71,58,69,78,68,61,48,120,49,44,83,84,65,82,84,61,48,120,48,10,99,46,78,70,58,67,79,76,76,69,67,84,61,48,120,56,48,44,70,82,69,69,61,48,120,49,48,44,70,82,69,69,95,79,78,95,85,78,76,79,67,75,61,48,120,56,44,73,78,73,84,73,65,76,73,83,69,68,61,48,120,50,44,73,78,84,69,71,82,65,76,61,48,120,52,44,77,69,83,83,65,71,69,61,48,120,50,48,48,44,78,65,77,69,61,48,120,56,48,48,48,48,48,48,48,44,80,82,73,86,65,84,69,61,48,120,48,44,82,69,67,76,65,83,83,69,68,61,48,120,49,48,48,44,83,73,71,78,65,76,76,69,68,61,48,120,52,48,48,44,83,85,80,80,82,69,83,83,95,76,79,71,61,48,120,52,48,44,84,73,77,69,82,95,83,85,66,61,48,120,50,48,44,85,78,73,81,85,69,61,48,120,52,48,48,48,48,48,48,48,44,85,78,84,82,65,67,75,69,68,61,48,120,49,10,99,46,79,80,70,58,65,82,71,83,61,48,120,52,48,44,68,69,84,65,73,76,61,48,120,52,44,69,82,82,79,82,61,48,120,56,48,44,77,65,88,95,68,69,80,84,72,61,48,120,50,44,77,79,68,85,76,69,95,80,65,84,72,61,48,120,52,48,48,44,79,80,84,73,79,78,83,61,48,120,49,44,80,82,73,86,73,76,69,71,69,68,61,48,120,49,48,48,44,82,79,79,84,95,80,65,84,72,61,48,120,56,48,48,44,83,67,65,78,95,77,79,68,85,76,69,83,61,48,120,49,48,48,48,44,83,72,79,87,95,69,82,82,79,82,83,61,48,120,50,48,44,83,72,79,87,95,73,79,61,48,120,49,48,44,83,72,79,87,95,77,69,77,79,82,89,61,48,120,56,44,83,89,83,84,69,77,95,80,65,84,72,61,48,120,50,48,48,10,99,46,80,69,82,77,73,84,58,65,76,76,95,68,69,76,69,84,69,61,48,120,56,56,56,44,65,76,76,95,69,88,69,67,61,48,120,52,52,52,44,65,76,76,95,82,69,65,68,61,48,120,49,49,49,44,65,76,76,95,87,82,73,84,69,61,48,120,50,50,50,44,65,82,67,72,73,86,69,61,48,120,50,48,48,48,44,68,69,76,69,84,69,61,48,120,56,44,69,86,69,82,89,79,78,69,95,65,67,67,69,83,83,61,48,120,102,102,102,44,69,86,69,82,89,79,78,69,95,68,69,76,69,84,69,61,48,120,56,56,56,44,69,86,69,82,89,79,78,69,95,69,88,69,67,61,48,120,52,52,52,44,69,86,69,82,89,79,78,69,95,82,69,65,68,61,48,120,49,49,49,44,69,86,69,82,89,79,78,69,95,82,69,65,68,87,82,73,84,69,61,48,120,51,51,51,44,69,86,69,82,89,79,78,69,95,87,82,73,84,69,61,48,120,50,50,50,44,69,88,69,67,61,48,120,52,44,71,82,79,85,80,61,48,120,102,48,44,71,82,79,85,80,73,68,61,48,120,49,48,48,48,48,44,71,82,79,85,80,95,68,69,76,69,84,69,61,48,120,56,48,44,71,82,79,85,80,95,69,88,69,67,61,48,120,52,48,44,71,82,79,85,80,95,82,69,65,68,61,48,120,49,48,44,71,82,79,85,80,95,87,82,73,84,69,61,48,120,50,48,44,72,73,68,68,69,78,61,48,120,49,48,48,48,44,73,78,72,69,82,73,84,61,48,120,50,48,48,48,48,44,78,69,84,87,79,82,75,61,48,120,56,48,48,48,48,44,79,70,70,76,73,78,69,61,48,120,52,48,48,48,48,44,79,84,72,69,82,83,61,48,120,102,48,48,44,79,84,72,69,82,83,95,68,69,76,69,84,69,61,48,120,56,48,48,44,79,84,72,69,82,83,95,69,88,69,67,61,48,120,52,48,48,44,79,84,72,69,82,83,95,82,69,65,68,61,48,120,49,48,48,44,79,84,72,69,82,83,95,87,82,73,84,69,61,48,120,50,48,48,44,80,65,83,83,87,79,82,68,61,48,120,52,48,48,48,44,82,69,65,68,61,48,120,49,44,85,83,69,82,61,48,120,102,44,85,83,69,82,73,68,61,48,120,56,48,48,48,44,85,83,69,82,95,69,88,69,67,61,48,120,52,44,85,83,69,82,95,82,69,65,68,61,48,120,49,44,85,83,69,82,95,87,82,73,84,69,61,48,120,50,44,87,82,73,84,69,61,48,120,50,10,99,46,80,77,70,58,83,89,83,84,69,77,95,78,79,95,66,82,69,65,75,61,48,120,49,10,99,46,80,84,67,58,67,82,79,83,83,72,65,73,82,61,48,120,97,44,67,85,83,84,79,77,61,48,120,49,55,44,68,69,70,65,85,76,84,61,48,120,49,44,68,82,65,71,71,65,66,76,69,61,48,120,49,56,44,69,78,68,61,48,120,49,57,44,72,65,78,68,61,48,120,49,48,44,72,65,78,68,95,76,69,70,84,61,48,120,49,49,44,72,65,78,68,95,82,73,71,72,84,61,48,120,49,50,44,73,78,86,73,83,73,66,76,69,61,48,120,49,54,44,77,65,71,78,73,70,73,69,82,61,48,120,102,44,78,79,95,67,72,65,78,71,69,61,48,120,48,44,80,65,73,78,84,66,82,85,83,72,61,48,120,49,52,44,83,73,90,69,95,66,79,84,84,79,77,61,48,120,57,44,83,73,90,69,95,66,79,84,84,79,77,95,76,69,70,84,61,48,120,50,44,83,73,90,69,95,66,79,84,84,79,77,95,82,73,71,72,84,61,48,120,51,44,83,73,90,69,95,76,69,70,84,61,48,120,54,44,83,73,90,69,95,82,73,71,72,84,61,48,120,55,44,83,73,90,69,95,84,79,80,61,48,120,56,44,83,73,90,69,95,84,79,80,95,76,69,70,84,61,48,120,52,44,83,73,90,69,95,84,79,80,95,82,73,71,72,84,61,48,120,53,44,83,73,90,73,78,71,61,48,120,99,44,83,76,69,69,80,61,48,120,98,44,83,80,76,73,84,95,72,79,82,73,90,79,78,84,65,76,61,48,120,101,44,83,80,76,73,84,95,86,69,82,84,73,67,65,76,61,48,120,100,44,83,84,79,80,61,48,120,49,53,44,84,69,88,84,61,48,120,49,51,10,99,46,82,68,70,58,65,82,67,72,73,86,69,61,48,120,50,48,48,48,44,68,65,84,69,61,48,120,50,44,70,73,76,69,61,48,120,56,44,70,73,76,69,83,61,48,120,56,44,70,79,76,68,69,82,61,48,120,49,48,44,70,79,76,68,69,82,83,61,48,120,49,48,44,72,73,68,68,69,78,61,48,120,49,48,48,44,76,73,78,75,61,48,120,52,48,44,79,80,69,78,68,73,82,61,48,120,52,48,48,48,44,80,69,82,77,73,83,83,73,79,78,83,61,48,120,52,44,81,85,65,76,73,70,73,69,68,61,48,120,50,48,48,44,81,85,65,76,73,70,89,61,48,120,50,48,48,44,82,69,65,68,95,65,76,76,61,48,120,49,102,44,82,69,65,68,95,79,78,76,89,61,48,120,49,48,48,48,44,83,73,90,69,61,48,120,49,44,83,84,82,69,65,77,61,48,120,56,48,48,44,84,65,71,83,61,48,120,56,48,44,84,73,77,69,61,48,120,50,44,86,73,82,84,85,65,76,61,48,120,52,48,48,44,86,79,76,85,77,69,61,48,120,50,48,10,99,46,82,69,83,58,67,79,78,83,79,76,69,95,70,68,61,48,120,50,44,67,79,82,69,95,73,68,76,61,48,120,56,44,67,80,85,95,83,80,69,69,68,61,48,120,49,54,44,68,73,83,80,76,65,89,95,68,82,73,86,69,82,61,48,120,53,44,69,88,67,69,80,84,73,79,78,95,72,65,78,68,76,69,82,61,48,120,49,49,44,70,82,69,69,95,77,69,77,79,82,89,61,48,120,49,55,44,70,82,69,69,95,83,87,65,80,61,48,120,49,44,74,78,73,95,69,78,86,61,48,120,101,44,75,69,89,95,83,84,65,84,69,61,48,120,51,44,76,79,71,95,68,69,80,84,72,61,48,120,100,44,76,79,71,95,76,69,86,69,76,61,48,120,97,44,77,65,88,95,80,82,79,67,69,83,83,69,83,61,48,120,99,44,78,69,84,95,80,82,79,67,69,83,83,73,78,71,61,48,120,49,50,44,79,80,69,78,95,73,78,70,79,61,48,120,49,48,44,80,65,82,69,78,84,95,67,79,78,84,69,88,84,61,48,120,57,44,80,82,73,86,73,76,69,71,69,68,61,48,120,55,44,80,82,73,86,73,76,69,71,69,68,95,85,83,69,82,61,48,120,54,44,80,82,79,67,69,83,83,95,83,84,65,84,69,61,48,120,49,51,44,83,84,65,84,73,67,95,66,85,73,76,68,61,48,120,49,56,44,84,72,82,69,65,68,95,73,68,61,48,120,102,44,84,79,84,65,76,95,77,69,77,79,82,89,61,48,120,49,52,44,84,79,84,65,76,95,83,72,65,82,69,68,95,77,69,77,79,82,89,61,48,120,98,44,84,79,84,65,76,95,83,87,65,80,61,48,120,49,53,44,85,83,69,82,95,73,68,61,48,120,52,10,99,46,82,70,68,58,65,76,76,79,87,95,82,69,67,85,82,83,73,79,78,61,48,120,50,48,44,65,76,87,65,89,83,95,67,65,76,76,61,48,120,49,48,48,44,69,88,67,69,80,84,61,48,120,50,44,82,69,65,68,61,48,120,52,44,82,69,67,65,76,76,61,48,120,56,48,44,82,69,77,79,86,69,61,48,120,56,44,83,79,67,75,69,84,61,48,120,52,48,44,83,84,79,80,95,82,69,67,85,82,83,69,61,48,120,49,48,44,87,82,73,84,69,61,48,120,49,10,99,46,82,80,58,77,79,68,85,76,69,95,80,65,84,72,61,48,120,49,44,82,79,79,84,95,80,65,84,72,61,48,120,51,44,83,89,83,84,69,77,95,80,65,84,72,61,48,120,50,10,99,46,82,83,70,58,65,80,80,82,79,88,73,77,65,84,69,61,48,120,52,44,67,65,83,69,95,83,69,78,83,73,84,73,86,69,61,48,120,50,48,44,67,72,69,67,75,95,86,73,82,84,85,65,76,61,48,120,50,44,78,79,95,68,69,69,80,95,83,67,65,78,61,48,120,56,44,78,79,95,70,73,76,69,95,67,72,69,67,75,61,48,120,49,44,80,65,84,72,61,48,120,49,48,10,99,46,83,67,70,58,69,88,73,84,95,79,78,95,69,82,82,79,82,61,48,120,49,44,76,79,71,95,65,76,76,61,48,120,50,10,99,46,83,69,69,75,58,67,85,82,82,69,78,84,61,48,120,49,44,69,78,68,61,48,120,50,44,82,69,76,65,84,73,86,69,61,48,120,51,44,83,84,65,82,84,61,48,120,48,10,99,46,83,84,80,58,65,78,73,77,61,48,120,56,44,88,61,48,120,49,44,89,61,48,120,50,44,90,61,48,120,52,10,99,46,83,84,82,58,67,65,83,69,61,48,120,49,44,77,65,84,67,72,95,67,65,83,69,61,48,120,49,44,77,65,84,67,72,95,76,69,78,61,48,120,50,44,87,73,76,68,67,65,82,68,61,48,120,52,10,99,46,83,84,84,58,70,76,79,65,84,61,48,120,50,44,72,69,88,61,48,120,51,44,78,85,77,66,69,82,61,48,120,49,44,83,84,82,73,78,71,61,48,120,52,10,99,46,84,72,70,58,65,85,84,79,95,70,82,69,69,61,48,120,49,10,99,46,84,79,73,58,65,78,68,82,79,73,68,95,65,83,83,69,84,77,71,82,61,48,120,52,44,65,78,68,82,79,73,68,95,67,76,65,83,83,61,48,120,51,44,65,78,68,82,79,73,68,95,69,78,86,61,48,120,50,44,76,79,67,65,76,95,67,65,67,72,69,61,48,120,48,44,76,79,67,65,76,95,83,84,79,82,65,71,69,61,48,120,49,10,99,46,84,83,70,58,65,84,84,65,67,72,69,68,61,48,120,49,48,48,44,68,69,84,65,67,72,69,68,61,48,120,56,48,44,70,79,82,69,73,71,78,61,48,120,49,44,76,79,71,95,65,76,76,61,48,120,50,48,44,80,73,80,69,61,48,120,50,48,48,44,80,82,73,86,73,76,69,71,69,68,61,48,120,56,44,81,85,73,69,84,61,48,120,52,48,44,82,69,83,69,84,95,80,65,84,72,61,48,120,52,44,83,72,69,76,76,61,48,120,49,48,44,87,65,73,84,61,48,120,50,10,99,46,84,83,84,65,84,69,58,80,65,85,83,69,68,61,48,120,49,44,82,85,78,78,73,78,71,61,48,120,48,44,83,84,79,80,80,73,78,71,61,48,120,50,44,84,69,82,77,73,78,65,84,69,68,61,48,120,51,10,99,46,86,65,83,58,67,65,83,69,95,83,69,78,83,73,84,73,86,69,61,48,120,102,44,67,76,79,83,69,95,68,73,82,61,48,120,54,44,67,82,69,65,84,69,95,76,73,78,75,61,48,120,49,49,44,68,69,76,69,84,69,61,48,120,51,44,68,69,82,69,71,73,83,84,69,82,61,48,120,49,44,68,82,73,86,69,82,95,83,73,90,69,61,48,120,49,50,44,71,69,84,95,68,69,86,73,67,69,95,73,78,70,79,61,48,120,98,44,71,69,84,95,73,78,70,79,61,48,120,97,44,73,68,69,78,84,73,70,89,95,70,73,76,69,61,48,120,99,44,73,71,78,79,82,69,95,70,73,76,69,61,48,120,57,44,77,65,75,69,95,68,73,82,61,48,120,100,44,79,80,69,78,95,68,73,82,61,48,120,53,44,82,69,65,68,95,76,73,78,75,61,48,120,49,48,44,82,69,78,65,77,69,61,48,120,52,44,83,65,77,69,95,70,73,76,69,61,48,120,101,44,83,67,65,78,95,68,73,82,61,48,120,50,44,84,69,83,84,95,80,65,84,72,61,48,120,55,44,87,65,84,67,72,95,80,65,84,72,61,48,120,56,10,99,46,86,76,70,58,65,80,73,61,48,120,50,48,44,66,82,65,78,67,72,61,48,120,49,44,67,82,73,84,73,67,65,76,61,48,120,56,44,68,69,84,65,73,76,61,48,120,52,48,44,69,82,82,79,82,61,48,120,50,44,70,85,78,67,84,73,79,78,61,48,120,49,48,48,44,73,78,70,79,61,48,120,49,48,44,84,82,65,67,69,61,48,120,56,48,44,87,65,82,78,73,78,71,61,48,120,52,10,99,46,86,79,76,85,77,69,58,72,73,68,68,69,78,61,48,120,52,44,80,82,73,79,82,73,84,89,61,48,120,50,44,82,69,80,76,65,67,69,61,48,120,49,44,83,89,83,84,69,77,61,48,120,56,10,0 };
    diff --git a/src/core/internal.cpp b/src/core/internal.cpp
    index 7a2e66cd1..68c7a6779 100644
    --- a/src/core/internal.cpp
    +++ b/src/core/internal.cpp
    @@ -48,11 +48,11 @@ struct sockaddr_un * get_socket_path(LONG ProcessID, socklen_t *Size)
     
     //********************************************************************************************************************
     
    -ERROR process_janitor(OBJECTID SubscriberID, LONG Elapsed, LONG TotalElapsed)
    +ERR process_janitor(OBJECTID SubscriberID, LONG Elapsed, LONG TotalElapsed)
     {
        if (glTasks.empty()) {
           glJanitorActive = false;
    -      return ERR_Terminate;
    +      return ERR::Terminate;
        }
     
     #ifdef __unix__
    @@ -93,7 +93,7 @@ ERROR process_janitor(OBJECTID SubscriberID, LONG Elapsed, LONG TotalElapsed)
        }
     #endif
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -125,19 +125,19 @@ public|untracked and private memory flags as necessary.  Example:
     
     *********************************************************************************************************************/
     
    -ERROR copy_args(const struct FunctionField *Args, LONG ArgsSize, BYTE *ArgsBuffer, BYTE *Buffer, LONG BufferSize,
    +ERR copy_args(const struct FunctionField *Args, LONG ArgsSize, BYTE *ArgsBuffer, BYTE *Buffer, LONG BufferSize,
                         LONG *NewSize, CSTRING ActionName)
     {
        pf::Log log("CopyArguments");
        BYTE *src, *data;
        LONG memsize, j, len;
    -   ERROR error;
    +   ERR error;
        STRING str;
     
    -   if ((!Args) or (!ArgsBuffer) or (!Buffer)) return log.warning(ERR_NullArgs);
    +   if ((!Args) or (!ArgsBuffer) or (!Buffer)) return log.warning(ERR::NullArgs);
     
        for (LONG i=0; (i < ArgsSize); i++) { // Copy the arguments to the buffer
    -      if (i >= BufferSize) return log.warning(ERR_BufferOverflow);
    +      if (i >= BufferSize) return log.warning(ERR::BufferOverflow);
           Buffer[i] = ArgsBuffer[i];
        }
     
    @@ -161,7 +161,7 @@ ERROR copy_args(const struct FunctionField *Args, LONG ArgsSize, BYTE *ArgsBuffe
                    Buffer[offset++] = 0;
                    ((STRING *)(Buffer + pos))[0] = str;
                 }
    -            else { error = ERR_BufferOverflow; goto looperror; }
    +            else { error = ERR::BufferOverflow; goto looperror; }
              }
              else ((STRING *)(Buffer + pos))[0] = NULL;
     
    @@ -174,7 +174,7 @@ ERROR copy_args(const struct FunctionField *Args, LONG ArgsSize, BYTE *ArgsBuffe
                    ((APTR *)(Buffer + pos))[0] = ArgsBuffer + offset;
                    offset += sizeof(LONG);
                 }
    -            else { error = ERR_BufferOverflow; goto looperror; }
    +            else { error = ERR::BufferOverflow; goto looperror; }
              }
              else if (Args[i].Type & (FD_DOUBLE|FD_LARGE)) { // Pointer to large/double
                 if ((size_t)offset < (BufferSize - sizeof(LARGE))) {
    @@ -182,7 +182,7 @@ ERROR copy_args(const struct FunctionField *Args, LONG ArgsSize, BYTE *ArgsBuffe
                    ((APTR *)(Buffer + pos))[0] = ArgsBuffer + offset;
                    offset += sizeof(LARGE);
                 }
    -            else { error = ERR_BufferOverflow; goto looperror; }
    +            else { error = ERR::BufferOverflow; goto looperror; }
              }
              else {
                 // There are two types of pointer references:
    @@ -206,27 +206,27 @@ ERROR copy_args(const struct FunctionField *Args, LONG ArgsSize, BYTE *ArgsBuffe
                    if (memsize > 0) {
                       if (Args[i].Type & FD_RESULT) { // "Receive" pointer type: Prepare a buffer so that we can accept a result
                          APTR mem;
    -                     if (!AllocMemory(memsize, MEM::NO_CLEAR, &mem, NULL)) {
    +                     if (AllocMemory(memsize, MEM::NO_CLEAR, &mem, NULL) IS ERR::Okay) {
                             ((APTR *)(Buffer + pos))[0] = mem;
                          }
    -                     else { error = ERR_AllocMemory; goto looperror; }
    +                     else { error = ERR::AllocMemory; goto looperror; }
                       }
                       else {
                          // "Send" pointer type: Prepare the argument structure for sending data to the other task
                          if ((src = ((BYTE **)(ArgsBuffer + pos))[0])) { // Get the data source pointer
                             if (memsize > MSG_MAXARGSIZE) {
                                // For large data areas, we need to allocate them as public memory blocks
    -                           if (!AllocMemory(memsize, MEM::NO_CLEAR, (void **)&data, NULL)) {
    +                           if (AllocMemory(memsize, MEM::NO_CLEAR, (void **)&data, NULL) IS ERR::Okay) {
                                   ((APTR *)(Buffer + pos))[0] = data;
                                   CopyMemory(src, data, memsize);
                                }
    -                           else { error = ERR_AllocMemory; goto looperror; }
    +                           else { error = ERR::AllocMemory; goto looperror; }
                             }
                             else {
                                ((APTR *)(Buffer + pos))[0] = ArgsBuffer + offset; // Record the address at which we are going to write the data
                                for (LONG len=0; len < memsize; len++) {
                                   if (offset >= BufferSize) {
    -                                 error = ERR_BufferOverflow;
    +                                 error = ERR::BufferOverflow;
                                      goto looperror;
                                   }
                                   else Buffer[offset++] = src[len];
    @@ -247,7 +247,7 @@ ERROR copy_args(const struct FunctionField *Args, LONG ArgsSize, BYTE *ArgsBuffe
        }
     
        *NewSize = offset;
    -   return ERR_Okay;
    +   return ERR::Okay;
     
     looperror:
        // When an error occurs inside the loop, we back-track through the position at where the error occurred and free any
    @@ -283,11 +283,11 @@ void local_free_args(APTR Parameters, const struct FunctionField *Args)
     ** Resolves pointers and strings within an ActionMessage structure.
     */
     
    -ERROR resolve_args(APTR Parameters, const struct FunctionField *Args)
    +ERR resolve_args(APTR Parameters, const struct FunctionField *Args)
     {
        pf::Log log(__FUNCTION__);
        LONG i;
    -   ERROR error;
    +   ERR error;
        BYTE *Buffer = (BYTE *)Parameters;
        LONG pos = 0;
        for (i=0; Args[i].Name; i++) {
    @@ -307,7 +307,7 @@ ERROR resolve_args(APTR Parameters, const struct FunctionField *Args)
                 MEMORYID mid = ((MEMORYID *)(Buffer + pos))[0];
                 if (mid) {
                    log.warning("Bad memory ID #%d for arg \"%s\", not a public allocation.", mid, Args[i].Name);
    -               error = ERR_AccessMemory;
    +               error = ERR::AccessMemory;
                    goto looperror;
                 }
              }
    @@ -322,7 +322,7 @@ ERROR resolve_args(APTR Parameters, const struct FunctionField *Args)
           else if (Args[i].Type & (FD_DOUBLE|FD_LARGE)) pos += sizeof(LARGE);
           else pos += sizeof(LONG);
        }
    -   return ERR_Okay;
    +   return ERR::Okay;
     
     looperror:
        // On failure we must back-track through the array looking for pointers that we have already gained access to, and release them before returning.
    diff --git a/src/core/lib_base64.cpp b/src/core/lib_base64.cpp
    index b37ab2df4..09cf9db96 100644
    --- a/src/core/lib_base64.cpp
    +++ b/src/core/lib_base64.cpp
    @@ -169,10 +169,10 @@ Args
     
     **********************************************************************************************************************/
     
    -ERROR Base64Decode(pfBase64Decode *State, CSTRING Input, LONG InputSize, APTR Output, LONG *Written)
    +ERR Base64Decode(pfBase64Decode *State, CSTRING Input, LONG InputSize, APTR Output, LONG *Written)
     {
    -   if ((!State) or (!Input) or (!Output) or (!Written)) return ERR_NullArgs;
    -   if (InputSize < 4) return ERR_Args;
    +   if ((!State) or (!Input) or (!Output) or (!Written)) return ERR::NullArgs;
    +   if (InputSize < 4) return ERR::Args;
     
        if (!State->Initialised) {
           State->Initialised = TRUE;
    @@ -181,7 +181,7 @@ ERROR Base64Decode(pfBase64Decode *State, CSTRING Input, LONG InputSize, APTR Ou
        }
     
        *Written = base64_decode_block(Input, InputSize, (char *)Output, State);
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     static LONG base64_decode_block(CSTRING code_in, LONG length_in, char * plaintext_out, pfBase64Decode *State)
    diff --git a/src/core/lib_events.cpp b/src/core/lib_events.cpp
    index cf0d260f1..d6cfcf7e3 100644
    --- a/src/core/lib_events.cpp
    +++ b/src/core/lib_events.cpp
    @@ -36,7 +36,8 @@ struct eventsub {
        struct eventsub *Prev;
        EVENTID  EventID;
        EVENTID  EventMask;
    -   void     (*Callback)(APTR Custom, APTR Info, LONG Size);
    +   void     (*Callback)(APTR Custom, APTR Info, LONG Size, APTR Meta);
    +   APTR     CallbackMeta;
        EVG      Group;
        UBYTE    Called;
        OBJECTID ContextID;
    @@ -101,11 +102,11 @@ NullArgs
     
     *********************************************************************************************************************/
     
    -ERROR BroadcastEvent(APTR Event, LONG EventSize)
    +ERR BroadcastEvent(APTR Event, LONG EventSize)
     {
        pf::Log log(__FUNCTION__);
     
    -   if ((!Event) or ((size_t)EventSize < sizeof(rkEvent))) return ERR_NullArgs;
    +   if ((!Event) or ((size_t)EventSize < sizeof(rkEvent))) return ERR::NullArgs;
     
        LONG groupmask = 1<<((((rkEvent *)Event)->EventID>>56) & 0xff);
     
    @@ -116,7 +117,7 @@ ERROR BroadcastEvent(APTR Event, LONG EventSize)
           SendMessage(MSGID_EVENT, MSF::NIL, Event, EventSize);
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
     /*********************************************************************************************************************
    @@ -196,29 +197,29 @@ AllocMemory
     
     *********************************************************************************************************************/
     
    -ERROR SubscribeEvent(LARGE EventID, FUNCTION *Callback, APTR Custom, APTR *Handle)
    +ERR SubscribeEvent(LARGE EventID, FUNCTION *Callback, APTR Custom, APTR *Handle)
     {
        pf::Log log(__FUNCTION__);
     
    -   if ((!Callback) or (!EventID) or (!Handle)) return ERR_NullArgs;
    +   if ((!Callback) or (!EventID) or (!Handle)) return ERR::NullArgs;
     
    -   if (Callback->Type != CALL_STDC) return ERR_Args; // Currently only StdC callbacks are accepted.
    +   if (!Callback->isC()) return ERR::Args; // Currently only StdC callbacks are accepted.
     
        auto gid = EVG(UBYTE(EventID>>56));
     
        if ((LONG(gid) < 1) or (LONG(gid) >= LONG(EVG::END))) {
    -      return log.warning(ERR_Args);
    +      return log.warning(ERR::Args);
        }
     
    -   struct eventsub *event;
    -   if ((event = (struct eventsub *)malloc(sizeof(struct eventsub)))) {
    +   if (auto event = (struct eventsub *)malloc(sizeof(struct eventsub))) {
           LARGE mask = 0xff00000000000000LL;
           if (EventID & 0x00ffffff00000000LL) mask |= 0x00ffffff00000000LL;
           if (EventID & 0x00000000ffffffffLL) mask |= 0x00000000ffffffffLL;
     
           OBJECTPTR context = CurrentContext();
           event->EventID   = EventID;
    -      event->Callback  = (void (*)(APTR, APTR, LONG))Callback->StdC.Routine;
    +      event->Callback  = (void (*)(APTR, APTR, LONG, APTR))Callback->StdC.Routine;
    +      event->CallbackMeta = Callback->StdC.Meta;
           event->Group     = gid;
           event->ContextID = context->UID;
           event->Next      = glEventList;
    @@ -241,9 +242,9 @@ ERROR SubscribeEvent(LARGE EventID, FUNCTION *Callback, APTR Custom, APTR *Handl
     
           *Handle = event;
     
    -      return ERR_Okay;
    +      return ERR::Okay;
        }
    -   else return ERR_AllocMemory;
    +   else return ERR::AllocMemory;
     }
     
     /*********************************************************************************************************************
    @@ -299,15 +300,15 @@ void UnsubscribeEvent(APTR Handle)
     ** ProcessMessages() will call this function whenever a MSGID_EVENT message is received.
     */
     
    -ERROR msg_event(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize)
    +ERR msg_event(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize)
     {
        pf::Log log(__FUNCTION__);
     
    -   if ((!Message) or ((size_t)MsgSize < sizeof(rkEvent))) return ERR_Okay;
    +   if ((!Message) or ((size_t)MsgSize < sizeof(rkEvent))) return ERR::Okay;
     
        rkEvent *eventmsg = (rkEvent *)Message;
     
    -   log.msg(VLF::EXTAPI|VLF::BRANCH, "Event $%.8x%8x has been received.", (LONG)((eventmsg->EventID>>32)& 0xffffffff),
    +   log.msg(VLF::DETAIL|VLF::BRANCH, "Event $%.8x%8x has been received.", (LONG)((eventmsg->EventID>>32)& 0xffffffff),
           (LONG)(eventmsg->EventID & 0xffffffff));
     
        struct eventsub *event;
    @@ -326,7 +327,7 @@ ERROR msg_event(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSiz
              pf::ScopedObjectLock lock(event->ContextID, 3000);
              if (lock.granted()) {
                 pf::SwitchContext ctx(lock.obj);
    -            event->Callback(event->Custom, Message, MsgSize);
    +            event->Callback(event->Custom, Message, MsgSize, event->CallbackMeta);
              }
     
              if (glEventListAltered) goto restart;
    @@ -335,5 +336,5 @@ ERROR msg_event(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSiz
           event = event->Next;
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
    diff --git a/src/core/lib_fields_read.cpp b/src/core/lib_fields_read.cpp
    index 4321ef05d..9e290dee5 100644
    --- a/src/core/lib_fields_read.cpp
    +++ b/src/core/lib_fields_read.cpp
    @@ -110,7 +110,7 @@ The FindField() function checks if an object supports a specified field by scann
     If a matching field is declared, its descriptor is returned.  For example:
     
     
    -if (auto field = FindField(Screen, FID_Width, NULL)) {
    +if (auto field = FindField(Display, FID_Width, NULL)) {
        log.msg("The field name is \"%s\".", field->Name);
     }
     
    @@ -185,10 +185,10 @@ UnsupportedField: The Field is not supported by the object's class. *********************************************************************************************************************/ -ERROR GetField(OBJECTPTR Object, FIELD FieldID, APTR Result) +ERR GetField(OBJECTPTR Object, FIELD FieldID, APTR Result) { pf::Log log(__FUNCTION__); - if ((!Object) or (!Result)) return log.warning(ERR_NullArgs); + if ((!Object) or (!Result)) return log.warning(ERR::NullArgs); ULONG type = FieldID>>32; FieldID = FieldID & 0xffffffff; @@ -207,7 +207,7 @@ ERROR GetField(OBJECTPTR Object, FIELD FieldID, APTR Result) if (!(field->Flags & FD_READ)) { if (!field->Name) log.warning("Illegal attempt to read field %s.", FieldName(FieldID)); else log.warning("Illegal attempt to read field %s.", field->Name); - return ERR_NoFieldAccess; + return ERR::NoFieldAccess; } ScopedObjectAccess objlock(Object); @@ -215,7 +215,7 @@ ERROR GetField(OBJECTPTR Object, FIELD FieldID, APTR Result) } else log.warning("Unsupported field %s", FieldName(FieldID)); - return ERR_UnsupportedField; + return ERR::UnsupportedField; } /********************************************************************************************************************* @@ -248,11 +248,11 @@ Mismatch *********************************************************************************************************************/ -ERROR GetFieldArray(OBJECTPTR Object, FIELD FieldID, APTR *Result, LONG *Elements) +ERR GetFieldArray(OBJECTPTR Object, FIELD FieldID, APTR *Result, LONG *Elements) { pf::Log log(__FUNCTION__); - if ((!Object) or (!Result) or (!Elements)) return log.warning(ERR_NullArgs); + if ((!Object) or (!Result) or (!Elements)) return log.warning(ERR::NullArgs); LONG req_type = FieldID>>32; FieldID = FieldID & 0xffffffff; @@ -263,20 +263,20 @@ ERROR GetFieldArray(OBJECTPTR Object, FIELD FieldID, APTR *Result, LONG *Element if ((!(field->Flags & FD_READ)) or (!(field->Flags & FD_ARRAY))) { if (!field->Name) log.warning("Illegal attempt to read field %s.", FieldName(FieldID)); else log.warning("Illegal attempt to read field %s.", field->Name); - return ERR_NoFieldAccess; + return ERR::NoFieldAccess; } if (req_type) { // Perform simple type validation if requested to do so. - if (!(req_type & field->Flags)) return log.warning(ERR_Mismatch); + if (!(req_type & field->Flags)) return log.warning(ERR::Mismatch); } ScopedObjectAccess objlock(Object); - ERROR error = copy_field_to_buffer(Object, field, FD_POINTER, Result, NULL, Elements); + ERR error = copy_field_to_buffer(Object, field, FD_POINTER, Result, NULL, Elements); return error; } else log.warning("Unsupported field %s", FieldName(FieldID)); - return ERR_UnsupportedField; + return ERR::UnsupportedField; } /********************************************************************************************************************* @@ -323,18 +323,18 @@ Mismatch: The field value cannot be converted into a string. *********************************************************************************************************************/ -ERROR GetFieldVariable(OBJECTPTR Object, CSTRING FieldName, STRING Buffer, LONG BufferSize) +ERR GetFieldVariable(OBJECTPTR Object, CSTRING FieldName, STRING Buffer, LONG BufferSize) { pf::Log log("GetVariable"); if ((!Object) or (!FieldName) or (!Buffer) or (BufferSize < 2)) { - return log.warning(ERR_Args); + return log.warning(ERR::Args); } Field *field; char flagref[80]; LONG i; - ERROR error; + ERR error; Buffer[0] = 0; flagref[0] = 0; @@ -383,14 +383,14 @@ ERROR GetFieldVariable(OBJECTPTR Object, CSTRING FieldName, STRING Buffer, LONG if (!(field->Flags & FD_READ)) { if (!field->Name) log.warning("Illegal attempt to read field %d.", field->FieldID); else log.warning("Illegal attempt to read field %s.", field->Name); - return ERR_NoFieldAccess; + return ERR::NoFieldAccess; } ScopedObjectAccess objlock(Object); if (field->Flags & (FD_STRING|FD_ARRAY)) { STRING str = NULL; - if (!(error = copy_field_to_buffer(Object, field, FD_POINTER|FD_STRING, &str, ext, NULL))) { + if ((error = copy_field_to_buffer(Object, field, FD_POINTER|FD_STRING, &str, ext, NULL)) IS ERR::Okay) { if (checkdefined) { if (field->Flags & FD_STRING) { if ((str) and (str[0])) Buffer[0] = '1'; // A string needs only one char (of any kind) to be considered to be defined @@ -414,14 +414,14 @@ ERROR GetFieldVariable(OBJECTPTR Object, CSTRING FieldName, STRING Buffer, LONG FieldDef *lookup; LARGE large; - if (!(error = copy_field_to_buffer(Object, field, FD_LARGE, &large, ext, NULL))) { + if ((error = copy_field_to_buffer(Object, field, FD_LARGE, &large, ext, NULL)) IS ERR::Okay) { if ((ext) and (field->Flags & (FD_FLAGS|FD_LOOKUP))) { Buffer[0] = '0'; Buffer[1] = 0; if ((lookup = (FieldDef *)field->Arg)) { while (lookup->Name) { - if (!StrMatch(lookup->Name, ext)) { + if (StrMatch(lookup->Name, ext) IS ERR::Okay) { if (field->Flags & FD_FLAGS) { if (large & lookup->Value) Buffer[0] = '1'; } @@ -433,7 +433,7 @@ ERROR GetFieldVariable(OBJECTPTR Object, CSTRING FieldName, STRING Buffer, LONG } else log.warning("No lookup table for field '%s', class '%s'.", fname, Object->className()); - return ERR_Okay; + return ERR::Okay; } else if (strconvert) { if (field->Flags & FD_FLAGS) { @@ -446,7 +446,7 @@ ERROR GetFieldVariable(OBJECTPTR Object, CSTRING FieldName, STRING Buffer, LONG } lookup++; } - return ERR_Okay; + return ERR::Okay; } } else if (field->Flags & FD_LOOKUP) { @@ -458,7 +458,7 @@ ERROR GetFieldVariable(OBJECTPTR Object, CSTRING FieldName, STRING Buffer, LONG } lookup++; } - return ERR_Okay; + return ERR::Okay; } } } @@ -473,14 +473,14 @@ ERROR GetFieldVariable(OBJECTPTR Object, CSTRING FieldName, STRING Buffer, LONG } else if (field->Flags & FD_DOUBLE) { DOUBLE dbl; - if (!(error = copy_field_to_buffer(Object, field, FD_DOUBLE, &dbl, ext, NULL))) { + if ((error = copy_field_to_buffer(Object, field, FD_DOUBLE, &dbl, ext, NULL)) IS ERR::Okay) { snprintf(Buffer, BufferSize, "%f", dbl); } else return error; } else if (field->Flags & (FD_INTEGRAL|FD_OBJECT)) { OBJECTPTR obj; - if (!(error = copy_field_to_buffer(Object, field, FD_POINTER, &obj, ext, NULL))) { + if ((error = copy_field_to_buffer(Object, field, FD_POINTER, &obj, ext, NULL)) IS ERR::Okay) { if (ext) { error = GetFieldVariable(obj, ext, Buffer, BufferSize); return error; @@ -491,33 +491,33 @@ ERROR GetFieldVariable(OBJECTPTR Object, CSTRING FieldName, STRING Buffer, LONG } else { log.warning("Field %s is not a value that can be converted to a string.", field->Name); - return ERR_Mismatch; + return ERR::Mismatch; } - return ERR_Okay; + return ERR::Okay; } else { - if (!CheckAction(Object, AC_GetVar)) { + if (CheckAction(Object, AC_GetVar) IS ERR::Okay) { struct acGetVar var = { .Field = FieldName, // Must use the original field name argument, not the modified fname .Buffer = Buffer, .Size = BufferSize }; - if (!Action(AC_GetVar, Object, &var)) { - return ERR_Okay; + if (Action(AC_GetVar, Object, &var) IS ERR::Okay) { + return ERR::Okay; } else log.msg("Could not find field %s from object %p (%s).", FieldName, Object, Object->className()); } else log.warning("Could not find field %s from object %p (%s).", FieldName, Object, Object->className()); - return ERR_UnsupportedField; + return ERR::UnsupportedField; } } //******************************************************************************************************************** // Used by the GetField() range of functions. -ERROR copy_field_to_buffer(OBJECTPTR Object, Field *Field, LONG DestFlags, APTR Result, CSTRING Option, LONG *TotalElements) +ERR copy_field_to_buffer(OBJECTPTR Object, Field *Field, LONG DestFlags, APTR Result, CSTRING Option, LONG *TotalElements) { pf::Log log("GetField"); @@ -531,10 +531,10 @@ ERROR copy_field_to_buffer(OBJECTPTR Object, Field *Field, LONG DestFlags, APTR if (!(DestFlags & (FD_VARIABLE|FD_LARGE|FD_LONG|FD_DOUBLE|FD_POINTER|FD_STRING|FD_ARRAY))) goto mismatch; if (srcflags & FD_VARIABLE) { - if (!Field->GetValue) return ERR_NoFieldAccess; + if (!Field->GetValue) return ERR::NoFieldAccess; Variable var; - ERROR error; + ERR error; ObjectContext ctx(Object, 0, Field); if (DestFlags & FD_VARIABLE) { @@ -544,22 +544,22 @@ ERROR copy_field_to_buffer(OBJECTPTR Object, Field *Field, LONG DestFlags, APTR var.Type = FD_DOUBLE | (DestFlags & (~(FD_LONG|FD_LARGE))); error = Field->GetValue(Object, &var); - if (!error) { + if (error IS ERR::Okay) { if (DestFlags & FD_LARGE) *((LARGE *)Result) = var.Double; else if (DestFlags & FD_LONG) *((LONG *)Result) = var.Double; else if (DestFlags & FD_DOUBLE) *((DOUBLE *)Result) = var.Double; - else error = ERR_FieldTypeMismatch; + else error = ERR::FieldTypeMismatch; } } else if (srcflags & (FD_LARGE|FD_LONG)) { var.Type = FD_LARGE | (DestFlags & (~(FD_LARGE|FD_LONG|FD_DOUBLE))); error = Field->GetValue(Object, &var); - if (!error) { + if (error IS ERR::Okay) { if (DestFlags & FD_LARGE) *((LARGE *)Result) = var.Large; else if (DestFlags & FD_LONG) *((LONG *)Result) = var.Large; else if (DestFlags & FD_DOUBLE) *((DOUBLE *)Result) = var.Large; - else error = ERR_FieldTypeMismatch; + else error = ERR::FieldTypeMismatch; } } else { @@ -568,7 +568,7 @@ ERROR copy_field_to_buffer(OBJECTPTR Object, Field *Field, LONG DestFlags, APTR else var.Type = DestFlags; error = Field->GetValue(Object, &var); - if (!error) { + if (error IS ERR::Okay) { if (DestFlags & FD_LARGE) *((LARGE *)Result) = var.Large; else if (DestFlags & FD_LONG) *((LONG *)Result) = (LONG)var.Large; else if (DestFlags & FD_DOUBLE) *((DOUBLE *)Result) = var.Double; @@ -576,15 +576,15 @@ ERROR copy_field_to_buffer(OBJECTPTR Object, Field *Field, LONG DestFlags, APTR } } - if (error IS ERR_FieldTypeMismatch) goto mismatch; + if (error IS ERR::FieldTypeMismatch) goto mismatch; else return error; } if (Field->GetValue) { ObjectContext ctx(Object, 0, Field); - auto get_field = (ERROR (*)(APTR, APTR, LONG *))Field->GetValue; - ERROR error = get_field(Object, value, &array_size); - if (error) return error; + auto get_field = (ERR (*)(APTR, APTR, LONG *))Field->GetValue; + ERR error = get_field(Object, value, &array_size); + if (error != ERR::Okay) return error; data = value; } else data = ((BYTE *)Object) + Field->Offset; @@ -604,7 +604,7 @@ ERROR copy_field_to_buffer(OBJECTPTR Object, Field *Field, LONG DestFlags, APTR else goto mismatch; // Drop through to field value conversion } - else return ERR_OutOfRange; + else return ERR::OutOfRange; } else if (DestFlags & FD_STRING) { // Special feature: If a string is requested, the array values are converted to CSV format. @@ -634,7 +634,7 @@ ERROR copy_field_to_buffer(OBJECTPTR Object, Field *Field, LONG DestFlags, APTR else { if (array_size IS -1) { log.warning("Array sizing not supported for field %s", Field->Name); - return ERR_Failed; + return ERR::Failed; } if (TotalElements) *TotalElements = array_size; @@ -648,7 +648,7 @@ ERROR copy_field_to_buffer(OBJECTPTR Object, Field *Field, LONG DestFlags, APTR else goto mismatch; // Drop through to field value conversion } - else return ERR_OutOfRange; + else return ERR::OutOfRange; } else if (DestFlags & FD_STRING) { // Special feature: If a string is requested, the array values are converted to CSV format. @@ -680,7 +680,7 @@ ERROR copy_field_to_buffer(OBJECTPTR Object, Field *Field, LONG DestFlags, APTR else if (DestFlags & FD_POINTER) *((APTR *)Result) = *((APTR *)data); else goto mismatch; } - return ERR_Okay; + return ERR::Okay; } if (srcflags & FD_LONG) { @@ -696,7 +696,7 @@ ERROR copy_field_to_buffer(OBJECTPTR Object, Field *Field, LONG DestFlags, APTR while (lookup->Name) { if (value IS lookup->Value) { *((CSTRING *)Result) = lookup->Name; - return ERR_Okay; + return ERR::Okay; } lookup++; } @@ -744,12 +744,12 @@ ERROR copy_field_to_buffer(OBJECTPTR Object, Field *Field, LONG DestFlags, APTR } else { log.warning("I dont recognise field flags of $%.8x.", srcflags); - return ERR_UnrecognisedFieldType; + return ERR::UnrecognisedFieldType; } - return ERR_Okay; + return ERR::Okay; mismatch: log.warning("Mismatch while reading %s.%s (field $%.8x, requested $%.8x).", Object->className(), Field->Name, Field->Flags, DestFlags); - return ERR_FieldTypeMismatch; + return ERR::FieldTypeMismatch; } diff --git a/src/core/lib_fields_write.cpp b/src/core/lib_fields_write.cpp index dfa186958..ebdc7aabf 100644 --- a/src/core/lib_fields_write.cpp +++ b/src/core/lib_fields_write.cpp @@ -19,22 +19,22 @@ Name: Fields #define OP_AND 1 #define OP_OVERWRITE 2 -static ERROR writeval_array(OBJECTPTR, Field *, LONG, CPTR , LONG); -static ERROR writeval_flags(OBJECTPTR, Field *, LONG, CPTR , LONG); -static ERROR writeval_long(OBJECTPTR, Field *, LONG, CPTR , LONG); -static ERROR writeval_large(OBJECTPTR, Field *, LONG, CPTR , LONG); -static ERROR writeval_double(OBJECTPTR, Field *, LONG, CPTR , LONG); -static ERROR writeval_function(OBJECTPTR, Field *, LONG, CPTR , LONG); -static ERROR writeval_ptr(OBJECTPTR, Field *, LONG, CPTR , LONG); - -static ERROR setval_large(OBJECTPTR, Field *, LONG Flags, CPTR , LONG); -static ERROR setval_pointer(OBJECTPTR, Field *, LONG Flags, CPTR , LONG); -static ERROR setval_double(OBJECTPTR, Field *, LONG Flags, CPTR , LONG); -static ERROR setval_long(OBJECTPTR, Field *, LONG Flags, CPTR , LONG); -static ERROR setval_function(OBJECTPTR, Field *, LONG Flags, CPTR , LONG); -static ERROR setval_array(OBJECTPTR, Field *, LONG Flags, CPTR , LONG); -static ERROR setval_brgb(OBJECTPTR, Field *, LONG Flags, CPTR , LONG); -static ERROR setval_variable(OBJECTPTR, Field *, LONG Flags, CPTR , LONG); +static ERR writeval_array(OBJECTPTR, Field *, LONG, CPTR , LONG); +static ERR writeval_flags(OBJECTPTR, Field *, LONG, CPTR , LONG); +static ERR writeval_long(OBJECTPTR, Field *, LONG, CPTR , LONG); +static ERR writeval_large(OBJECTPTR, Field *, LONG, CPTR , LONG); +static ERR writeval_double(OBJECTPTR, Field *, LONG, CPTR , LONG); +static ERR writeval_function(OBJECTPTR, Field *, LONG, CPTR , LONG); +static ERR writeval_ptr(OBJECTPTR, Field *, LONG, CPTR , LONG); + +static ERR setval_large(OBJECTPTR, Field *, LONG Flags, CPTR , LONG); +static ERR setval_pointer(OBJECTPTR, Field *, LONG Flags, CPTR , LONG); +static ERR setval_double(OBJECTPTR, Field *, LONG Flags, CPTR , LONG); +static ERR setval_long(OBJECTPTR, Field *, LONG Flags, CPTR , LONG); +static ERR setval_function(OBJECTPTR, Field *, LONG Flags, CPTR , LONG); +static ERR setval_array(OBJECTPTR, Field *, LONG Flags, CPTR , LONG); +static ERR setval_brgb(OBJECTPTR, Field *, LONG Flags, CPTR , LONG); +static ERR setval_variable(OBJECTPTR, Field *, LONG Flags, CPTR , LONG); /********************************************************************************************************************* @@ -69,40 +69,40 @@ NoFieldAccess: The field is read-only. *********************************************************************************************************************/ -ERROR SetArray(OBJECTPTR Object, FIELD FieldID, APTR Array, LONG Elements) +ERR SetArray(OBJECTPTR Object, FIELD FieldID, APTR Array, LONG Elements) { pf::Log log(__FUNCTION__); - if (!Object) return log.warning(ERR_NullArgs); + if (!Object) return log.warning(ERR::NullArgs); if (Elements <= 0) log.warning("Element count not specified."); LONG type = (FieldID>>32)|FD_ARRAY; FieldID = FieldID & 0xffffffff; if (auto field = lookup_id(Object, FieldID, &Object)) { - if (!(field->Flags & FD_ARRAY)) return log.warning(ERR_FieldTypeMismatch); + if (!(field->Flags & FD_ARRAY)) return log.warning(ERR::FieldTypeMismatch); if ((!(field->Flags & (FD_INIT|FD_WRITE))) and (tlContext->object() != Object)) { if (!field->Name) log.warning("Field %s of class %s is not writeable.", FieldName(field->FieldID), Object->className()); else log.warning("Field \"%s\" of class %s is not writeable.", field->Name, Object->className()); - return ERR_NoFieldAccess; + return ERR::NoFieldAccess; } if ((field->Flags & FD_INIT) and (Object->initialised()) and (tlContext->object() != Object)) { if (!field->Name) log.warning("Field %s in class %s is init-only.", FieldName(field->FieldID), Object->className()); else log.warning("Field \"%s\" in class %s is init-only.", field->Name, Object->className()); - return ERR_NoFieldAccess; + return ERR::NoFieldAccess; } Object->lock(); - ERROR error = field->WriteValue(Object, field, type, Array, Elements); + ERR error = field->WriteValue(Object, field, type, Array, Elements); Object->unlock(); return error; } else { - log.warning("Could not find field %s in object class %s.", FieldName(FieldID), Object->className()); - return ERR_UnsupportedField; + log.warning("Could not find field %s in class %s.", FieldName(FieldID), Object->className()); + return ERR::UnsupportedField; } } @@ -120,27 +120,28 @@ SetField(Object, FID_X|TLONG, 100); SetField(Object, FID_Statement|TSTR, "string");
    -Fields are referenced by unique ID's that reflect their names. On occasion you may find that there is no reserved ID -for the field that you wish to access. To convert field names into their relevant IDs, call the -~StrHash() function. Reserved field ID's are listed in the `parasol/system/fields.h` include file. +Fields are referenced as hashed UID's calculated from the ~StrHash() function. The majority of field ID's are +predefined in the `parasol/system/fields.h` include file. -The type of the Value parameter must be OR'd into the Field parameter. When writing a field you must give -consideration to the type of the target, in order to prevent a type mismatch from occurring. All numeric types are -compatible with each other and strings can also be converted to numeric types automatically. String and pointer types -are interchangeable. +The type of the Value parameter must be OR'd into the Field parameter. If the provided type does not match that of +the field, a type conversion will occur. All numeric types are compatible with each other and strings can also be +converted to a numeric value automatically. String and pointer types are interchangeable. Available field types are as follows: A 32-bit integer value. A 64-bit floating point value. +A 64-bit floating point value that represents a scaled multiplier or percentage (1.0 is equivalent to 100%). A 64-bit integer value. -A standard 32-bit address space pointer. -A 32-bit pointer that refers to a string. +A standard address space pointer. +A pointer that refers to a string. +A pointer to a FUNCTION structure. +A pointer to a Variable structure. -There is no requirement for you to have a working knowledge of the target object's field configuration in order to -write information to it. +There is no requirement for the client to have a working knowledge of the target object's field configuration in +order to write information to it. To set a field with a fixed-size array, please use the ~SetArray() function. @@ -157,11 +158,11 @@ NoFieldAccess: The field is read-only. *********************************************************************************************************************/ -ERROR SetField(OBJECTPTR Object, FIELD FieldID, ...) +ERR SetField(OBJECTPTR Object, FIELD FieldID, ...) { pf::Log log(__FUNCTION__); - if (!Object) return log.warning(ERR_NullArgs); + if (!Object) return log.warning(ERR::NullArgs); ULONG type = FieldID>>32; FieldID = FieldID & 0xffffffff; @@ -170,19 +171,19 @@ ERROR SetField(OBJECTPTR Object, FIELD FieldID, ...) // Validation if ((!(field->Flags & (FD_INIT|FD_WRITE))) and (tlContext->object() != Object)) { - if (!field->Name) log.warning("Field %s of class %s is not writeable.", FieldName(field->FieldID), Object->className()); - else log.warning("Field \"%s\" of class %s is not writeable.", field->Name, Object->className()); - return ERR_NoFieldAccess; + if (field->Name) log.warning("%s.%s is immutable.", Object->className(), field->Name); + else log.warning("%s.%s is immutable.", Object->className(), FieldName(field->FieldID)); + return ERR::NoFieldAccess; } else if ((field->Flags & FD_INIT) and (Object->initialised()) and (tlContext->object() != Object)) { - if (!field->Name) log.warning("Field %s in class %s is init-only.", FieldName(field->FieldID), Object->className()); - else log.warning("Field \"%s\" in class %s is init-only.", field->Name, Object->className()); - return ERR_NoFieldAccess; + if (field->Name) log.warning("%s.%s is init-only.", Object->className(), field->Name); + else log.warning("%s.%s is init-only.", Object->className(), FieldName(field->FieldID)); + return ERR::NoFieldAccess; } Object->lock(); - ERROR error; + ERR error; va_list list; va_start(list, FieldID); @@ -208,8 +209,8 @@ ERROR SetField(OBJECTPTR Object, FIELD FieldID, ...) return error; } else { - log.warning("Could not find field %s in object class %s.", FieldName(FieldID), Object->className()); - return ERR_UnsupportedField; + log.warning("Could not find field %s in class %s.", FieldName(FieldID), Object->className()); + return ERR::UnsupportedField; } } @@ -290,7 +291,7 @@ static LONG write_array(CSTRING String, LONG Flags, WORD ArraySize, APTR Dest) //******************************************************************************************************************** // Used by some of the SetField() range of instructions. -ERROR writeval_default(OBJECTPTR Object, Field *Field, LONG flags, CPTR Data, LONG Elements) +ERR writeval_default(OBJECTPTR Object, Field *Field, LONG flags, CPTR Data, LONG Elements) { pf::Log log("WriteField"); @@ -299,7 +300,7 @@ ERROR writeval_default(OBJECTPTR Object, Field *Field, LONG flags, CPTR Data, LO if (!flags) flags = Field->Flags; if (!Field->SetValue) { - ERROR error = ERR_Okay; + ERR error = ERR::Okay; if (Field->Flags & FD_ARRAY) error = writeval_array(Object, Field, flags, Data, Elements); else if (Field->Flags & FD_LONG) error = writeval_long(Object, Field, flags, Data, 0); else if (Field->Flags & FD_LARGE) error = writeval_large(Object, Field, flags, Data, 0); @@ -308,7 +309,7 @@ ERROR writeval_default(OBJECTPTR Object, Field *Field, LONG flags, CPTR Data, LO else if (Field->Flags & (FD_POINTER|FD_STRING)) error = writeval_ptr(Object, Field, flags, Data, 0); else log.warning("Unrecognised field flags $%.8x.", Field->Flags); - if (error != ERR_Okay) log.warning("An error occurred writing to field %s (field type $%.8x, source type $%.8x).", Field->Name, Field->Flags, flags); + if (error != ERR::Okay) log.warning("An error occurred writing to field %s (field type $%.8x, source type $%.8x).", Field->Name, Field->Flags, flags); return error; } else { @@ -320,7 +321,7 @@ ERROR writeval_default(OBJECTPTR Object, Field *Field, LONG flags, CPTR Data, LO else if (Field->Flags & (FD_DOUBLE|FD_FLOAT)) return setval_double(Object, Field, flags, Data, 0); else if (Field->Flags & (FD_POINTER|FD_STRING)) return setval_pointer(Object, Field, flags, Data, 0); else if (Field->Flags & FD_LARGE) return setval_large(Object, Field, flags, Data, 0); - else return ERR_FieldTypeMismatch; + else return ERR::FieldTypeMismatch; } } @@ -328,7 +329,7 @@ ERROR writeval_default(OBJECTPTR Object, Field *Field, LONG flags, CPTR Data, LO // The writeval() functions are used as optimised calls for all cases where the client has not provided a SetValue() // function. -static ERROR writeval_array(OBJECTPTR Object, Field *Field, LONG SrcType, CPTR Source, LONG Elements) +static ERR writeval_array(OBJECTPTR Object, Field *Field, LONG SrcType, CPTR Source, LONG Elements) { pf::Log log("WriteField"); @@ -342,7 +343,7 @@ static ERROR writeval_array(OBJECTPTR Object, Field *Field, LONG SrcType, CPTR S else if (Field->Flags & FD_LONG) ((RGB8 *)offset)->Alpha = 255; else if (Field->Flags & FD_BYTE) ((RGB8 *)offset)->Alpha = 255; write_array((CSTRING)Source, Field->Flags, 4, offset); - return ERR_Okay; + return ERR::Okay; } else if ((SrcType & FD_POINTER) and (Field->Flags & FD_RGB)) { // Presume the source is a pointer to an RGB structure RGB8 *rgb = (RGB8 *)Source; @@ -350,14 +351,14 @@ static ERROR writeval_array(OBJECTPTR Object, Field *Field, LONG SrcType, CPTR S ((RGB8 *)offset)->Green = rgb->Green; ((RGB8 *)offset)->Blue = rgb->Blue; ((RGB8 *)offset)->Alpha = rgb->Alpha; - return ERR_Okay; + return ERR::Okay; } log.warning("Field array '%s' is poorly defined.", Field->Name); - return ERR_Failed; + return ERR::Failed; } -static ERROR writeval_flags(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) +static ERR writeval_flags(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) { pf::Log log("WriteField"); LONG j, int32; @@ -389,7 +390,7 @@ static ERROR writeval_flags(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Dat if (j > 0) { FieldDef *lk = (FieldDef *)Field->Arg; while (lk->Name) { - if ((!StrCompare(lk->Name, str, j)) and (!lk->Name[j])) { + if ((StrCompare(lk->Name, str, j) IS ERR::Okay) and (!lk->Name[j])) { int64 |= lk->Value; break; } @@ -406,9 +407,9 @@ static ERROR writeval_flags(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Dat // Get the current flag values from the field if special ops are requested if (op != OP_OVERWRITE) { - ERROR error; + ERR error; LONG currentflags; - if (!(error = copy_field_to_buffer(Object, Field, FT_LONG, ¤tflags, NULL, NULL))) { + if ((error = copy_field_to_buffer(Object, Field, FT_LONG, ¤tflags, NULL, NULL)) IS ERR::Okay) { if (op IS OP_OR) int64 = currentflags | int64; else if (op IS OP_AND) int64 = currentflags & int64; } @@ -427,13 +428,13 @@ static ERROR writeval_flags(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Dat Flags = FD_LARGE; Data = &int64; } - else return ERR_SetValueNotArray; + else return ERR::SetValueNotArray; } return writeval_default(Object, Field, Flags, Data, Elements); } -static ERROR writeval_lookup(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) +static ERR writeval_lookup(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) { pf::Log log("WriteField"); LONG int32; @@ -444,7 +445,7 @@ static ERROR writeval_lookup(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Da int32 = StrToInt((CSTRING)Data); // If the Data string is a number rather than a lookup, this will extract it if ((lookup = (FieldDef *)Field->Arg)) { while (lookup->Name) { - if (!StrCompare((CSTRING)Data, lookup->Name, 0, STR::MATCH_LEN)) { + if (StrCompare((CSTRING)Data, lookup->Name, 0, STR::MATCH_LEN) IS ERR::Okay) { int32 = lookup->Value; break; } @@ -462,42 +463,42 @@ static ERROR writeval_lookup(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Da return writeval_default(Object, Field, Flags, Data, Elements); } -static ERROR writeval_long(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) +static ERR writeval_long(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) { - LONG *offset = (LONG *)((BYTE *)Object + Field->Offset); + auto offset = (LONG *)((BYTE *)Object + Field->Offset); if (Flags & FD_LONG) *offset = *((LONG *)Data); else if (Flags & FD_LARGE) *offset = (LONG)(*((LARGE *)Data)); else if (Flags & (FD_DOUBLE|FD_FLOAT)) *offset = F2I(*((DOUBLE *)Data)); else if (Flags & FD_STRING) *offset = (LONG)StrToInt((STRING)Data); - else return ERR_SetValueNotNumeric; - return ERR_Okay; + else return ERR::SetValueNotNumeric; + return ERR::Okay; } -static ERROR writeval_large(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) +static ERR writeval_large(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) { - LARGE *offset = (LARGE *)((BYTE *)Object + Field->Offset); + auto offset = (LARGE *)((BYTE *)Object + Field->Offset); if (Flags & FD_LARGE) *offset = *((LARGE *)Data); else if (Flags & FD_LONG) *offset = *((LONG *)Data); else if (Flags & (FD_DOUBLE|FD_FLOAT)) *offset = F2I(*((DOUBLE *)Data)); else if (Flags & FD_STRING) *offset = strtoll((STRING)Data, NULL, 0); - else return ERR_SetValueNotNumeric; - return ERR_Okay; + else return ERR::SetValueNotNumeric; + return ERR::Okay; } -static ERROR writeval_double(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) +static ERR writeval_double(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) { - DOUBLE *offset = (DOUBLE *)((BYTE *)Object + Field->Offset); + auto offset = (DOUBLE *)((BYTE *)Object + Field->Offset); if (Flags & (FD_DOUBLE|FD_FLOAT)) *offset = *((DOUBLE *)Data); else if (Flags & FD_LONG) *offset = *((LONG *)Data); else if (Flags & FD_LARGE) *offset = (*((LARGE *)Data)); else if (Flags & FD_STRING) *offset = strtod((STRING)Data, NULL); - else return ERR_SetValueNotNumeric; - return ERR_Okay; + else return ERR::SetValueNotNumeric; + return ERR::Okay; } -static ERROR writeval_function(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) +static ERR writeval_function(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) { - FUNCTION *offset = (FUNCTION *)((BYTE *)Object + Field->Offset); + auto offset = (FUNCTION *)((BYTE *)Object + Field->Offset); if (Flags & FD_FUNCTION) { offset[0] = ((FUNCTION *)Data)[0]; } @@ -506,16 +507,16 @@ static ERROR writeval_function(OBJECTPTR Object, Field *Field, LONG Flags, CPTR offset[0].StdC.Routine = (FUNCTION *)Data; offset[0].StdC.Context = tlContext->object(); } - else return ERR_SetValueNotFunction; - return ERR_Okay; + else return ERR::SetValueNotFunction; + return ERR::Okay; } -static ERROR writeval_ptr(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) +static ERR writeval_ptr(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) { - APTR *offset = (APTR *)((BYTE *)Object + Field->Offset); + auto offset = (APTR *)((BYTE *)Object + Field->Offset); if (Flags & (FD_POINTER|FD_STRING)) *offset = (void *)Data; - else return ERR_SetValueNotPointer; - return ERR_Okay; + else return ERR::SetValueNotPointer; + return ERR::Okay; } //******************************************************************************************************************** @@ -541,7 +542,7 @@ class FieldContext : public ObjectContext { //******************************************************************************************************************** -static ERROR setval_variable(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) +static ERR setval_variable(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) { // Convert the value to match what the variable will accept, then call the variable field's set function. @@ -552,41 +553,41 @@ static ERROR setval_variable(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Da var.Type = FD_LARGE | (Flags & (~(FD_LONG|FD_LARGE|FD_DOUBLE|FD_POINTER|FD_STRING))); if (Flags & FD_LONG) var.Large = *((LONG *)Data); else var.Large = *((LARGE *)Data); - return ((ERROR (*)(APTR, Variable *))(Field->SetValue))(Object, &var); + return ((ERR (*)(APTR, Variable *))(Field->SetValue))(Object, &var); } else if (Flags & (FD_DOUBLE|FD_FLOAT)) { var.Type = FD_DOUBLE | (Flags & (~(FD_LONG|FD_LARGE|FD_DOUBLE|FD_POINTER|FD_STRING))); var.Double = *((DOUBLE *)Data); - return ((ERROR (*)(APTR, Variable *))(Field->SetValue))(Object, &var); + return ((ERR (*)(APTR, Variable *))(Field->SetValue))(Object, &var); } else if (Flags & (FD_POINTER|FD_STRING)) { - if (Field->Flags & FD_PERCENTAGE) { + if (Field->Flags & FD_SCALED) { // Percentages are only applicable to numeric variables, and require conversion in advance. - // NB: If a field needs total control over variable conversion, it should not specify FD_PERCENTAGE. + // NB: If a field needs total control over variable conversion, it should not specify FD_SCALED. STRING pct; var.Double = strtod((CSTRING)Data, &pct); if (pct[0] IS '%') { - var.Type = FD_DOUBLE|FD_PERCENTAGE; + var.Type = FD_DOUBLE|FD_SCALED; var.Double *= 0.01; - return ((ERROR (*)(APTR, Variable *))(Field->SetValue))(Object, &var); + return ((ERR (*)(APTR, Variable *))(Field->SetValue))(Object, &var); } else { var.Type = FD_DOUBLE; - return ((ERROR (*)(APTR, Variable *))(Field->SetValue))(Object, &var); + return ((ERR (*)(APTR, Variable *))(Field->SetValue))(Object, &var); } } var.Type = FD_POINTER | (Flags & (~(FD_LONG|FD_LARGE|FD_DOUBLE|FD_POINTER))); // Allows support flags like FD_STRING to fall through var.Pointer = (APTR)Data; - return ((ERROR (*)(APTR, Variable *))(Field->SetValue))(Object, &var); + return ((ERR (*)(APTR, Variable *))(Field->SetValue))(Object, &var); } else if (Flags & FD_VARIABLE) { - return ((ERROR (*)(APTR, APTR))(Field->SetValue))(Object, (APTR)Data); + return ((ERR (*)(APTR, APTR))(Field->SetValue))(Object, (APTR)Data); } - else return ERR_FieldTypeMismatch; + else return ERR::FieldTypeMismatch; } -static ERROR setval_brgb(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) +static ERR setval_brgb(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) { if (Field->Flags & FD_BYTE) { FieldContext ctx(Object, Field); @@ -594,14 +595,14 @@ static ERROR setval_brgb(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, RGB8 rgb; rgb.Alpha = 255; write_array((CSTRING)Data, FD_BYTE, 4, &rgb); - ERROR error = ((ERROR (*)(APTR, RGB8 *, LONG))(Field->SetValue))(Object, &rgb, 4); + ERR error = ((ERR (*)(APTR, RGB8 *, LONG))(Field->SetValue))(Object, &rgb, 4); return error; } - else return ERR_FieldTypeMismatch; + else return ERR::FieldTypeMismatch; } -static ERROR setval_array(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) +static ERR setval_array(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) { FieldContext ctx(Object, Field); @@ -610,10 +611,10 @@ static ERROR setval_array(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG src_type = Flags & (FD_LONG|FD_LARGE|FD_FLOAT|FD_DOUBLE|FD_POINTER|FD_BYTE|FD_WORD|FD_STRUCT); if (src_type) { LONG dest_type = Field->Flags & (FD_LONG|FD_LARGE|FD_FLOAT|FD_DOUBLE|FD_POINTER|FD_BYTE|FD_WORD|FD_STRUCT); - if (!(src_type & dest_type)) return ERR_SetValueNotArray; + if (!(src_type & dest_type)) return ERR::SetValueNotArray; } - return ((ERROR (*)(APTR, APTR, LONG))(Field->SetValue))(Object, (APTR)Data, Elements); + return ((ERR (*)(APTR, APTR, LONG))(Field->SetValue))(Object, (APTR)Data, Elements); } else if (Flags & FD_STRING) { APTR arraybuffer; @@ -632,27 +633,27 @@ static ERROR setval_array(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, } else Elements = write_array((CSTRING)Data, Field->Flags, 0, arraybuffer); - auto error = ((ERROR (*)(APTR, APTR, LONG))(Field->SetValue))(Object, arraybuffer, Elements); + auto error = ((ERR (*)(APTR, APTR, LONG))(Field->SetValue))(Object, arraybuffer, Elements); free(arraybuffer); return error; } - else return ERR_AllocMemory; + else return ERR::AllocMemory; } else { pf::Log log(__FUNCTION__); log.warning("Arrays can only be set using the FD_ARRAY type."); - return ERR_SetValueNotArray; + return ERR::SetValueNotArray; } } -static ERROR setval_function(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) +static ERR setval_function(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) { OBJECTPTR caller = tlContext->object(); FieldContext ctx(Object, Field); if (Flags & FD_FUNCTION) { - return ((ERROR (*)(APTR, APTR))(Field->SetValue))(Object, (APTR)Data); + return ((ERR (*)(APTR, APTR))(Field->SetValue))(Object, (APTR)Data); } else if (Flags & FD_POINTER) { FUNCTION func; @@ -661,13 +662,13 @@ static ERROR setval_function(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Da func.StdC.Context = caller; func.StdC.Routine = (APTR)Data; } - else func.Type = CALL_NONE; - return ((ERROR (*)(APTR, FUNCTION *))(Field->SetValue))(Object, &func); + else func.clear(); + return ((ERR (*)(APTR, FUNCTION *))(Field->SetValue))(Object, &func); } - else return ERR_SetValueNotFunction; + else return ERR::SetValueNotFunction; } -static ERROR setval_long(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) +static ERR setval_long(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) { FieldContext ctx(Object, Field); @@ -676,12 +677,12 @@ static ERROR setval_long(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, else if (Flags & (FD_DOUBLE|FD_FLOAT)) int32 = F2I(*((DOUBLE *)Data)); else if (Flags & FD_STRING) int32 = strtol((STRING)Data, NULL, 0); else if (Flags & FD_LONG) int32 = *((LONG *)Data); - else return ERR_SetValueNotNumeric; + else return ERR::SetValueNotNumeric; - return ((ERROR (*)(APTR, LONG))(Field->SetValue))(Object, int32); + return ((ERR (*)(APTR, LONG))(Field->SetValue))(Object, int32); } -static ERROR setval_double(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) +static ERR setval_double(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) { FieldContext ctx(Object, Field); @@ -690,37 +691,37 @@ static ERROR setval_double(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data else if (Flags & FD_LARGE) float64 = (DOUBLE)(*((LARGE *)Data)); else if (Flags & FD_STRING) float64 = strtod((CSTRING)Data, NULL); else if (Flags & (FD_DOUBLE|FD_FLOAT)) float64 = *((DOUBLE *)Data); - else return ERR_SetValueNotNumeric; + else return ERR::SetValueNotNumeric; - return ((ERROR (*)(APTR, DOUBLE))(Field->SetValue))(Object, float64); + return ((ERR (*)(APTR, DOUBLE))(Field->SetValue))(Object, float64); } -static ERROR setval_pointer(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) +static ERR setval_pointer(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) { FieldContext ctx(Object, Field); if (Flags & (FD_POINTER|FD_STRING)) { - return ((ERROR (*)(APTR, CPTR ))(Field->SetValue))(Object, Data); + return ((ERR (*)(APTR, CPTR ))(Field->SetValue))(Object, Data); } else if (Flags & FD_LONG) { char buffer[32]; IntToStr(*((LONG *)Data), buffer, sizeof(buffer)); - return ((ERROR (*)(APTR, char *))(Field->SetValue))(Object, buffer); + return ((ERR (*)(APTR, char *))(Field->SetValue))(Object, buffer); } else if (Flags & FD_LARGE) { char buffer[64]; IntToStr(*((LARGE *)Data), buffer, sizeof(buffer)); - return ((ERROR (*)(APTR, char *))(Field->SetValue))(Object, buffer); + return ((ERR (*)(APTR, char *))(Field->SetValue))(Object, buffer); } else if (Flags & (FD_DOUBLE|FD_FLOAT)) { char buffer[64]; IntToStr(*((DOUBLE *)Data), buffer, sizeof(buffer)); - return ((ERROR (*)(APTR, char *))(Field->SetValue))(Object, buffer); + return ((ERR (*)(APTR, char *))(Field->SetValue))(Object, buffer); } - else return ERR_SetValueNotPointer; + else return ERR::SetValueNotPointer; } -static ERROR setval_large(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) +static ERR setval_large(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, LONG Elements) { LARGE int64; FieldContext ctx(Object, Field); @@ -729,9 +730,9 @@ static ERROR setval_large(OBJECTPTR Object, Field *Field, LONG Flags, CPTR Data, else if (Flags & (FD_DOUBLE|FD_FLOAT)) int64 = F2I(*((DOUBLE *)Data)); else if (Flags & FD_STRING) int64 = strtoll((CSTRING)Data, NULL, 0); else if (Flags & FD_LARGE) int64 = *((LARGE *)Data); - else return ERR_SetValueNotNumeric; + else return ERR::SetValueNotNumeric; - return ((ERROR (*)(APTR, LARGE))(Field->SetValue))(Object, int64); + return ((ERR (*)(APTR, LARGE))(Field->SetValue))(Object, int64); } //******************************************************************************************************************** diff --git a/src/core/lib_filesystem.cpp b/src/core/lib_filesystem.cpp index 3983dfdf9..610027a4d 100644 --- a/src/core/lib_filesystem.cpp +++ b/src/core/lib_filesystem.cpp @@ -180,30 +180,27 @@ extern "C" FFR CALL_FEEDBACK(FUNCTION *Callback, FileFeedback *Feedback) { if ((!Callback) or (!Feedback)) return FFR::OKAY; - if (Callback->Type IS CALL_STDC) { - auto routine = (FFR (*)(FileFeedback *))Callback->StdC.Routine; - return routine(Feedback); - } - else if (Callback->Type IS CALL_SCRIPT) { - if (auto script = Callback->Script.Script) { - const ScriptArg args[] = { - { "Size", Feedback->Size }, - { "Position", Feedback->Position }, - { "Path", Feedback->Path }, - { "Dest", Feedback->Dest }, - { "FeedbackID", LONG(Feedback->FeedbackID) } - }; - - ERROR error; - if (scCallback(script, Callback->Script.ProcedureID, args, ARRAYSIZE(args), &error)) error = ERR_Failed; - - if (!error) { - CSTRING *results; - LONG size; - if ((!GetFieldArray(script, FID_Results, (APTR *)&results, &size)) and (size > 0)) { - return FFR(StrToInt(results[0])); - } - else return FFR::OKAY; + if (Callback->isC()) { + auto routine = (FFR (*)(FileFeedback *, APTR))Callback->StdC.Routine; + return routine(Feedback, Callback->StdC.Meta); + } + else if (Callback->isScript()) { + const ScriptArg args[] = { + { "Size", Feedback->Size }, + { "Position", Feedback->Position }, + { "Path", Feedback->Path }, + { "Dest", Feedback->Dest }, + { "FeedbackID", LONG(Feedback->FeedbackID) } + }; + + ERR error; + if (scCallback(Callback->Script.Script, Callback->Script.ProcedureID, args, std::ssize(args), &error) != ERR::Okay) error = ERR::Failed; + + if (error IS ERR::Okay) { + CSTRING *results; + LONG size; + if ((GetFieldArray(Callback->Script.Script, FID_Results, (APTR *)&results, &size) IS ERR::Okay) and (size > 0)) { + return FFR(StrToInt(results[0])); } else return FFR::OKAY; } @@ -212,12 +209,11 @@ extern "C" FFR CALL_FEEDBACK(FUNCTION *Callback, FileFeedback *Feedback) else return FFR::OKAY; } -/********************************************************************************************************************* -** Cleans up path strings such as "../../myfile.txt". Note that for Linux, the targeted file/folder has to exist or -** NULL will be returned. -** -** The Path must be resolved to the native OS format. -*/ +//******************************************************************************************************************** +// Cleans up path strings such as "../../myfile.txt". Note that for Linux, the targeted file/folder has to exist or +// NULL will be returned. +// +// The Path must be resolved to the native OS format. static STRING cleaned_path(CSTRING Path) { @@ -271,7 +267,7 @@ const virtual_drive * get_fs(CSTRING Path) //******************************************************************************************************************** // Assigned to a timer for the purpose of checking up on the expiry of cached files. -ERROR check_cache(OBJECTPTR Subscriber, LARGE Elapsed, LARGE CurrentTime) +ERR check_cache(OBJECTPTR Subscriber, LARGE Elapsed, LARGE CurrentTime) { pf::Log log(__FUNCTION__); @@ -288,9 +284,9 @@ ERROR check_cache(OBJECTPTR Subscriber, LARGE Elapsed, LARGE CurrentTime) if (glCache.empty()) { glCacheTimer = 0; - return ERR_Terminate; + return ERR::Terminate; } - else return ERR_Okay; + else return ERR::Okay; } /********************************************************************************************************************* @@ -313,15 +309,15 @@ cstr Value: The value to associate with the tag name. If NULL, any existing tag *********************************************************************************************************************/ -ERROR AddInfoTag(FileInfo *Info, CSTRING Name, CSTRING Value) +ERR AddInfoTag(FileInfo *Info, CSTRING Name, CSTRING Value) { if (!Info->Tags) { Info->Tags = new (std::nothrow) std::unordered_map(); - if (!Info->Tags) return ERR_CreateResource; + if (!Info->Tags) return ERR::CreateResource; } Info->Tags[0][Name] = std::string(Value); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -357,18 +353,18 @@ Okay: The path was analysed and the result is stored in the Type variable. *********************************************************************************************************************/ -ERROR AnalysePath(CSTRING Path, LOC *PathType) +ERR AnalysePath(CSTRING Path, LOC *PathType) { pf::Log log(__FUNCTION__); if (PathType) *PathType = LOC::NIL; - if (!Path) return ERR_NullArgs; + if (!Path) return ERR::NullArgs; // Special volumes 'string:' and 'memory:' are considered to be file paths. - if (!StrCompare("string:", Path, 7)) { + if (StrCompare("string:", Path, 7) IS ERR::Okay) { if (PathType) *PathType = LOC::FILE; - return ERR_Okay; + return ERR::Okay; } log.traceBranch("%s", Path); @@ -385,31 +381,31 @@ ERROR AnalysePath(CSTRING Path, LOC *PathType) std::string path_vol(Path, len-1); if (glVolumes.contains(path_vol)) { if (PathType) *PathType = LOC::VOLUME; - return ERR_Okay; + return ERR::Okay; } } - return ERR_DoesNotExist; + return ERR::DoesNotExist; } STRING test_path; - if (!ResolvePath(Path, flags, &test_path)) { + if (ResolvePath(Path, flags, &test_path) IS ERR::Okay) { log.trace("Testing path type for '%s'", test_path); - ERROR error; + ERR error; auto vd = get_fs(test_path); if (vd->TestPath) { LOC dummy; if (!PathType) PathType = &dummy; // Dummy variable, helps to avoid bugs error = vd->TestPath(test_path, RSF::NIL, PathType); } - else error = ERR_NoSupport; + else error = ERR::NoSupport; FreeResource(test_path); return error; } else { log.trace("Path '%s' does not exist.", Path); - return ERR_DoesNotExist; + return ERR::DoesNotExist; } } @@ -420,7 +416,7 @@ CompareFilePaths: Checks if two file paths refer to the same physical file. This function will test two file paths, checking if they refer to the same file in a storage device. It uses a string comparison on the resolved path names, then attempts a second test based on an in-depth analysis of file attributes if -the string comparison fails. In the event of a match, `ERR_Okay` is returned. All other error codes indicate a +the string comparison fails. In the event of a match, `ERR::Okay` is returned. All other error codes indicate a mis-match or internal failure. The targeted paths do not have to refer to an existing file or folder in order to match (i.e. match on string @@ -438,17 +434,17 @@ NullArgs *********************************************************************************************************************/ -ERROR CompareFilePaths(CSTRING PathA, CSTRING PathB) +ERR CompareFilePaths(CSTRING PathA, CSTRING PathB) { - if ((!PathA) or (!PathB)) return ERR_NullArgs; + if ((!PathA) or (!PathB)) return ERR::NullArgs; STRING path1, path2; - ERROR error; - if ((error = ResolvePath(PathA, RSF::NO_FILE_CHECK, &path1))) { + ERR error; + if ((error = ResolvePath(PathA, RSF::NO_FILE_CHECK, &path1)) != ERR::Okay) { return error; } - if ((error = ResolvePath(PathB, RSF::NO_FILE_CHECK, &path2))) { + if ((error = ResolvePath(PathB, RSF::NO_FILE_CHECK, &path2)) != ERR::Okay) { FreeResource(path1); return error; } @@ -462,16 +458,16 @@ ERROR CompareFilePaths(CSTRING PathA, CSTRING PathB) } else error = StrCompare(path1, path2, 0, STR::MATCH_LEN|STR::MATCH_CASE); - if (error) { + if (error != ERR::Okay) { if (v1 IS v2) { // Ask the virtual FS if the paths match if (v1->SameFile) { error = v1->SameFile(path1, path2); } - else error = ERR_False; // Assume the earlier string comparison is good enough + else error = ERR::False; // Assume the earlier string comparison is good enough } - else error = ERR_False; + else error = ERR::False; } FreeResource(path1); @@ -481,7 +477,7 @@ ERROR CompareFilePaths(CSTRING PathA, CSTRING PathB) //******************************************************************************************************************** -ERROR fs_samefile(CSTRING Path1, CSTRING Path2) +ERR fs_samefile(CSTRING Path1, CSTRING Path2) { #ifdef __unix__ struct stat64 stat1, stat2; @@ -492,13 +488,13 @@ ERROR fs_samefile(CSTRING Path1, CSTRING Path2) and (stat1.st_mode IS stat2.st_mode) and (stat1.st_uid IS stat2.st_uid) and (stat1.st_gid IS stat2.st_gid)) { - return ERR_True; + return ERR::True; } - else return ERR_False; + else return ERR::False; } - else return ERR_False; + else return ERR::False; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -609,7 +605,7 @@ The Callback parameter can be set with a function that matches this prototype: For each file that is processed during the copy operation, a &FileFeedback structure is passed that describes the source file and its target. The callback must return a constant value that can potentially affect file processing. Valid values are `FFR::Okay` (copy the file), `FFR::Skip` (do not copy the file) and `FFR::Abort` (abort the process -completely and return `ERR_Cancelled` as an error code). +completely and return `ERR::Cancelled` as an error code). -INPUT- cstr Source: The source location. @@ -623,7 +619,7 @@ Failed: A failure occurred during the copy process. *********************************************************************************************************************/ -ERROR CopyFile(CSTRING Source, CSTRING Dest, FUNCTION *Callback) +ERR CopyFile(CSTRING Source, CSTRING Dest, FUNCTION *Callback) { return fs_copy(Source, Dest, Callback, FALSE); } @@ -639,7 +635,7 @@ you can link `documents:myfiles/newlink.txt` to `../readme.txt` or `folder/readm used when making references to parent folders. The permission flags for the link are inherited from the file that you are linking to. If the file location referenced -at From already exists as a file or folder, the function will fail with an ERR_FileExists error code. +at From already exists as a file or folder, the function will fail with an ERR::FileExists error code. This function does not automatically create folders in circumstances where new folders are required to complete the From link. You will need to call ~CreateFolder() to ensure that the necessary paths exist beforehand. If the @@ -663,17 +659,17 @@ FileExists: The location referenced at From already exists. *********************************************************************************************************************/ -ERROR CreateLink(CSTRING From, CSTRING To) +ERR CreateLink(CSTRING From, CSTRING To) { #ifdef _WIN32 - return ERR_NoSupport; + return ERR::NoSupport; #else pf::Log log(__FUNCTION__); - if ((!From) or (!To)) return ERR_NullArgs; + if ((!From) or (!To)) return ERR::NullArgs; log.branch("From: %.40s, To: %s", From, To); @@ -684,17 +680,17 @@ ERROR CreateLink(CSTRING From, CSTRING To) FreeResource(dest); FreeResource(src); - if (!err) return ERR_Okay; - else return convert_errno(err, ERR_Failed); + if (!err) return ERR::Okay; + else return convert_errno(err, ERR::Failed); } else { FreeResource(src); - return ERR_ResolvePath; + return ERR::ResolvePath; } } - else return ERR_ResolvePath; + else return ERR::ResolvePath; - return ERR_Okay; + return ERR::Okay; #endif } @@ -717,7 +713,7 @@ The Callback parameter can be set with a function that matches this prototype: Prior to the deletion of any file, a &FileFeedback structure is passed that describes the file's location. The callback must return a constant value that can potentially affect file processing. Valid values are `FFR::Okay` (delete -the file), `FFR::Skip` (do not delete the file) and `FFR::Abort` (abort the process completely and return `ERR_Cancelled` +the file), `FFR::Skip` (do not delete the file) and `FFR::Abort` (abort the process completely and return `ERR::Cancelled` as an error code). -INPUT- @@ -733,11 +729,11 @@ NoSupport: The filesystem driver does not support deletion. *********************************************************************************************************************/ -ERROR DeleteFile(CSTRING Path, FUNCTION *Callback) +ERR DeleteFile(CSTRING Path, FUNCTION *Callback) { pf::Log log(__FUNCTION__); - if (!Path) return ERR_NullArgs; + if (!Path) return ERR::NullArgs; log.branch("%s", Path); @@ -745,12 +741,12 @@ ERROR DeleteFile(CSTRING Path, FUNCTION *Callback) if (Path[len-1] IS ':') return DeleteVolume(Path); - ERROR error; + ERR error; STRING resolve; - if (!(error = ResolvePath(Path, RSF::NIL, &resolve))) { + if ((error = ResolvePath(Path, RSF::NIL, &resolve)) IS ERR::Okay) { const virtual_drive *vd = get_fs(resolve); if (vd->Delete) error = vd->Delete(resolve, NULL); - else error = ERR_NoSupport; + else error = ERR::NoSupport; FreeResource(resolve); } @@ -784,7 +780,7 @@ void SetDefaultPermissions(LONG User, LONG Group, PERMIT Permissions) glForceGID = Group; if (Permissions IS PERMIT(-1)) { // Prevent improper permission settings - log.warning(ERR_Args); + log.warning(ERR::Args); Permissions = PERMIT::NIL; } @@ -795,13 +791,13 @@ void SetDefaultPermissions(LONG User, LONG Group, PERMIT Permissions) // Internal function for getting information from files, particularly virtual volumes. If you know that a path // refers directly to the client's filesystem then you can revert to calling fs_getinfo() instead. -ERROR get_file_info(CSTRING Path, FileInfo *Info, LONG InfoSize) +ERR get_file_info(CSTRING Path, FileInfo *Info, LONG InfoSize) { pf::Log log(__FUNCTION__); LONG i, len; - ERROR error; + ERR error; - if ((!Path) or (!Path[0]) or (!Info) or (InfoSize <= 0)) return log.warning(ERR_Args); + if ((!Path) or (!Path[0]) or (!Info) or (InfoSize <= 0)) return log.warning(ERR::Args); char NameBuffer[MAX_FILENAME]; ClearMemory(Info, InfoSize); @@ -820,14 +816,14 @@ ERROR get_file_info(CSTRING Path, FileInfo *Info, LONG InfoSize) LONG pos = i; NameBuffer[i] = 0; - error = ERR_Okay; + error = ERR::Okay; if (auto lock = std::unique_lock{glmVolumes, 4s}) { if (glVolumes.contains(NameBuffer)) { if (glVolumes[NameBuffer]["Hidden"] == "Yes") Info->Flags |= RDF::HIDDEN; } } - else error = ERR_LockFailed; + else error = ERR::LockFailed; if (pos < MAX_FILENAME-2) { NameBuffer[pos++] = ':'; @@ -840,23 +836,23 @@ ERROR get_file_info(CSTRING Path, FileInfo *Info, LONG InfoSize) return error; } - else return log.warning(ERR_BufferOverflow); + else return log.warning(ERR::BufferOverflow); } log.traceBranch("%s", Path); STRING path; - if (!(error = ResolvePath(Path, RSF::NIL, &path))) { + if ((error = ResolvePath(Path, RSF::NIL, &path)) IS ERR::Okay) { auto vfs = get_fs(path); if (vfs->GetInfo) { if (vfs->is_virtual()) Info->Flags |= RDF::VIRTUAL; - if (!(error = vfs->GetInfo(path, Info, InfoSize))) { + if ((error = vfs->GetInfo(path, Info, InfoSize)) IS ERR::Okay) { Info->TimeStamp = calc_timestamp(&Info->Modified); } } - else log.warning(ERR_NoSupport); + else log.warning(ERR::NoSupport); FreeResource(path); } @@ -897,28 +893,27 @@ Search: If CHECK_EXISTS is specified, this failure indicates that the file is no *********************************************************************************************************************/ -ERROR LoadFile(CSTRING Path, LDF Flags, CacheFile **Cache) +ERR LoadFile(CSTRING Path, LDF Flags, CacheFile **Cache) { pf::Log log(__FUNCTION__); - if ((!Path) or (!Cache)) return ERR_NullArgs; + if ((!Path) or (!Cache)) return ERR::NullArgs; // Check if the file is already cached. If it is, check that the file hasn't been written since the last time it was cached. STRING path; - ERROR error; - if ((error = ResolvePath(Path, RSF::APPROXIMATE, &path)) != ERR_Okay) return error; + ERR error; + if ((error = ResolvePath(Path, RSF::APPROXIMATE, &path)) != ERR::Okay) return error; const std::lock_guard lock(glCacheLock); log.branch("%.80s, Flags: $%.8x", path, LONG(Flags)); - objFile::create file = { fl::Path(path), fl::Flags(FL::READ|FL::FILE) }; + auto file = objFile::create { fl::Path(path), fl::Flags(FL::READ|FL::FILE) }; if (file.ok()) { - LARGE timestamp, file_size; - file->get(FID_Size, &file_size); - file->get(FID_TimeStamp, ×tamp); + auto file_size = file->get(FID_Size); + auto timestamp = file->get(FID_TimeStamp); CacheFileIndex index(path, timestamp, file_size); @@ -927,14 +922,14 @@ ERROR LoadFile(CSTRING Path, LDF Flags, CacheFile **Cache) *((extCacheFile **)Cache) = &glCache[index]; if ((Flags & LDF::CHECK_EXISTS) IS LDF::NIL) glCache[index].Locks++; - return ERR_Okay; + return ERR::Okay; } // If the client just wanted to check for the existence of the file, do not proceed in loading it. if ((Flags & LDF::CHECK_EXISTS) != LDF::NIL) { FreeResource(path); - return ERR_Search; + return ERR::Search; } glCache.emplace(index, extCacheFile(path, file_size, timestamp)); @@ -942,23 +937,23 @@ ERROR LoadFile(CSTRING Path, LDF Flags, CacheFile **Cache) if (file_size) { LONG result; error = file->read(glCache[index].Data, file_size, &result); - if ((!error) and (file_size != result)) error = ERR_Read; + if ((error IS ERR::Okay) and (file_size != result)) error = ERR::Read; } - if (!error) { + if (error IS ERR::Okay) { *((extCacheFile **)Cache) = &glCache[index]; if (!glCacheTimer) { pf::SwitchContext context(CurrentTask()); - auto call = make_function_stdc(check_cache); + auto call = FUNCTION(check_cache); SubscribeTimer(60, &call, &glCacheTimer); } FreeResource(path); - return ERR_Okay; + return ERR::Okay; } } - else error = ERR_CreateObject; + else error = ERR::CreateObject; FreeResource(path); return error; @@ -991,11 +986,11 @@ NoSupport: Virtual file system does not support folder creation. *********************************************************************************************************************/ -ERROR CreateFolder(CSTRING Path, PERMIT Permissions) +ERR CreateFolder(CSTRING Path, PERMIT Permissions) { pf::Log log(__FUNCTION__); - if ((!Path) or (!*Path)) return log.warning(ERR_NullArgs); + if ((!Path) or (!*Path)) return log.warning(ERR::NullArgs); if (glDefaultPermissions != PERMIT::NIL) Permissions = glDefaultPermissions; else if ((Permissions IS PERMIT::NIL) or ((Permissions & PERMIT::INHERIT) != PERMIT::NIL)) { @@ -1003,14 +998,14 @@ ERROR CreateFolder(CSTRING Path, PERMIT Permissions) if (Permissions IS PERMIT::NIL) Permissions = PERMIT::READ|PERMIT::WRITE|PERMIT::EXEC|PERMIT::GROUP_READ|PERMIT::GROUP_WRITE|PERMIT::GROUP_EXEC; // If no permissions are set, give current user full access } - ERROR error; + ERR error; STRING resolve; - if (!(error = ResolvePath(Path, RSF::NO_FILE_CHECK, &resolve))) { + if ((error = ResolvePath(Path, RSF::NO_FILE_CHECK, &resolve)) IS ERR::Okay) { const virtual_drive *vd = get_fs(resolve); if (vd->CreateFolder) { error = vd->CreateFolder(resolve, Permissions); } - else error = ERR_NoSupport; + else error = ERR::NoSupport; FreeResource(resolve); } @@ -1050,7 +1045,7 @@ The Callback parameter can be set with a function that matches this prototype: For each file that is processed during the move operation, a &FileFeedback structure is passed that describes the source file and its target. The callback must return a constant value that can potentially affect file processing. Valid values are `FFR::Okay` (move the file), `FFR::Skip` (do not move the file) and `FFR::Abort` (abort the process -completely and return `ERR_Cancelled` as an error code). +completely and return `ERR::Cancelled` as an error code). -INPUT- cstr Source: The source path. @@ -1064,11 +1059,11 @@ Failed *********************************************************************************************************************/ -ERROR MoveFile(CSTRING Source, CSTRING Dest, FUNCTION *Callback) +ERR MoveFile(CSTRING Source, CSTRING Dest, FUNCTION *Callback) { pf::Log log(__FUNCTION__); - if ((!Source) or (!Dest)) return ERR_NullArgs; + if ((!Source) or (!Dest)) return ERR::NullArgs; log.branch("%s to %s", Source, Dest); return fs_copy(Source, Dest, Callback, TRUE); @@ -1103,14 +1098,14 @@ File *********************************************************************************************************************/ -ERROR ReadFileToBuffer(CSTRING Path, APTR Buffer, LONG BufferSize, LONG *BytesRead) +ERR ReadFileToBuffer(CSTRING Path, APTR Buffer, LONG BufferSize, LONG *BytesRead) { pf::Log log(__FUNCTION__); log.traceBranch("Path: %s, Buffer Size: %d", Path, BufferSize); #if defined(__unix__) || defined(_WIN32) - if ((!Path) or (BufferSize <= 0) or (!Buffer)) return ERR_Args; + if ((!Path) or (BufferSize <= 0) or (!Buffer)) return ERR::Args; bool approx; if (*Path IS '~') { @@ -1121,13 +1116,13 @@ ERROR ReadFileToBuffer(CSTRING Path, APTR Buffer, LONG BufferSize, LONG *BytesRe if (BytesRead) *BytesRead = 0; - ERROR error; + ERR error; STRING res_path; - if (!(error = ResolvePath(Path, RSF::CHECK_VIRTUAL | (approx ? RSF::APPROXIMATE : RSF::NIL), &res_path))) { - if (StrCompare("/dev/", res_path, 5) != ERR_Okay) { + if ((error = ResolvePath(Path, RSF::CHECK_VIRTUAL | (approx ? RSF::APPROXIMATE : RSF::NIL), &res_path)) IS ERR::Okay) { + if (StrCompare("/dev/", res_path, 5) != ERR::Okay) { if (auto handle = open(res_path, O_RDONLY|O_NONBLOCK|O_LARGEFILE|WIN32OPEN, NULL); handle != -1) { if (auto result = read(handle, Buffer, BufferSize); result IS -1) { - error = ERR_Read; + error = ERR::Read; #ifdef __unix__ log.warning("read(%s, %p, %d): %s", Path, Buffer, BufferSize, strerror(errno)); #endif @@ -1140,26 +1135,26 @@ ERROR ReadFileToBuffer(CSTRING Path, APTR Buffer, LONG BufferSize, LONG *BytesRe #ifdef __unix__ log.warning("open(%s): %s", Path, strerror(errno)); #endif - error = ERR_OpenFile; + error = ERR::OpenFile; } } - else error = ERR_InvalidPath; + else error = ERR::InvalidPath; FreeResource(res_path); } - else if (error IS ERR_VirtualVolume) { + else if (error IS ERR::VirtualVolume) { extFile::create file = { fl::Path(res_path), fl::Flags(FL::READ|FL::FILE|(approx ? FL::APPROXIMATE : FL::NIL)) }; if (file.ok()) { - if (!file->read(Buffer, BufferSize, BytesRead)) error = ERR_Okay; - else error = ERR_Read; + if (file->read(Buffer, BufferSize, BytesRead) IS ERR::Okay) error = ERR::Okay; + else error = ERR::Read; } - else error = ERR_File; + else error = ERR::File; FreeResource(res_path); return error; } - else error = ERR_FileNotFound; + else error = ERR::FileNotFound; #ifdef _DEBUG if (error) log.warning(error); @@ -1174,11 +1169,11 @@ ERROR ReadFileToBuffer(CSTRING Path, APTR Buffer, LONG BufferSize, LONG *BytesRe LONG result; if (!file->read(Buffer, BufferSize, &result)) { if (BytesRead) *BytesRead = result; - return ERR_Okay; + return ERR::Okay; } - else return ERR_Read; + else return ERR::Read; } - else return ERR_File; + else return ERR::File; #endif } @@ -1189,7 +1184,7 @@ ERROR ReadFileToBuffer(CSTRING Path, APTR Buffer, LONG BufferSize, LONG *BytesRe ReadInfoTag: Read a named tag from a FileInfo structure. Call ReadInfoTag() to retrieve the string value associated with a named tag in a FileInfo structure. The tag must -have been added with AddInfoTag() or `ERR_NotFound` will be returned. +have been added with AddInfoTag() or `ERR::NotFound` will be returned. -INPUT- struct(FileInfo) Info: Pointer to a valid FileInfo structure. @@ -1203,20 +1198,20 @@ cstr Name: The name of the tag. *********************************************************************************************************************/ -ERROR ReadInfoTag(FileInfo *Info, CSTRING Name, CSTRING *Value) +ERR ReadInfoTag(FileInfo *Info, CSTRING Name, CSTRING *Value) { if ((!Info) or (!Name) or (!Value)) { pf::Log log(__FUNCTION__); - return ERR_NullArgs; + return ERR::NullArgs; } if ((Info->Tags) and (Info->Tags->contains(Name))) { *Value = Info->Tags[0][Name].c_str(); - return ERR_Okay; + return ERR::Okay; } else *Value = NULL; - return ERR_NotFound; + return ERR::NotFound; } /********************************************************************************************************************* @@ -1224,7 +1219,7 @@ ERROR ReadInfoTag(FileInfo *Info, CSTRING Name, CSTRING *Value) ** large buffer as this function will modify it. */ -ERROR test_path(STRING Path, RSF Flags) +ERR test_path(STRING Path, RSF Flags) { pf::Log log(__FUNCTION__); LONG len; @@ -1234,19 +1229,19 @@ ERROR test_path(STRING Path, RSF Flags) struct stat64 info; #endif - if (!Path) return ERR_NullArgs; + if (!Path) return ERR::NullArgs; log.trace("%s", Path); if (auto vd = get_virtual(Path)) { if (vd->TestPath) { LOC type; - if (!vd->TestPath(Path, Flags, &type)) { - return ERR_Okay; + if (vd->TestPath(Path, Flags, &type) IS ERR::Okay) { + return ERR::Okay; } - else return ERR_FileNotFound; + else return ERR::FileNotFound; } - else return ERR_Okay; + else return ERR::Okay; } #ifdef _WIN32 @@ -1260,17 +1255,17 @@ ERROR test_path(STRING Path, RSF Flags) #ifdef __unix__ - if (len IS 1) return ERR_Okay; // Do not lstat() the root '/' folder + if (len IS 1) return ERR::Okay; // Do not lstat() the root '/' folder Path[len-1] = 0; LONG result = lstat64(Path, &info); Path[len-1] = '/'; - if (!result) return ERR_Okay; + if (!result) return ERR::Okay; #elif _WIN32 - if (winCheckDirectoryExists(Path)) return ERR_Okay; + if (winCheckDirectoryExists(Path)) return ERR::Okay; else log.trace("Folder does not exist."); #else @@ -1281,7 +1276,7 @@ ERROR test_path(STRING Path, RSF Flags) // This code handles testing for file locations if ((Flags & RSF::APPROXIMATE) != RSF::NIL) { - if (!findfile(Path)) return ERR_Okay; + if (findfile(Path) IS ERR::Okay) return ERR::Okay; } #ifdef __unix__ else if (!lstat64(Path, &info)) { @@ -1290,17 +1285,17 @@ ERROR test_path(STRING Path, RSF Flags) Path[len] = 0; } - return ERR_Okay; + return ERR::Okay; } #else else if (!access(Path, 0)) { - return ERR_Okay; + return ERR::Okay; } //else log.trace("access() failed."); #endif } - return ERR_FileNotFound; + return ERR::FileNotFound; } /********************************************************************************************************************* @@ -1343,7 +1338,7 @@ struct olddirent { char d_name[]; // file name (null-terminated) }; -ERROR findfile(STRING Path) +ERR findfile(STRING Path) { pf::Log log("FindFile"); struct stat64 info; @@ -1351,12 +1346,12 @@ ERROR findfile(STRING Path) LONG namelen, len; char save; - if ((!Path) or (Path[0] IS ':')) return ERR_Args; + if ((!Path) or (Path[0] IS ':')) return ERR::Args; // Return if the file exists at the specified Path and is not a folder if (lstat64(Path, &info) != -1) { - if (!S_ISDIR(info.st_mode)) return ERR_Okay; + if (!S_ISDIR(info.st_mode)) return ERR::Okay; } for (len=0; Path[len]; len++); @@ -1397,7 +1392,7 @@ ERROR findfile(STRING Path) } closedir(dir); - return ERR_Okay; + return ERR::Okay; } } @@ -1431,7 +1426,7 @@ ERROR findfile(STRING Path) } close(dir); - return ERR_Okay; + return ERR::Okay; } } } @@ -1442,21 +1437,21 @@ ERROR findfile(STRING Path) #endif - return ERR_Search; + return ERR::Search; } #elif _WIN32 -ERROR findfile(STRING Path) +ERR findfile(STRING Path) { - if ((!Path) or (Path[0] IS ':')) return ERR_Args; + if ((!Path) or (Path[0] IS ':')) return ERR::Args; // Find a file with the standard Path LONG filehandle; if ((filehandle = open(Path, O_RDONLY|O_LARGEFILE|WIN32OPEN, NULL)) != -1) { close(filehandle); - return ERR_Okay; + return ERR::Okay; } // Find a file with an extension @@ -1472,10 +1467,10 @@ ERROR findfile(STRING Path) while ((len > 0) and (Path[len-1] != ':') and (Path[len-1] != '/') and (Path[len-1] != '\\')) len--; StrCopy(buffer, Path+len); winFindClose(handle); - return ERR_Okay; + return ERR::Okay; } - return ERR_Search; + return ERR::Search; } #endif @@ -1542,7 +1537,7 @@ PERMIT convert_fs_permissions(LONG Permissions) //******************************************************************************************************************** // Strips the filename and calls CreateFolder() to create all paths leading up to the filename. -ERROR check_paths(CSTRING Path, PERMIT Permissions) +ERR check_paths(CSTRING Path, PERMIT Permissions) { pf::Log log(__FUNCTION__); log.traceBranch("%s", Path); @@ -1552,13 +1547,13 @@ ERROR check_paths(CSTRING Path, PERMIT Permissions) path.resize(i); return CreateFolder(path.c_str(), Permissions); } - else return ERR_Failed; + else return ERR::Failed; } //******************************************************************************************************************** // This low level function is used for copying/moving/renaming files and folders. -ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) +ERR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) { pf::Log log(Move ? "MoveFile" : "CopyFile"); #ifdef __unix__ @@ -1576,19 +1571,19 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) LONG srclen; char dest[2000]; bool srcdir; - ERROR error; + ERR error; - if ((!Source) or (!Source[0]) or (!Dest) or (!Dest[0])) return log.warning(ERR_NullArgs); + if ((!Source) or (!Source[0]) or (!Dest) or (!Dest[0])) return log.warning(ERR::NullArgs); log.traceBranch("\"%s\" to \"%s\"", Source, Dest); - if ((error = ResolvePath(Source, RSF::NIL, &src)) != ERR_Okay) { - return ERR_FileNotFound; + if ((error = ResolvePath(Source, RSF::NIL, &src)) != ERR::Okay) { + return ERR::FileNotFound; } - if ((error = ResolvePath(Dest, RSF::NO_FILE_CHECK, &tmp)) != ERR_Okay) { + if ((error = ResolvePath(Dest, RSF::NO_FILE_CHECK, &tmp)) != ERR::Okay) { FreeResource(src); - return ERR_ResolvePath; + return ERR::ResolvePath; } const virtual_drive *srcvirtual = get_fs(src); @@ -1615,16 +1610,16 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) } if ((size_t)destlen >= sizeof(dest)) { - error = ERR_BufferOverflow; + error = ERR::BufferOverflow; goto exit; } log.trace("Copy: %s TO %s", src, dest); - if (!CompareFilePaths(src, dest)) { + if (CompareFilePaths(src, dest) IS ERR::Okay) { log.trace("The source and destination refer to the same location."); - if (Move) return ERR_IdenticalPaths; // Move fails if source and dest are identical, since the source is not deleted - else return ERR_Okay; // Copy succeeds if source and dest are identical + if (Move) return ERR::IdenticalPaths; // Move fails if source and dest are identical, since the source is not deleted + else return ERR::Okay; // Copy succeeds if source and dest are identical } FileFeedback feedback; @@ -1650,7 +1645,7 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) } } else { - error = ERR_FileNotFound; + error = ERR::FileNotFound; goto exit; } @@ -1661,7 +1656,7 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) }; if (!destfile.ok()) { - error = ERR_CreateFile; + error = ERR::CreateFile; goto exit; } @@ -1672,7 +1667,7 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) if ((destfile->Flags & FL::FOLDER) IS FL::NIL) { // You cannot copy from a folder to a file - error = ERR_Mismatch; + error = ERR::Mismatch; goto exit; } @@ -1681,9 +1676,9 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) // Check if the copy would cause recursion - e.g. "/parasol/system/" to "/parasol/system/temp/". if (srclen <= destlen) { - if (StrCompare(src, dest, srclen) IS ERR_True) { + if (StrCompare(src, dest, srclen) IS ERR::True) { log.warning("The requested copy would cause recursion."); - error = ERR_Loop; + error = ERR::Loop; goto exit; } } @@ -1693,11 +1688,11 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) if (glDefaultPermissions != PERMIT::NIL) CreateFolder(dest, glDefaultPermissions); else CreateFolder(dest, PERMIT::USER|PERMIT::GROUP); - if (!(error = fs_copydir(srcbuffer, dest, &feedback, Callback, Move))) { + if ((error = fs_copydir(srcbuffer, dest, &feedback, Callback, Move)) IS ERR::Okay) { // Delete the source if we are moving folders if (Move) error = DeleteFile(srcbuffer, NULL); } - else log.warning("Folder copy process failed, error %d.", error); + else log.warning("Folder copy process failed, error %d.", LONG(error)); goto exit; } @@ -1713,14 +1708,14 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) // This routine is designed to handle streams - where either the source is a stream or the destination is a stream. APTR data; - error = ERR_Okay; - if (!AllocMemory(bufsize, MEM::DATA|MEM::NO_CLEAR, (APTR *)&data, NULL)) { + error = ERR::Okay; + if (AllocMemory(bufsize, MEM::DATA|MEM::NO_CLEAR, (APTR *)&data, NULL) IS ERR::Okay) { #define STREAM_TIMEOUT (10000LL) LARGE time = (PreciseTime() / 1000LL); while (srcfile->Position < srcfile->Size) { error = srcfile->read(data, bufsize, &len); - if (error) { + if (error != ERR::Okay) { log.warning("acRead() failed: %s", GetErrorMsg(error)); break; } @@ -1735,7 +1730,7 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) if ((PreciseTime() / 1000LL) - time > STREAM_TIMEOUT) { log.warning("Timeout - stopped reading at offset %" PF64 " of %" PF64 "", srcfile->Position, srcfile->Size); - error = ERR_TimeOut; + error = ERR::TimeOut; break; } } @@ -1744,15 +1739,15 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) while (len > 0) { LONG result; - if ((error = acWrite(*destfile, data, len, &result)) != ERR_Okay) { - error = ERR_Write; + if ((error = acWrite(*destfile, data, len, &result)) != ERR::Okay) { + error = ERR::Write; break; } if (result) time = (PreciseTime() / 1000LL); else if ((PreciseTime() / 1000LL) - time > STREAM_TIMEOUT) { log.warning("Timeout - failed to write remaining %d bytes.", len); - error = ERR_TimeOut; + error = ERR::TimeOut; break; } @@ -1762,21 +1757,21 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) } else if (len > 0) { log.warning("Out of space - wrote %d bytes, %d left.", result, len); - error = ERR_OutOfSpace; + error = ERR::OutOfSpace; break; } if (len > 0) ProcessMessages(PMF::NIL, 0); } - if (error) break; + if (error != ERR::Okay) break; if ((Callback) and (Callback->Type)) { if (feedback.Size < feedback.Position) feedback.Size = feedback.Position; FFR result = CALL_FEEDBACK(Callback, &feedback); - if (result IS FFR::ABORT) { error = ERR_Cancelled; break; } + if (result IS FFR::ABORT) { error = ERR::Cancelled; break; } else if (result IS FFR::SKIP) break; } @@ -1785,9 +1780,9 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) FreeResource(data); } - else error = log.warning(ERR_AllocMemory); + else error = log.warning(ERR::AllocMemory); - if ((Move) and (!error)) { + if ((Move) and (error IS ERR::Okay)) { flDelete(*srcfile, 0); } @@ -1815,29 +1810,29 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) if ((Callback) and (Callback->Type)) { FFR result = CALL_FEEDBACK(Callback, &feedback); - if (result IS FFR::ABORT) { error = ERR_Cancelled; goto exit; } - else if (result IS FFR::SKIP) { error = ERR_Okay; goto exit; } + if (result IS FFR::ABORT) { error = ERR::Cancelled; goto exit; } + else if (result IS FFR::SKIP) { error = ERR::Okay; goto exit; } } unlink(dest); // Remove any existing file first - if (!symlink(linkto, dest)) error = ERR_Okay; + if (!symlink(linkto, dest)) error = ERR::Okay; else { // On failure, it may be possible that precursing folders need to be created for the link. Do this here and then try // creating the link a second time. check_paths(dest, PERMIT::READ|PERMIT::WRITE|PERMIT::GROUP_READ|PERMIT::GROUP_WRITE); - if (!symlink(linkto, dest)) error = ERR_Okay; + if (!symlink(linkto, dest)) error = ERR::Okay; else { log.warning("Failed to create link \"%s\"", dest); - error = ERR_CreateFile; + error = ERR::CreateFile; } } } else { log.warning("Failed to read link \"%s\"", src); - error = ERR_Read; + error = ERR::Read; } if ((Move) and (!error)) { // Delete the source @@ -1854,11 +1849,11 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) // Attempt to move the source to the destination using a simple rename operation. If the rename fails, // the files may need to be copied across drives, so we don't abort in the case of failure. - error = ERR_Okay; + error = ERR::Okay; if ((Callback) and (Callback->Type)) { FFR result = CALL_FEEDBACK(Callback, &feedback); - if (result IS FFR::ABORT) { error = ERR_Cancelled; goto exit; } + if (result IS FFR::ABORT) { error = ERR::Cancelled; goto exit; } else if (result IS FFR::SKIP) goto exit; } @@ -1902,7 +1897,7 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) #ifdef _WIN32 if (winCheckDirectoryExists(src)); else { - error = ERR_File; + error = ERR::File; goto exit; } #else @@ -1911,7 +1906,7 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) closedir(dirhandle); } else { - error = ERR_File; + error = ERR::File; goto exit; } #endif @@ -1921,9 +1916,9 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) // Check if the copy would cause recursion - e.g. "/parasol/system/" to "/parasol/system/temp/". if (srclen <= destlen) { - if (StrCompare(src, dest, srclen) IS ERR_True) { + if (StrCompare(src, dest, srclen) IS ERR::True) { log.warning("The requested copy would cause recursion."); - error = ERR_Loop; + error = ERR::Loop; goto exit; } } @@ -1946,11 +1941,11 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) #endif } - if (!(error = fs_copydir(srcbuffer, dest, &feedback, Callback, Move))) { + if ((error = fs_copydir(srcbuffer, dest, &feedback, Callback, Move)) IS ERR::Okay) { // Delete the source if we are moving folders if (Move) error = DeleteFile(srcbuffer, NULL); } - else log.warning("Folder copy process failed, error %d.", error); + else log.warning("Folder copy process failed, error %d.", LONG(error)); goto exit; } @@ -1958,8 +1953,8 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) if (!Move) { // (If Move is enabled, we would have already sent feedback during the earlier rename() attempt if ((Callback) and (Callback->Type)) { FFR result = CALL_FEEDBACK(Callback, &feedback); - if (result IS FFR::ABORT) { error = ERR_Cancelled; goto exit; } - else if (result IS FFR::SKIP) { error = ERR_Okay; goto exit; } + if (result IS FFR::ABORT) { error = ERR::Cancelled; goto exit; } + else if (result IS FFR::SKIP) { error = ERR::Okay; goto exit; } } } @@ -2013,7 +2008,7 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) if (device->BytesFree - 1024LL <= feedback.Size) { close(handle); log.warning("Not enough space on device (%" PF64 "/%" PF64 " < %" PF64 ")", device->BytesFree, device->DeviceSize, (LARGE)feedback.Size); - error = ERR_OutOfSpace; + error = ERR::OutOfSpace; goto exit; } } @@ -2052,18 +2047,18 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) // Use a reasonably small read buffer so that we can provide continuous feedback LONG bufsize = ((Callback) and (Callback->Type)) ? 65536 : 524288; - error = ERR_Okay; - if (!AllocMemory(bufsize, MEM::DATA|MEM::NO_CLEAR, (APTR *)&data, NULL)) { + error = ERR::Okay; + if (AllocMemory(bufsize, MEM::DATA|MEM::NO_CLEAR, (APTR *)&data, NULL) IS ERR::Okay) { while ((len = read(handle, data, bufsize)) > 0) { LONG result; if ((result = write(dhandle, data, len)) IS -1) { - if (errno IS ENOSPC) error = log.warning(ERR_OutOfSpace); - else error = log.warning(ERR_Write); + if (errno IS ENOSPC) error = log.warning(ERR::OutOfSpace); + else error = log.warning(ERR::Write); break; } else if (result < len) { log.warning("Wrote %d of %d bytes.", result, len); - error = ERR_OutOfSpace; + error = ERR::OutOfSpace; break; } @@ -2071,19 +2066,19 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) feedback.Position += len; if (feedback.Size < feedback.Position) feedback.Size = feedback.Position; FFR result = CALL_FEEDBACK(Callback, &feedback); - if (result IS FFR::ABORT) { error = ERR_Cancelled; break; } + if (result IS FFR::ABORT) { error = ERR::Cancelled; break; } else if (result IS FFR::SKIP) break; } } if (len IS -1) { log.warning("Error reading source file."); - error = ERR_Read; + error = ERR::Read; } FreeResource(data); } - else error = log.warning(ERR_AllocMemory); + else error = log.warning(ERR::AllocMemory); #ifdef __unix__ // If the sticky bits were set, we need to set them again because Linux sneakily turns off those bits when a @@ -2096,13 +2091,13 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) close(dhandle); } - else error = log.warning(ERR_CreateFile); + else error = log.warning(ERR::CreateFile); close(handle); } - else error = log.warning(ERR_FileNotFound); + else error = log.warning(ERR::FileNotFound); - if ((Move) and (!error)) { // Delete the source + if ((Move) and (error IS ERR::Okay)) { // Delete the source error = DeleteFile(src, NULL); } @@ -2114,7 +2109,7 @@ ERROR fs_copy(CSTRING Source, CSTRING Dest, FUNCTION *Callback, BYTE Move) //******************************************************************************************************************** // Generic routine for copying folders, intended to be used in conjunction with fs_copy() -ERROR fs_copydir(STRING Source, STRING Dest, FileFeedback *Feedback, FUNCTION *Callback, BYTE Move) +ERR fs_copydir(STRING Source, STRING Dest, FileFeedback *Feedback, FUNCTION *Callback, BYTE Move) { pf::Log log("copy_file"); @@ -2138,9 +2133,9 @@ ERROR fs_copydir(STRING Source, STRING Dest, FileFeedback *Feedback, FUNCTION *C } DirInfo *dir; - ERROR error; - if (!(error = OpenDir(Source, RDF::FILE|RDF::FOLDER|RDF::PERMISSIONS, &dir))) { - while (!(error = ScanDir(dir))) { + ERR error; + if ((error = OpenDir(Source, RDF::FILE|RDF::FOLDER|RDF::PERMISSIONS, &dir)) IS ERR::Okay) { + while ((error = ScanDir(dir)) IS ERR::Okay) { FileInfo *file = dir->Info; if ((file->Flags & RDF::LINK) != RDF::NIL) { if ((vsrc->ReadLink) and (vdest->CreateLink)) { @@ -2151,19 +2146,19 @@ ERROR fs_copydir(STRING Source, STRING Dest, FileFeedback *Feedback, FUNCTION *C Feedback->Path = Source; Feedback->Dest = Dest; FFR result = CALL_FEEDBACK(Callback, Feedback); - if (result IS FFR::ABORT) { error = ERR_Cancelled; break; } + if (result IS FFR::ABORT) { error = ERR::Cancelled; break; } else if (result IS FFR::SKIP) continue; } STRING link; - if (!(error = vsrc->ReadLink(Source, &link))) { + if ((error = vsrc->ReadLink(Source, &link)) IS ERR::Okay) { DeleteFile(Dest, NULL); error = vdest->CreateLink(Dest, link); } } else { log.warning("Cannot copy linked file to destination."); - error = ERR_NoSupport; + error = ERR::NoSupport; } } else if ((file->Flags & RDF::FILE) != RDF::NIL) { @@ -2181,7 +2176,7 @@ ERROR fs_copydir(STRING Source, STRING Dest, FileFeedback *Feedback, FUNCTION *C Feedback->Path = Source; Feedback->Dest = Dest; FFR result = CALL_FEEDBACK(Callback, Feedback); - if (result IS FFR::ABORT) { error = ERR_Cancelled; break; } + if (result IS FFR::ABORT) { error = ERR::Cancelled; break; } else if (result IS FFR::SKIP) continue; } @@ -2192,12 +2187,12 @@ ERROR fs_copydir(STRING Source, STRING Dest, FileFeedback *Feedback, FUNCTION *C chown(Dest, (glForceUID != -1) ? glForceUID : file->UserID, (glForceGID != -1) ? glForceGID : file->GroupID); } #endif - if (error IS ERR_FileExists) error = ERR_Okay; + if (error IS ERR::FileExists) error = ERR::Okay; AdjustLogLevel(-1); // Copy everything under the folder to the destination - if (!error) { + if (error IS ERR::Okay) { StrCopy(file->Name, Source+srclen); fs_copydir(Source, Dest, Feedback, Callback, Move); } @@ -2210,7 +2205,7 @@ ERROR fs_copydir(STRING Source, STRING Dest, FileFeedback *Feedback, FUNCTION *C Dest[destlen] = 0; return error; } - else if (error IS ERR_DirEmpty) return ERR_Okay; + else if (error IS ERR::DirEmpty) return ERR::Okay; else { log.msg("Folder list failed for \"%s\"", Source); return error; @@ -2241,7 +2236,7 @@ PERMIT get_parent_permissions(CSTRING Path, LONG *UserID, LONG *GroupID) folder[i+1] = 0; FileInfo info; - if ((i > 0) and (!get_file_info(folder, &info, sizeof(info)))) { + if ((i > 0) and (get_file_info(folder, &info, sizeof(info)) IS ERR::Okay)) { //log.msg("%s [$%.8x]", Path, info.Permissions); if (UserID) *UserID = info.UserID; if (GroupID) *GroupID = info.GroupID; @@ -2272,7 +2267,7 @@ BYTE strip_folder(STRING Path) //******************************************************************************************************************** -ERROR fs_readlink(STRING Source, STRING *Link) +ERR fs_readlink(STRING Source, STRING *Link) { #ifdef __unix__ char buffer[512]; @@ -2281,34 +2276,34 @@ ERROR fs_readlink(STRING Source, STRING *Link) if ((i = readlink(Source, buffer, sizeof(buffer)-1)) != -1) { buffer[i] = 0; *Link = StrClone(buffer); - return ERR_Okay; + return ERR::Okay; } - else return ERR_Failed; + else return ERR::Failed; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } //******************************************************************************************************************** -ERROR fs_createlink(CSTRING Target, CSTRING Link) +ERR fs_createlink(CSTRING Target, CSTRING Link) { #ifdef __unix__ if (symlink(Link, Target) IS -1) { - return convert_errno(errno, ERR_CreateFile); + return convert_errno(errno, ERR::CreateFile); } - else return ERR_Okay; + else return ERR::Okay; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } //******************************************************************************************************************** // NB: The path that is received is already resolved. -ERROR fs_delete(STRING Path, FUNCTION *Callback) +ERR fs_delete(STRING Path, FUNCTION *Callback) { - ERROR error; + ERR error; LONG len; for (len=0; Path[len]; len++); @@ -2329,7 +2324,7 @@ ERROR fs_delete(STRING Path, FUNCTION *Callback) error = delete_tree(buffer, sizeof(buffer), Callback, &feedback); #else if (!unlink(Path)) { // unlink() works if the folder is empty - error = ERR_Okay; + error = ERR::Okay; } else if (errno IS EISDIR) { FileFeedback feedback; @@ -2345,7 +2340,7 @@ ERROR fs_delete(STRING Path, FUNCTION *Callback) error = delete_tree(buffer, sizeof(buffer), Callback, &feedback); } - else error = convert_errno(errno, ERR_Failed); + else error = convert_errno(errno, ERR::Failed); #endif return error; @@ -2353,7 +2348,7 @@ ERROR fs_delete(STRING Path, FUNCTION *Callback) //******************************************************************************************************************** -ERROR fs_scandir(DirInfo *Dir) +ERR fs_scandir(DirInfo *Dir) { #ifdef __unix__ struct dirent *de; @@ -2363,7 +2358,7 @@ ERROR fs_scandir(DirInfo *Dir) char pathbuf[256]; LONG path_end = StrCopy(Dir->prvResolvedPath, pathbuf, sizeof(pathbuf)); - if ((size_t)path_end >= sizeof(pathbuf)-12) return(ERR_BufferOverflow); + if ((size_t)path_end >= sizeof(pathbuf)-12) return(ERR::BufferOverflow); if (pathbuf[path_end-1] != '/') pathbuf[path_end++] = '/'; while ((de = readdir((DIR *)Dir->prvHandle))) { @@ -2436,7 +2431,7 @@ ERROR fs_scandir(DirInfo *Dir) file->Created.Minute = local->tm_min; file->Created.Second = local->tm_sec; } - return ERR_Okay; + return ERR::Okay; } #elif _WIN32 @@ -2464,19 +2459,19 @@ ERROR fs_scandir(DirInfo *Dir) Dir->Info->Flags |= RDF::FILE|RDF::SIZE|RDF::DATE; } - return ERR_Okay; + return ERR::Okay; } #else #error Platform requires support for ScanDir(); #endif - return ERR_DirEmpty; + return ERR::DirEmpty; } //******************************************************************************************************************** -ERROR fs_opendir(DirInfo *Info) +ERR fs_opendir(DirInfo *Info) { pf::Log log(__FUNCTION__); @@ -2486,9 +2481,9 @@ ERROR fs_opendir(DirInfo *Info) if ((Info->prvHandle = opendir(Info->prvResolvedPath))) { rewinddir((DIR *)Info->prvHandle); - return ERR_Okay; + return ERR::Okay; } - else return ERR_InvalidPath; + else return ERR::InvalidPath; #elif _WIN32 @@ -2498,9 +2493,9 @@ ERROR fs_opendir(DirInfo *Info) str[Info->prvResolveLen++] = 0; Info->prvHandle = (WINHANDLE)-1; // No handle is required for windows until ScanDir() is called. TODO: See winScan() - we should probably call FindFirstFile() here to ensure that the folder exists and initialise the search. - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_BufferOverflow); + else return log.warning(ERR::BufferOverflow); #else #error Platform requires support for OpenDir() @@ -2509,7 +2504,7 @@ ERROR fs_opendir(DirInfo *Info) //******************************************************************************************************************** -ERROR fs_closedir(DirInfo *Dir) +ERR fs_closedir(DirInfo *Dir) { pf::Log log(__FUNCTION__); @@ -2545,19 +2540,19 @@ ERROR fs_closedir(DirInfo *Dir) } } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -ERROR fs_rename(STRING CurrentPath, STRING NewPath) +ERR fs_rename(STRING CurrentPath, STRING NewPath) { - return ERR_NoSupport; + return ERR::NoSupport; } //******************************************************************************************************************** -ERROR fs_testpath(CSTRING Path, RSF Flags, LOC *Type) +ERR fs_testpath(CSTRING Path, RSF Flags, LOC *Type) { LOC type; @@ -2565,12 +2560,12 @@ ERROR fs_testpath(CSTRING Path, RSF Flags, LOC *Type) if (Path[len-1] IS ':') { STRING str; - if (!ResolvePath(Path, RSF::NIL, &str)) { + if (ResolvePath(Path, RSF::NIL, &str) IS ERR::Okay) { if (Type) *Type = LOC::VOLUME; FreeResource(str); - return ERR_Okay; + return ERR::Okay; } - else return ERR_DoesNotExist; + else return ERR::DoesNotExist; } #ifdef __unix__ @@ -2591,14 +2586,14 @@ ERROR fs_testpath(CSTRING Path, RSF Flags, LOC *Type) if (type != LOC::NIL) { if (Type) *Type = type; - return ERR_Okay; + return ERR::Okay; } - else return ERR_DoesNotExist; + else return ERR::DoesNotExist; } //******************************************************************************************************************** -ERROR fs_getinfo(CSTRING Path, FileInfo *Info, LONG InfoSize) +ERR fs_getinfo(CSTRING Path, FileInfo *Info, LONG InfoSize) { pf::Log log(__FUNCTION__); @@ -2607,14 +2602,14 @@ ERROR fs_getinfo(CSTRING Path, FileInfo *Info, LONG InfoSize) char path_ref[256]; LONG len = StrCopy(Path, path_ref, sizeof(path_ref)); - if ((size_t)len >= sizeof(path_ref)-1) return ERR_BufferOverflow; + if ((size_t)len >= sizeof(path_ref)-1) return ERR::BufferOverflow; if ((path_ref[len-1] IS '/') or (path_ref[len-1] IS '\\')) path_ref[len-1] = 0; // Get the file info. Use lstat64() and if it turns out that the file is a symbolic link, set the RDF::LINK flag // and then switch to stat64(). struct stat64 info; - if (lstat64(path_ref, &info) IS -1) return ERR_FileNotFound; + if (lstat64(path_ref, &info) IS -1) return ERR::FileNotFound; Info->Flags = RDF::NIL; @@ -2679,7 +2674,7 @@ ERROR fs_getinfo(CSTRING Path, FileInfo *Info, LONG InfoSize) LONG i, len; Info->Flags = RDF::NIL; - if (!winFileInfo(Path, &Info->Size, &Info->Modified, &dir)) return ERR_File; + if (!winFileInfo(Path, &Info->Size, &Info->Modified, &dir)) return ERR::File; // TimeStamp has to match that produced by GET_TimeStamp @@ -2725,17 +2720,17 @@ ERROR fs_getinfo(CSTRING Path, FileInfo *Info, LONG InfoSize) #endif - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -ERROR fs_getdeviceinfo(CSTRING Path, objStorageDevice *Info) +ERR fs_getdeviceinfo(CSTRING Path, objStorageDevice *Info) { pf::Log log("GetDeviceInfo"); STRING location; - ERROR error; + ERR error; // Device information is stored in the SystemVolumes object @@ -2763,7 +2758,7 @@ ERROR fs_getdeviceinfo(CSTRING Path, objStorageDevice *Info) } } } - else return log.warning(ERR_SystemLocked); + else return log.warning(ERR::SystemLocked); if (Info->DeviceFlags IS DEVICE::NIL) { // Unable to find a device reference for the volume, so try to resolve the path and try again. @@ -2780,9 +2775,9 @@ ERROR fs_getdeviceinfo(CSTRING Path, objStorageDevice *Info) resolve = NULL; } else { - if (ResolvePath(Path, RSF::NO_FILE_CHECK, &resolve) != ERR_Okay) { + if (ResolvePath(Path, RSF::NO_FILE_CHECK, &resolve) != ERR::Okay) { if (resolve) FreeResource(resolve); - return ERR_ResolvePath; + return ERR::ResolvePath; } Path = resolve; @@ -2804,26 +2799,26 @@ ERROR fs_getdeviceinfo(CSTRING Path, objStorageDevice *Info) LARGE bytes_avail, total_size; if (!location) error = ResolvePath(Path, RSF::NO_FILE_CHECK, &location); - else error = ERR_Okay; + else error = ERR::Okay; - if (!error) { + if (error IS ERR::Okay) { if (!(winGetFreeDiskSpace(location[0], &bytes_avail, &total_size))) { log.msg("Failed to read location \"%s\" (from \"%s\")", location, Path); Info->BytesFree = -1; Info->BytesUsed = 0; Info->DeviceSize = -1; FreeResource(location); - return ERR_Okay; // Even though the disk space calculation failed, we succeeded on resolving other device information + return ERR::Okay; // Even though the disk space calculation failed, we succeeded on resolving other device information } else { Info->BytesFree = bytes_avail; Info->BytesUsed = total_size - bytes_avail; Info->DeviceSize = total_size; FreeResource(location); - return ERR_Okay; + return ERR::Okay; } } - else error = ERR_ResolvePath; + else error = ERR::ResolvePath; if (location) FreeResource(location); return log.warning(error); @@ -2834,7 +2829,7 @@ ERROR fs_getdeviceinfo(CSTRING Path, objStorageDevice *Info) if (!location) { error = ResolvePath(Path, RSF::NO_FILE_CHECK, &location); } - else error = ERR_Okay; + else error = ERR::Okay; if (!error) { struct statfs fstat; @@ -2858,26 +2853,26 @@ ERROR fs_getdeviceinfo(CSTRING Path, objStorageDevice *Info) if (Info->BytesFree < 1) Info->BytesFree = 0; if (Info->BytesUsed < 1) Info->BytesUsed = 0; if (Info->DeviceSize < 1) Info->DeviceSize = 0; - return ERR_Okay; + return ERR::Okay; } - else return log.warning(convert_errno(errno, ERR_File)); + else return log.warning(convert_errno(errno, ERR::File)); } - else return log.warning(ERR_ResolvePath); + else return log.warning(ERR::ResolvePath); } else { Info->BytesFree = -1; Info->DeviceSize = -1; Info->BytesUsed = 0; - return ERR_Okay; + return ERR::Okay; } #endif - return ERR_NoSupport; + return ERR::NoSupport; } //******************************************************************************************************************** -ERROR fs_makedir(CSTRING Path, PERMIT Permissions) +ERR fs_makedir(CSTRING Path, PERMIT Permissions) { pf::Log log(__FUNCTION__); @@ -2901,7 +2896,7 @@ ERROR fs_makedir(CSTRING Path, PERMIT Permissions) if (errno IS EEXIST) { log.msg("A folder or file already exists at \"%s\"", Path); - return ERR_FileExists; + return ERR::FileExists; } // This loop will go through the complete path attempting to create multiple folders. @@ -2924,7 +2919,7 @@ ERROR fs_makedir(CSTRING Path, PERMIT Permissions) if (Path[i]) { log.warning("Failed to create folder \"%s\".", Path); - return ERR_Failed; + return ERR::Failed; } else if (Path[i-1] != '/') { // If the path did not end with a slash, there is still one last folder to create @@ -2932,7 +2927,7 @@ ERROR fs_makedir(CSTRING Path, PERMIT Permissions) log.msg("%s", buffer.get()); if (((err = mkdir(buffer.get(), secureflags)) IS -1) and (errno != EEXIST)) { log.warning("Failed to create folder \"%s\".", Path); - return convert_errno(errno, ERR_SystemCall); + return convert_errno(errno, ERR::SystemCall); } if (!err) { if ((glForceUID != -1) or (glForceGID != -1)) chown(buffer.get(), glForceUID, glForceGID); @@ -2945,16 +2940,15 @@ ERROR fs_makedir(CSTRING Path, PERMIT Permissions) if (secureflags & (S_ISUID|S_ISGID)) chmod(Path, secureflags); } - return ERR_Okay; + return ERR::Okay; #elif _WIN32 - ERROR error; LONG i; - if ((error = winCreateDir(Path))) { + if (auto error = winCreateDir(Path); error != ERR::Okay) { auto buffer = std::make_unique(StrLength(Path)+1); - if (error IS ERR_FileExists) return ERR_FileExists; + if (error IS ERR::FileExists) return ERR::FileExists; // This loop will go through the complete path attempting to create multiple folders. @@ -2971,11 +2965,11 @@ ERROR fs_makedir(CSTRING Path, PERMIT Permissions) if (Path[i]) { log.traceWarning("Failed to create folder \"%s\".", Path); - return ERR_Failed; + return ERR::Failed; } } - return ERR_Okay; + return ERR::Okay; #endif } @@ -2983,20 +2977,20 @@ ERROR fs_makedir(CSTRING Path, PERMIT Permissions) #ifdef __ANDROID__ // The Android release does not keep an associations.cfg file. -ERROR load_datatypes(void) +ERR load_datatypes(void) { pf::Log log(__FUNCTION__); if (!glDatatypes) { if (!(glDatatypes = objConfig::create::untracked(fl::Path("user:config/locale.cfg")))) { - return log.warning(ERR_CreateObject); + return log.warning(ERR::CreateObject); } } - return ERR_Okay; + return ERR::Okay; } #else -ERROR load_datatypes(void) +ERR load_datatypes(void) { pf::Log log(__FUNCTION__); FileInfo info; @@ -3007,14 +3001,14 @@ ERROR load_datatypes(void) if (!glDatatypes) { reload = true; - if (!get_file_info("config:users/associations.cfg", &info, sizeof(info))) { + if (get_file_info("config:users/associations.cfg", &info, sizeof(info)) IS ERR::Okay) { user_ts = info.TimeStamp; } - else return log.warning(ERR_FileDoesNotExist); + else return log.warning(ERR::FileDoesNotExist); } else { reload = false; - if (!get_file_info("config:users/associations.cfg", &info, sizeof(info))) { + if (get_file_info("config:users/associations.cfg", &info, sizeof(info)) IS ERR::Okay) { if (user_ts != info.TimeStamp) { user_ts = info.TimeStamp; reload = true; @@ -3028,10 +3022,10 @@ ERROR load_datatypes(void) if (glDatatypes) FreeResource(glDatatypes); glDatatypes = cfg; } - else return log.warning(ERR_CreateObject); + else return log.warning(ERR::CreateObject); } - return ERR_Okay; + return ERR::Okay; } #endif @@ -3040,14 +3034,14 @@ ERROR load_datatypes(void) #ifdef __unix__ -ERROR delete_tree(STRING Path, LONG Size, FUNCTION *Callback, FileFeedback *Feedback) +ERR delete_tree(STRING Path, LONG Size, FUNCTION *Callback, FileFeedback *Feedback) { pf::Log log(__FUNCTION__); struct dirent *direntry; LONG len; DIR *dummydir, *stream; struct stat64 info; - ERROR error; + ERR error; log.trace("Path: %s", Path); @@ -3056,11 +3050,11 @@ ERROR delete_tree(STRING Path, LONG Size, FUNCTION *Callback, FileFeedback *Feed FFR result = CALL_FEEDBACK(Callback, Feedback); if (result IS FFR::ABORT) { log.trace("Feedback requested abort at file '%s'", Path); - return ERR_Cancelled; + return ERR::Cancelled; } else if (result IS FFR::SKIP) { log.trace("Feedback requested skip at file '%s'", Path); - return ERR_Okay; + return ERR::Okay; } } @@ -3070,9 +3064,9 @@ ERROR delete_tree(STRING Path, LONG Size, FUNCTION *Callback, FileFeedback *Feed if (S_ISLNK(info.st_mode)) { if (unlink(Path)) { log.error("unlink() failed on symbolic link '%s'", Path); - return convert_errno(errno, ERR_SystemCall); + return convert_errno(errno, ERR::SystemCall); } - else return ERR_Okay; + else return ERR::Okay; } } @@ -3080,7 +3074,7 @@ ERROR delete_tree(STRING Path, LONG Size, FUNCTION *Callback, FileFeedback *Feed for (len=0; Path[len]; len++); Path[len] = '/'; - error = ERR_Okay; + error = ERR::Okay; rewinddir(stream); while ((direntry = readdir(stream))) { if ((direntry->d_name[0] IS '.') and (direntry->d_name[1] IS 0)); @@ -3089,8 +3083,8 @@ ERROR delete_tree(STRING Path, LONG Size, FUNCTION *Callback, FileFeedback *Feed StrCopy(direntry->d_name, Path+len+1, Size-len-1); if ((dummydir = opendir(Path))) { closedir(dummydir); - if (delete_tree(Path, Size, Callback, Feedback) IS ERR_Cancelled) { - error = ERR_Cancelled; + if (delete_tree(Path, Size, Callback, Feedback) IS ERR::Cancelled) { + error = ERR::Cancelled; break; } } @@ -3098,7 +3092,7 @@ ERROR delete_tree(STRING Path, LONG Size, FUNCTION *Callback, FileFeedback *Feed // Delete a file within the folder if (unlink(Path)) { log.error("unlink() failed on '%s'", Path); - error = convert_errno(errno, ERR_SystemCall); + error = convert_errno(errno, ERR::SystemCall); break; } } @@ -3110,14 +3104,14 @@ ERROR delete_tree(STRING Path, LONG Size, FUNCTION *Callback, FileFeedback *Feed if ((!error) and (rmdir(Path))) { log.error("rmdir(%s) error: %s", Path, strerror(errno)); - return convert_errno(errno, ERR_SystemCall); + return convert_errno(errno, ERR::SystemCall); } return error; } else { log.error("Failed to open folder \"%s\" using opendir().", Path); - return convert_errno(errno, ERR_SystemCall); + return convert_errno(errno, ERR::SystemCall); } } diff --git a/src/core/lib_functions.cpp b/src/core/lib_functions.cpp index f600bee20..3b61caebf 100644 --- a/src/core/lib_functions.cpp +++ b/src/core/lib_functions.cpp @@ -118,12 +118,12 @@ cstr: A human readable string for the error code is returned. By default error *********************************************************************************************************************/ -CSTRING GetErrorMsg(ERROR Code) +CSTRING GetErrorMsg(ERR Code) { - if ((Code < glTotalMessages) and (Code > 0)) { - return glMessages[Code]; + if ((LONG(Code) < glTotalMessages) and (LONG(Code) > 0)) { + return glMessages[LONG(Code)]; } - else if (!Code) return "Operation successful."; + else if (Code IS ERR::Okay) return "Operation successful."; else return "Unknown error code."; } @@ -490,7 +490,7 @@ LARGE GetResource(RES Resource) if (cpu_mhz) return cpu_mhz; - objFile::create file = { fl::Path("drive1:proc/cpuinfo"), fl::Flags(FL::READ|FL::BUFFER) }; + auto file = objFile::create { fl::Path("drive1:proc/cpuinfo"), fl::Flags(FL::READ|FL::BUFFER) }; if (file.ok()) { while ((line = flReadLine(*file))) { @@ -618,9 +618,9 @@ NoSupport: The host platform does not support file descriptors. *********************************************************************************************************************/ #ifdef _WIN32 -ERROR RegisterFD(HOSTHANDLE FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR), APTR Data) +ERR RegisterFD(HOSTHANDLE FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR), APTR Data) #else -ERROR RegisterFD(LONG FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR), APTR Data) +ERR RegisterFD(LONG FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR), APTR Data) #endif { pf::Log log(__FUNCTION__); @@ -628,15 +628,15 @@ ERROR RegisterFD(LONG FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR), APTR Dat // Note that FD's < -1 are permitted for the registering of functions marked with RFD::ALWAYS_CALL #ifdef _WIN32 - if (FD IS (HOSTHANDLE)-1) return log.warning(ERR_Args); - if ((Flags & RFD::SOCKET) != RFD::NIL) return log.warning(ERR_NoSupport); // In MS Windows, socket handles are managed as window messages (see Network module's Windows code) + if (FD IS (HOSTHANDLE)-1) return log.warning(ERR::Args); + if ((Flags & RFD::SOCKET) != RFD::NIL) return log.warning(ERR::NoSupport); // In MS Windows, socket handles are managed as window messages (see Network module's Windows code) #else - if (FD IS -1) return log.warning(ERR_Args); + if (FD IS -1) return log.warning(ERR::Args); #endif if (glFDProtected) { // Cache the request while glFDTable is in use. glRegisterFD.emplace_back(FD, Routine, Data, Flags); - return ERR_Okay; + return ERR::Okay; } if ((Flags & RFD::REMOVE) != RFD::NIL) { @@ -649,7 +649,7 @@ ERROR RegisterFD(LONG FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR), APTR Dat } else it++; } - return ERR_Okay; + return ERR::Okay; } if ((Flags & (RFD::READ|RFD::WRITE|RFD::EXCEPT|RFD::REMOVE|RFD::ALWAYS_CALL)) IS RFD::NIL) Flags |= RFD::READ; @@ -659,7 +659,7 @@ ERROR RegisterFD(LONG FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR), APTR Dat fd.Routine = Routine; fd.Flags = Flags; fd.Data = Data; - return ERR_Okay; + return ERR::Okay; } } @@ -672,7 +672,7 @@ ERROR RegisterFD(LONG FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR), APTR Dat #endif glFDTable.emplace_back(FD, Routine, Data, Flags); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -694,7 +694,7 @@ cstr Path: The new location to set for the resource path. *********************************************************************************************************************/ -ERROR SetResourcePath(RP PathType, CSTRING Path) +ERR SetResourcePath(RP PathType, CSTRING Path) { pf::Log log(__FUNCTION__); @@ -712,7 +712,7 @@ ERROR SetResourcePath(RP PathType, CSTRING Path) #endif } } - return ERR_Okay; + return ERR::Okay; case RP::SYSTEM_PATH: if (Path) { @@ -725,7 +725,7 @@ ERROR SetResourcePath(RP PathType, CSTRING Path) #endif } } - return ERR_Okay; + return ERR::Okay; case RP::MODULE_PATH: // An alternative path to the system modules. This was introduced for Android, which holds the module binaries in the assets folders. if (Path) { @@ -738,10 +738,10 @@ ERROR SetResourcePath(RP PathType, CSTRING Path) #endif } } - return ERR_Okay; + return ERR::Okay; default: - return ERR_Args; + return ERR::Args; } } @@ -808,10 +808,10 @@ LARGE SetResource(RES Resource, LARGE Value) #ifdef __unix__ log.trace("Privileged User: %s, Current UID: %d, Depth: %d", (Value) ? "TRUE" : "FALSE", geteuid(), privileged); - if (glPrivileged) return ERR_Okay; // In privileged mode, the user is always an admin + if (glPrivileged) return ERR::Okay; // In privileged mode, the user is always an admin if (Value) { // Enable admin privileges - oldvalue = ERR_Okay; + oldvalue = ERR::Okay; if (!privileged) { if (glUID) { if (glUID != glEUID) { @@ -820,7 +820,7 @@ LARGE SetResource(RES Resource, LARGE Value) } else { log.msg("Admin privileges not available."); - oldvalue = ERR_Failed; // Admin privileges are not available + oldvalue = ERR::Failed; // Admin privileges are not available } } else privileged++;; // The user already has admin privileges @@ -837,7 +837,7 @@ LARGE SetResource(RES Resource, LARGE Value) } } #else - return ERR_Okay; + return LARGE(ERR::Okay); #endif break; @@ -855,12 +855,12 @@ SubscribeTimer: Subscribes an object or function to the timer service. This function creates a new timer subscription that will be called at regular intervals for the calling object. -A callback function must be provided that follows this prototype: `ERROR Function(OBJECTPTR Subscriber, LARGE Elapsed, LARGE CurrentTime)` +A callback function must be provided that follows this prototype: `ERR Function(OBJECTPTR Subscriber, LARGE Elapsed, LARGE CurrentTime)` The Elapsed parameter is the total number of microseconds that have elapsed since the last call. The CurrentTime parameter is set to the ~PreciseTime() value just prior to the Callback being called. The callback function -can return `ERR_Terminate` at any time to cancel the subscription. All other error codes are ignored. Fluid callbacks -should call `check(ERR_Terminate)` to perform the equivalent of this behaviour. +can return `ERR::Terminate` at any time to cancel the subscription. All other error codes are ignored. Fluid callbacks +should call `check(ERR::Terminate)` to perform the equivalent of this behaviour. To change the interval, call ~UpdateTimer() with the new value. To release a timer subscription, call ~UpdateTimer() with the resulting SubscriptionID and an Interval of zero. @@ -885,18 +885,18 @@ InvalidState: The subscriber is marked for termination. *********************************************************************************************************************/ -ERROR SubscribeTimer(DOUBLE Interval, FUNCTION *Callback, APTR *Subscription) +ERR SubscribeTimer(DOUBLE Interval, FUNCTION *Callback, APTR *Subscription) { pf::Log log(__FUNCTION__); - if ((!Interval) or (!Callback)) return log.warning(ERR_NullArgs); - if (Interval < 0) return log.warning(ERR_Args); + if ((!Interval) or (!Callback)) return log.warning(ERR::NullArgs); + if (Interval < 0) return log.warning(ERR::Args); auto subscriber = tlContext->object(); - if (subscriber->collecting()) return log.warning(ERR_InvalidState); + if (subscriber->collecting()) return log.warning(ERR::InvalidState); - if (Callback->Type IS CALL_SCRIPT) log.msg(VLF::BRANCH|VLF::FUNCTION|VLF::DEBUG, "Interval: %.3fs", Interval); - else log.msg(VLF::BRANCH|VLF::FUNCTION|VLF::DEBUG, "Callback: %p, Interval: %.3fs", Callback->StdC.Routine, Interval); + if (Callback->Type IS CALL_SCRIPT) log.msg(VLF::BRANCH|VLF::FUNCTION|VLF::DETAIL, "Interval: %.3fs", Interval); + else log.msg(VLF::BRANCH|VLF::FUNCTION|VLF::DETAIL, "Callback: %p, Interval: %.3fs", Callback->StdC.Routine, Interval); if (auto lock = std::unique_lock{glmTimer, 200ms}) { auto usInterval = LARGE(Interval * 1000000.0); // Scale the interval to microseconds @@ -923,9 +923,9 @@ ERROR SubscribeTimer(DOUBLE Interval, FUNCTION *Callback, APTR *Subscription) subscriber->Flags |= NF::TIMER_SUB; if (Subscription) *Subscription = &*it; - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_SystemLocked); + else return log.warning(ERR::SystemLocked); } /********************************************************************************************************************* @@ -948,13 +948,13 @@ double Interval: The new interval for the timer (measured in seconds), or zero t *********************************************************************************************************************/ -ERROR UpdateTimer(APTR Subscription, DOUBLE Interval) +ERR UpdateTimer(APTR Subscription, DOUBLE Interval) { pf::Log log(__FUNCTION__); - if (!Subscription) return log.warning(ERR_NullArgs); + if (!Subscription) return log.warning(ERR::NullArgs); - log.msg(VLF::EXTAPI|VLF::BRANCH|VLF::FUNCTION, "Subscription: %p, Interval: %.4f", Subscription, Interval); + log.msg(VLF::DETAIL|VLF::BRANCH|VLF::FUNCTION, "Subscription: %p, Interval: %.4f", Subscription, Interval); if (auto lock = std::unique_lock{glmTimer, 200ms}) { auto timer = (CoreTimer *)Subscription; @@ -962,25 +962,25 @@ ERROR UpdateTimer(APTR Subscription, DOUBLE Interval) // Special mode: Preserve existing timer settings for the subscriber (ticker values are not reset etc) auto usInterval = -(LARGE(Interval * 1000000.0)); if (usInterval < timer->Interval) timer->Interval = usInterval; - return ERR_Okay; + return ERR::Okay; } else if (Interval > 0) { auto usInterval = LARGE(Interval * 1000000.0); timer->Interval = usInterval; timer->NextCall = PreciseTime() + usInterval; - return ERR_Okay; + return ERR::Okay; } else { if (timer->Locked) { // A timer can't be removed during its execution, but we can nullify the function entry // and ProcessMessages() will automatically terminate it on the next cycle. timer->Routine.Type = 0; - return log.warning(ERR_AlreadyLocked); + return log.warning(ERR::AlreadyLocked); } lock.release(); - if (timer->Routine.Type IS CALL_SCRIPT) { + if (timer->Routine.isScript()) { scDerefProcedure(timer->Routine.Script.Script, &timer->Routine); } @@ -991,10 +991,10 @@ ERROR UpdateTimer(APTR Subscription, DOUBLE Interval) } } - return ERR_Okay; + return ERR::Okay; } } - else return log.warning(ERR_SystemLocked); + else return log.warning(ERR::SystemLocked); } /********************************************************************************************************************* @@ -1006,7 +1006,7 @@ This function waits for a period of time as specified by the Seconds and MicroSe task will continue to process incoming messages in order to prevent the process' message queue from developing a back-log. -WaitTime() can return earlier than the indicated timeout if a message handler returns `ERR_Terminate`, or if a +WaitTime() can return earlier than the indicated timeout if a message handler returns `ERR::Terminate`, or if a `MSGID_QUIT` message is sent to the task's message queue. -INPUT- @@ -1042,7 +1042,7 @@ void WaitTime(LONG Seconds, LONG MicroSeconds) LARGE current = PreciseTime() / 1000LL; LARGE end = current + (Seconds * 1000) + (MicroSeconds / 1000); do { - if (ProcessMessages(PMF::NIL, end - current) IS ERR_Terminate) break; + if (ProcessMessages(PMF::NIL, end - current) IS ERR::Terminate) break; current = (PreciseTime() / 1000LL); } while (current < end); } diff --git a/src/core/lib_locking.cpp b/src/core/lib_locking.cpp index eb77219e6..58ae0fa74 100644 --- a/src/core/lib_locking.cpp +++ b/src/core/lib_locking.cpp @@ -52,12 +52,12 @@ static std::mutex glWaitLockMutex; ** Used by AccessMemory() and LockObject() */ -ERROR init_sleep(LONG OtherThreadID, LONG ResourceID, LONG ResourceType) +ERR init_sleep(LONG OtherThreadID, LONG ResourceID, LONG ResourceType) { //log.trace("Sleeping on thread %d for resource #%d, Total Threads: %d", OtherThreadID, ResourceID, LONG(glWaitLocks.size())); auto our_thread = get_thread_id(); - if (OtherThreadID IS our_thread) return ERR_Args; + if (OtherThreadID IS our_thread) return ERR::Args; const std::lock_guard lock(glWaitLockMutex); @@ -77,7 +77,7 @@ ERROR init_sleep(LONG OtherThreadID, LONG ResourceID, LONG ResourceType) if (glWaitLocks[i].WaitingForThreadID IS our_thread) { pf::Log log(__FUNCTION__); log.warning("Deadlock: Thread %d holds resource #%d and is waiting for us (%d) to release #%d.", glWaitLocks[i].ThreadID, ResourceID, our_thread, glWaitLocks[i].WaitingForResourceID); - return ERR_DeadLock; + return ERR::DeadLock; } } } @@ -90,7 +90,7 @@ ERROR init_sleep(LONG OtherThreadID, LONG ResourceID, LONG ResourceType) glWaitLocks[glWLIndex].Lock = get_threadlock(); #endif - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -150,7 +150,7 @@ WINHANDLE get_threadlock(void) if (index >= ARRAYSIZE(glThreadLocks)) index = glThreadLockIndex = 1; // Has the array reached exhaustion? If so, we need to wrap it. if (!glThreadLocks[index]) { WINHANDLE lock; - if (!alloc_public_waitlock(&lock, NULL)) { + if (alloc_public_waitlock(&lock, NULL) IS ERR::Okay) { glThreadLocks[index] = lock; // For resource tracking. tlThreadLock = lock; log.trace("Allocated thread-lock #%d for thread #%d", index, get_thread_id()); @@ -216,12 +216,12 @@ MemoryDoesNotExist: The MemoryID that you supplied does not refer to an existing *********************************************************************************************************************/ -ERROR AccessMemory(MEMORYID MemoryID, MEM Flags, LONG MilliSeconds, APTR *Result) +ERR AccessMemory(MEMORYID MemoryID, MEM Flags, LONG MilliSeconds, APTR *Result) { pf::Log log(__FUNCTION__); - if ((!MemoryID) or (!Result)) return log.warning(ERR_NullArgs); - if (MilliSeconds <= 0) return log.warning(ERR_Args); + if ((!MemoryID) or (!Result)) return log.warning(ERR::NullArgs); + if (MilliSeconds <= 0) return log.warning(ERR::Args); // NB: Logging AccessMemory() calls is usually a waste of time unless the process is going to sleep. //log.trace("MemoryID: %d, Flags: $%x, TimeOut: %d", MemoryID, LONG(Flags), MilliSeconds); @@ -240,11 +240,11 @@ ERROR AccessMemory(MEMORYID MemoryID, MEM Flags, LONG MilliSeconds, APTR *Result auto current_time = PreciseTime(); if (!end_time) end_time = (current_time / 1000LL) + MilliSeconds; auto timeout = end_time - (current_time / 1000LL); - if (timeout <= 0) return log.warning(ERR_TimeOut); + if (timeout <= 0) return log.warning(ERR::TimeOut); else { //log.msg("Sleep on memory #%d, Access %d, Threads %d/%d", MemoryID, mem->second.AccessCount, (LONG)mem->second.ThreadLockID, our_thread); if (cvResources.wait_for(glmMemory, std::chrono::milliseconds{timeout}) IS std::cv_status::timeout) { - return log.warning(ERR_TimeOut); + return log.warning(ERR::TimeOut); } } } @@ -254,13 +254,13 @@ ERROR AccessMemory(MEMORYID MemoryID, MEM Flags, LONG MilliSeconds, APTR *Result tlPrivateLockCount++; *Result = mem->second.Address; - return ERR_Okay; + return ERR::Okay; } else log.traceWarning("Cannot find memory ID #%d", MemoryID); // This is not uncommon, so trace only } - else return log.warning(ERR_SystemLocked); + else return log.warning(ERR::SystemLocked); - return ERR_MemoryDoesNotExist; + return ERR::MemoryDoesNotExist; } /********************************************************************************************************************* @@ -273,8 +273,8 @@ This function resolves an object ID to its address and acquires a lock on the ob it simultaneously. If the object is already locked, it will wait until the object becomes available. This must occur within the amount -of time specified in the Milliseconds parameter. If the time expires, the function will return with an `ERR_TimeOut` -error code. If successful, `ERR_Okay` is returned and a reference to the object's address is stored in the Result +of time specified in the Milliseconds parameter. If the time expires, the function will return with an `ERR::TimeOut` +error code. If successful, `ERR::Okay` is returned and a reference to the object's address is stored in the Result variable. It is crucial that calls to AccessObject() are followed with a call to ~ReleaseObject() once the lock is no @@ -309,32 +309,32 @@ SystemLocked *********************************************************************************************************************/ -ERROR AccessObject(OBJECTID ObjectID, LONG MilliSeconds, OBJECTPTR *Result) +ERR AccessObject(OBJECTID ObjectID, LONG MilliSeconds, OBJECTPTR *Result) { pf::Log log(__FUNCTION__); - if ((!Result) or (!ObjectID)) return log.warning(ERR_NullArgs); - if (MilliSeconds <= 0) log.warning(ERR_Args); // Warn but do not fail + if ((!Result) or (!ObjectID)) return log.warning(ERR::NullArgs); + if (MilliSeconds <= 0) log.warning(ERR::Args); // Warn but do not fail if (auto lock = std::unique_lock{glmMemory}) { auto mem = glPrivateMemory.find(ObjectID); if ((mem != glPrivateMemory.end()) and (mem->second.Address)) { - if (auto error = LockObject((OBJECTPTR)mem->second.Address, MilliSeconds); !error) { + if (auto error = LockObject((OBJECTPTR)mem->second.Address, MilliSeconds); error IS ERR::Okay) { *Result = (OBJECTPTR)mem->second.Address; - return ERR_Okay; + return ERR::Okay; } else return error; } else if (ObjectID IS glMetaClass.UID) { // Access to the MetaClass requires this special case handler. - if (auto error = LockObject(&glMetaClass, MilliSeconds); !error) { + if (auto error = LockObject(&glMetaClass, MilliSeconds); error IS ERR::Okay) { *Result = &glMetaClass; - return ERR_Okay; + return ERR::Okay; } else return error; } - else return ERR_NoMatchingObject; + else return ERR::NoMatchingObject; } - else return log.warning(ERR_SystemLocked); + else return log.warning(ERR::SystemLocked); } /********************************************************************************************************************* @@ -366,13 +366,13 @@ int MilliSeconds: The total number of milliseconds to wait before giving up. If *********************************************************************************************************************/ -ERROR LockObject(OBJECTPTR Object, LONG Timeout) +ERR LockObject(OBJECTPTR Object, LONG Timeout) { pf::Log log(__FUNCTION__); if (!Object) { DEBUG_BREAK - return log.warning(ERR_NullArgs); + return log.warning(ERR::NullArgs); } auto our_thread = get_thread_id(); @@ -385,11 +385,11 @@ ERROR LockObject(OBJECTPTR Object, LONG Timeout) if (++Object->Queue IS 1) { Object->Locked = true; Object->ThreadID = our_thread; - return ERR_Okay; + return ERR::Okay; } if (our_thread IS Object->ThreadID) { // Support nested locks. - return ERR_Okay; + return ERR::Okay; } // Problem: If a ReleaseObject() were to occur inside this while loop, it receives a queue value of 1 instead of @@ -398,7 +398,7 @@ ERROR LockObject(OBJECTPTR Object, LONG Timeout) // object is free. By not sleeping, we don't have to be concerned about the missing signal. } while (--Object->Queue IS 0); // Make a correction because we didn't obtain the lock. Repeat loop if the object lock is at zero (available). - if (Object->defined(NF::FREE|NF::FREE_ON_UNLOCK)) return ERR_MarkedForDeletion; // If the object is currently being removed by another thread, sleeping on it is pointless. + if (Object->defined(NF::FREE|NF::FREE_ON_UNLOCK)) return ERR::MarkedForDeletion; // If the object is currently being removed by another thread, sleeping on it is pointless. // Problem: What if ReleaseObject() in another thread were to release the object prior to our glmObjectLocking lock? This means that we would never receive the wake signal. // Solution: Prior to wait_until(), increment the object queue to attempt a lock. This is *slightly* less efficient than doing it after the cond_wait(), but @@ -413,8 +413,8 @@ ERROR LockObject(OBJECTPTR Object, LONG Timeout) if (auto lock = std::unique_lock{glmObjectLocking, std::chrono::milliseconds(Timeout)}) { //log.function("TID: %d, Sleeping on #%d, Timeout: %d, Queue: %d, Locked By: %d", our_thread, Object->UID, Timeout, Object->Queue, Object->ThreadID); - ERROR error = ERR_TimeOut; - if (!init_sleep(Object->ThreadID, Object->UID, RT_OBJECT)) { // Indicate that our thread is sleeping. + ERR error = ERR::TimeOut; + if (init_sleep(Object->ThreadID, Object->UID, RT_OBJECT) IS ERR::Okay) { // Indicate that our thread is sleeping. while ((current_time = (PreciseTime() / 1000LL)) < end_time) { auto tmout = end_time - current_time; if (tmout < 0) tmout = 0; @@ -422,7 +422,7 @@ ERROR LockObject(OBJECTPTR Object, LONG Timeout) if (glWaitLocks[glWLIndex].Flags & WLF_REMOVED) { glWaitLocks[glWLIndex].notWaiting(); Object->SleepQueue--; - return ERR_DoesNotExist; + return ERR::DoesNotExist; } if (++Object->Queue IS 1) { // Increment the lock count - also doubles as a prv_access() call if the lock value is 1. @@ -430,7 +430,7 @@ ERROR LockObject(OBJECTPTR Object, LONG Timeout) Object->Locked = false; Object->ThreadID = our_thread; Object->SleepQueue--; - return ERR_Okay; + return ERR::Okay; } else --Object->Queue; @@ -442,23 +442,23 @@ ERROR LockObject(OBJECTPTR Object, LONG Timeout) if (glWaitLocks[glWLIndex].Flags & WLF_REMOVED) { pf::Log log(__FUNCTION__); log.warning("TID %d: The resource no longer exists.", get_thread_id()); - error = ERR_DoesNotExist; + error = ERR::DoesNotExist; } else { log.traceWarning("TID: %d, #%d, Timeout occurred.", our_thread, Object->UID); - error = ERR_TimeOut; + error = ERR::TimeOut; } glWaitLocks[glWLIndex].notWaiting(); } - else error = log.error(ERR_Failed); + else error = log.error(ERR::Failed); Object->SleepQueue--; return error; } else { Object->SleepQueue--; - return ERR_SystemLocked; + return ERR::SystemLocked; } } @@ -484,11 +484,11 @@ SystemLocked *********************************************************************************************************************/ -ERROR ReleaseMemory(MEMORYID MemoryID) +ERR ReleaseMemory(MEMORYID MemoryID) { pf::Log log(__FUNCTION__); - if (!MemoryID) return log.warning(ERR_NullArgs); + if (!MemoryID) return log.warning(ERR::NullArgs); std::lock_guard lock(glmMemory); auto mem = glPrivateMemory.find(MemoryID); @@ -496,7 +496,7 @@ ERROR ReleaseMemory(MEMORYID MemoryID) if ((mem IS glPrivateMemory.end()) or (!mem->second.Address)) { // Sanity check; this should never happen if (tlContext->object()->Class) log.warning("Unable to find a record for memory address #%d [Context %d, Class %s].", MemoryID, tlContext->object()->UID, tlContext->object()->className()); else log.warning("Unable to find a record for memory #%d.", MemoryID); - return ERR_Search; + return ERR::Search; } WORD access; @@ -520,7 +520,7 @@ ERROR ReleaseMemory(MEMORYID MemoryID) cvResources.notify_all(); // Wake up any threads sleeping on this memory block. } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* diff --git a/src/core/lib_log.cpp b/src/core/lib_log.cpp index 630fcace3..d0cebf14d 100644 --- a/src/core/lib_log.cpp +++ b/src/core/lib_log.cpp @@ -17,8 +17,7 @@ Log levels are: 3 Application log message, level 1 4 INFO Application log message, level 2 5 API Top-level API messages, e.g. function entry points (default) -6 EXTAPI Extended API messages. For messages within functions, and entry-points for minor functions. -7 DEBUG More detailed API messages. +6 DETAIL Detailed API messages. For messages within functions, and entry-points for minor functions. 8 TRACE Extremely detailed API messages suitable for intensive debugging only. 9 Noisy debug messages that will appear frequently, e.g. being used in inner loops. @@ -134,10 +133,10 @@ void VLogF(VLF Flags, CSTRING Header, CSTRING Message, va_list Args) VLF::INFO|VLF::WARNING|VLF::ERROR|VLF::CRITICAL, VLF::INFO|VLF::WARNING|VLF::ERROR|VLF::CRITICAL, VLF::API|VLF::INFO|VLF::WARNING|VLF::ERROR|VLF::CRITICAL, - VLF::EXTAPI|VLF::API|VLF::INFO|VLF::WARNING|VLF::ERROR|VLF::CRITICAL, - VLF::DEBUG|VLF::EXTAPI|VLF::API|VLF::INFO|VLF::WARNING|VLF::ERROR|VLF::CRITICAL, - VLF::TRACE|VLF::DEBUG|VLF::EXTAPI|VLF::API|VLF::INFO|VLF::WARNING|VLF::ERROR|VLF::CRITICAL, - VLF::TRACE|VLF::DEBUG|VLF::EXTAPI|VLF::API|VLF::INFO|VLF::WARNING|VLF::ERROR|VLF::CRITICAL + VLF::DETAIL|VLF::API|VLF::INFO|VLF::WARNING|VLF::ERROR|VLF::CRITICAL, + VLF::DETAIL|VLF::API|VLF::INFO|VLF::WARNING|VLF::ERROR|VLF::CRITICAL, + VLF::TRACE|VLF::DETAIL|VLF::API|VLF::INFO|VLF::WARNING|VLF::ERROR|VLF::CRITICAL, + VLF::TRACE|VLF::DETAIL|VLF::API|VLF::INFO|VLF::WARNING|VLF::ERROR|VLF::CRITICAL }; if ((Flags & VLF::CRITICAL) != VLF::NIL) { // Print the message irrespective of the log level @@ -213,7 +212,7 @@ void VLogF(VLF Flags, CSTRING Header, CSTRING Message, va_list Args) // If no header is provided, make one to match the current context auto ctx = tlContext; - auto obj = tlContext->object(); + auto obj = ctx->object(); if (ctx->Action > 0) action = ActionTable[ctx->Action].Name; else if (ctx->Action < 0) { if (obj->Class) action = ((extMetaClass *)obj->Class)->Methods[-ctx->Action].Name; @@ -265,8 +264,7 @@ void VLogF(VLF Flags, CSTRING Header, CSTRING Message, va_list Args) } if (obj->Class) { - if (obj->Name[0]) name = obj->Name; - else name = obj->Class->ClassName; + name = obj->Name[0] ? obj->Name : obj->Class->ClassName; if (glLogLevel > 5) { if (ctx->Field) { @@ -309,7 +307,7 @@ FuncError: Sends basic error messages to the application log. Status: Internal This function outputs a message to the application log. It uses the codes listed in the system/errors.h file to -display the correct string to the user. The following example `FuncError(ERR_Write)` would produce input such +display the correct string to the user. The following example `FuncError(ERR::Write)` would produce input such as the following: `WriteFile: Error writing data to file.`. Notice that the Header parameter is not provided in the example. It is not necessary to supply this parameter in @@ -324,7 +322,7 @@ error: Returns the same code that was specified in the Error parameter. *********************************************************************************************************************/ -ERROR FuncError(CSTRING Header, ERROR Code) +ERR FuncError(CSTRING Header, ERR Code) { if (tlLogStatus <= 0) return Code; if (glLogLevel < 2) return Code; @@ -372,11 +370,11 @@ ERROR FuncError(CSTRING Header, ERROR Code) CSTRING name = obj->Name[0] ? obj->Name : obj->Class->ClassName; if (ctx->Field) { - fprintf(stderr, "%s%s[%s:%d:%s] %s%s\n", histart, msgheader, name, obj->UID, ctx->Field->Name, glMessages[Code], hiend); + fprintf(stderr, "%s%s[%s:%d:%s] %s%s\n", histart, msgheader, name, obj->UID, ctx->Field->Name, glMessages[LONG(Code)], hiend); } - else fprintf(stderr, "%s%s[%s:%d] %s%s\n", histart, msgheader, name, obj->UID, glMessages[Code], hiend); + else fprintf(stderr, "%s%s[%s:%d] %s%s\n", histart, msgheader, name, obj->UID, glMessages[LONG(Code)], hiend); } - else fprintf(stderr, "%s%s%s%s\n", histart, msgheader, glMessages[Code], hiend); + else fprintf(stderr, "%s%s%s%s\n", histart, msgheader, glMessages[LONG(Code)], hiend); #if defined(__unix__) && !defined(__ANDROID__) if (glSync) { fflush(0); fsync(STDERR_FILENO); } diff --git a/src/core/lib_memory.cpp b/src/core/lib_memory.cpp index a48e1b9ff..c31948b9b 100644 --- a/src/core/lib_memory.cpp +++ b/src/core/lib_memory.cpp @@ -73,13 +73,13 @@ AccessMemory: The block was allocated but access to it was not granted, causing *********************************************************************************************************************/ -ERROR AllocMemory(LONG Size, MEM Flags, APTR *Address, MEMORYID *MemoryID) +ERR AllocMemory(LONG Size, MEM Flags, APTR *Address, MEMORYID *MemoryID) { pf::Log log(__FUNCTION__); if ((Size <= 0) or ((!Address) and (!MemoryID))) { log.warning("Bad args - Size %d, Address %p, MemoryID %p", Size, Address, MemoryID); - return ERR_Args; + return ERR::Args; } if (MemoryID) *MemoryID = 0; @@ -106,7 +106,7 @@ ERROR AllocMemory(LONG Size, MEM Flags, APTR *Address, MEMORYID *MemoryID) if (!start_mem) { log.warning("Could not allocate %d bytes.", Size); - return ERR_AllocMemory; + return ERR::AllocMemory; } APTR data_start = (char *)start_mem + sizeof(LONG) + sizeof(LONG); // Skip MEMH and unique ID. @@ -146,9 +146,9 @@ ERROR AllocMemory(LONG Size, MEM Flags, APTR *Address, MEMORYID *MemoryID) if ((MemoryID) and (Address)) { if ((Flags & MEM::NO_LOCK) != MEM::NIL) *Address = data_start; - else if (AccessMemory(unique_id, MEM::READ_WRITE, 2000, Address) != ERR_Okay) { + else if (AccessMemory(unique_id, MEM::READ_WRITE, 2000, Address) != ERR::Okay) { log.warning("Memory block %d stolen during allocation!", *MemoryID); - return ERR_AccessMemory; + return ERR::AccessMemory; } *MemoryID = unique_id; } @@ -158,11 +158,11 @@ ERROR AllocMemory(LONG Size, MEM Flags, APTR *Address, MEMORYID *MemoryID) } if (glShowPrivate) log.pmsg("AllocMemory(%p/#%d, %d, $%.8x, Owner: #%d)", data_start, unique_id, Size, LONG(Flags), object_id); - return ERR_Okay; + return ERR::Okay; } else { freemem(start_mem); - return ERR_SystemLocked; + return ERR::SystemLocked; } } @@ -183,12 +183,12 @@ False: The block does not exist. *********************************************************************************************************************/ -ERROR CheckMemoryExists(MEMORYID MemoryID) +ERR CheckMemoryExists(MEMORYID MemoryID) { if (auto lock = std::unique_lock{glmMemory}) { - if (glPrivateMemory.contains(MemoryID)) return ERR_True; + if (glPrivateMemory.contains(MemoryID)) return ERR::True; } - return ERR_False; + return ERR::False; } /********************************************************************************************************************* @@ -219,7 +219,7 @@ MemoryDoesNotExist *********************************************************************************************************************/ -ERROR FreeResource(MEMORYID MemoryID) +ERR FreeResource(MEMORYID MemoryID) { pf::Log log(__FUNCTION__); @@ -229,7 +229,7 @@ ERROR FreeResource(MEMORYID MemoryID) auto &mem = it->second; if (glShowPrivate) log.branch("FreeResource(#%d, %p, Size: %d, $%.8x, Owner: #%d)", MemoryID, mem.Address, mem.Size, LONG(mem.Flags), mem.OwnerID); - ERROR error = ERR_Okay; + ERR error = ERR::Okay; if (mem.AccessCount > 0) { log.msg("Private memory ID #%d marked for deletion (open count %d).", MemoryID, mem.AccessCount); mem.Flags |= MEM::DELETE; @@ -242,9 +242,9 @@ ERROR FreeResource(MEMORYID MemoryID) start_mem -= sizeof(ResourceManager *); if (!glCrashStatus) { // Resource managers are not considered safe in an uncontrolled shutdown auto rm = ((ResourceManager **)start_mem)[0]; - if (rm->Free((APTR)mem.Address) IS ERR_InUse) { + if (rm->Free((APTR)mem.Address) IS ERR::InUse) { // Memory block is in use - the manager will be entrusted to handle this situation appropriately. - return ERR_Okay; + return ERR::Okay; } } } @@ -253,12 +253,12 @@ ERROR FreeResource(MEMORYID MemoryID) if (((LONG *)mem.Address)[-1] != CODE_MEMH) { log.warning("Bad header on block #%d, address %p, size %d.", MemoryID, mem.Address, mem.Size); - error = ERR_InvalidData; + error = ERR::InvalidData; } if (((LONG *)mem_end)[0] != CODE_MEMT) { log.warning("Bad tail on block #%d, address %p, size %d.", MemoryID, mem.Address, mem.Size); - error = ERR_InvalidData; + error = ERR::InvalidData; DEBUG_BREAK } @@ -279,10 +279,10 @@ ERROR FreeResource(MEMORYID MemoryID) return error; } - log.warning("Memory ID #%d does not exist.", MemoryID); - return ERR_MemoryDoesNotExist; + log.traceWarning("Memory ID #%d does not exist.", MemoryID); + return ERR::MemoryDoesNotExist; } - else return log.warning(ERR_SystemLocked); + else return log.warning(ERR::SystemLocked); } /********************************************************************************************************************* @@ -317,12 +317,12 @@ SystemLocked *********************************************************************************************************************/ -ERROR MemoryIDInfo(MEMORYID MemoryID, MemInfo *MemInfo, LONG Size) +ERR MemoryIDInfo(MEMORYID MemoryID, MemInfo *MemInfo, LONG Size) { pf::Log log(__FUNCTION__); - if ((!MemInfo) or (!MemoryID)) return log.warning(ERR_NullArgs); - if ((size_t)Size < sizeof(MemInfo)) return log.warning(ERR_Args); + if ((!MemInfo) or (!MemoryID)) return log.warning(ERR::NullArgs); + if ((size_t)Size < sizeof(MemInfo)) return log.warning(ERR::Args); ClearMemory(MemInfo, Size); @@ -335,11 +335,11 @@ ERROR MemoryIDInfo(MEMORYID MemoryID, MemInfo *MemInfo, LONG Size) MemInfo->AccessCount = mem->second.AccessCount; MemInfo->Flags = mem->second.Flags; MemInfo->MemoryID = mem->second.MemoryID; - return ERR_Okay; + return ERR::Okay; } - else return ERR_MemoryDoesNotExist; + else return ERR::MemoryDoesNotExist; } - else return log.warning(ERR_SystemLocked); + else return log.warning(ERR::SystemLocked); } /********************************************************************************************************************* @@ -376,12 +376,12 @@ MemoryDoesNotExist *********************************************************************************************************************/ -ERROR MemoryPtrInfo(APTR Memory, MemInfo *MemInfo, LONG Size) +ERR MemoryPtrInfo(APTR Memory, MemInfo *MemInfo, LONG Size) { pf::Log log(__FUNCTION__); - if ((!MemInfo) or (!Memory)) return log.warning(ERR_NullArgs); - if ((size_t)Size < sizeof(MemInfo)) return log.warning(ERR_Args); + if ((!MemInfo) or (!Memory)) return log.warning(ERR::NullArgs); + if ((size_t)Size < sizeof(MemInfo)) return log.warning(ERR::Args); ClearMemory(MemInfo, Size); @@ -398,13 +398,13 @@ ERROR MemoryPtrInfo(APTR Memory, MemInfo *MemInfo, LONG Size) MemInfo->AccessCount = mem.AccessCount; MemInfo->Flags = mem.Flags; MemInfo->MemoryID = mem.MemoryID; - return ERR_Okay; + return ERR::Okay; } } log.warning("Private memory address %p is not valid.", Memory); - return ERR_MemoryDoesNotExist; + return ERR::MemoryDoesNotExist; } - else return log.warning(ERR_SystemLocked); + else return log.warning(ERR::SystemLocked); } /********************************************************************************************************************* @@ -436,7 +436,7 @@ Memory: The memory block to be re-allocated is invalid. *********************************************************************************************************************/ -ERROR ReallocMemory(APTR Address, ULONG NewSize, APTR *Memory, MEMORYID *MemoryID) +ERR ReallocMemory(APTR Address, ULONG NewSize, APTR *Memory, MEMORYID *MemoryID) { pf::Log log(__FUNCTION__); @@ -444,29 +444,29 @@ ERROR ReallocMemory(APTR Address, ULONG NewSize, APTR *Memory, MEMORYID *MemoryI if ((!Address) or (NewSize <= 0)) { log.function("Address: %p, NewSize: %d, &Memory: %p, &MemoryID: %p", Address, NewSize, Memory, MemoryID); - return log.warning(ERR_Args); + return log.warning(ERR::Args); } if ((!Memory) and (!MemoryID)) { log.function("Address: %p, NewSize: %d, &Memory: %p, &MemoryID: %p", Address, NewSize, Memory, MemoryID); - return log.warning(ERR_NullArgs); + return log.warning(ERR::NullArgs); } // Check the validity of what we have been sent MemInfo meminfo; - if (MemoryIDInfo(GetMemoryID(Address), &meminfo, sizeof(meminfo)) != ERR_Okay) { + if (MemoryIDInfo(GetMemoryID(Address), &meminfo, sizeof(meminfo)) != ERR::Okay) { log.warning("MemoryPtrInfo() failed for address %p.", Address); - return ERR_Memory; + return ERR::Memory; } - if (meminfo.Size IS NewSize) return ERR_Okay; + if (meminfo.Size IS NewSize) return ERR::Okay; if (glShowPrivate) log.branch("Address: %p, NewSize: %d", Address, NewSize); // Allocate the new memory block and copy the data across - if (!AllocMemory(NewSize, meminfo.Flags, Memory, MemoryID)) { + if (AllocMemory(NewSize, meminfo.Flags, Memory, MemoryID) IS ERR::Okay) { auto copysize = (NewSize < meminfo.Size) ? NewSize : meminfo.Size; CopyMemory(Address, *Memory, copysize); @@ -475,9 +475,9 @@ ERROR ReallocMemory(APTR Address, ULONG NewSize, APTR *Memory, MEMORYID *MemoryI if (meminfo.AccessCount > 0) ReleaseMemory(Address); FreeResource(Address); - return ERR_Okay; + return ERR::Okay; } - else return log.error(ERR_AllocMemory); + else return log.error(ERR::AllocMemory); } //******************************************************************************************************************** diff --git a/src/core/lib_messages.cpp b/src/core/lib_messages.cpp index c99512c81..48afbd710 100644 --- a/src/core/lib_messages.cpp +++ b/src/core/lib_messages.cpp @@ -32,19 +32,19 @@ Name: Messages #include "defs.h" -static ERROR wake_task(void); +static ERR wake_task(void); #ifdef _WIN32 -static ERROR sleep_task(LONG, BYTE); +static ERR sleep_task(LONG, BYTE); #else -static ERROR sleep_task(LONG); -ERROR write_nonblock(LONG Handle, APTR Data, LONG Size, LARGE EndTime); +static ERR sleep_task(LONG); +ERR write_nonblock(LONG Handle, APTR Data, LONG Size, LARGE EndTime); #endif template inline APTR ResolveAddress(T *Pointer, LONG Offset) { return APTR(((BYTE *)Pointer) + Offset); } -static ERROR msghandler_free(APTR Address) +static ERR msghandler_free(APTR Address) { pf::Log log("RemoveMsgHandler"); log.trace("Handle: %p", Address); @@ -56,7 +56,7 @@ static ERROR msghandler_free(APTR Address) if (h->Next) h->Next->Prev = h->Prev; if (h->Prev) h->Prev->Next = h->Next; } - return ERR_Okay; + return ERR::Okay; } static ResourceManager glResourceMsgHandler = { @@ -72,7 +72,7 @@ static std::mutex glQueueLock; // Handler for WaitForObjects(). If an object on the list is signalled then it is removed from the list. A // message is sent once the list of objects that require signalling has been exhausted. -static void notify_signal_wfo(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, APTR Args) +static void notify_signal_wfo(OBJECTPTR Object, ACTIONID ActionID, ERR Result, APTR Args) { if (auto lref = glWFOList.find(Object->UID); lref != glWFOList.end()) { pf::Log log; @@ -109,11 +109,11 @@ When calling AddMsgHandler(), you can provide an optional Custom pointer that wi MsgType acts as a filter so that only messages with the same type identifier will be passed to the handler. The Routine parameter must point to the function handler, which will follow this definition: -
    ERROR handler(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize)
    +
    ERR handler(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize)
    -The handler must return `ERR_Okay` if the message was handled. This means that the message will not be passed to message -handlers that are yet to receive the message. Throw `ERR_NothingDone` if the message has been ignored or `ERR_Continue` -if the message was processed but may be analysed by other handlers. Throw `ERR_Terminate` to break the current +The handler must return `ERR::Okay` if the message was handled. This means that the message will not be passed to message +handlers that are yet to receive the message. Throw `ERR::NothingDone` if the message has been ignored or `ERR::Continue` +if the message was processed but may be analysed by other handlers. Throw `ERR::Terminate` to break the current ProcessMessages() loop. When using Fluid, this is best achieved by writing `check(errorcode)` in the handler. The handler will be identified by a unique pointer returned in the Handle parameter. This handle will be garbage @@ -133,17 +133,17 @@ AllocMemory *********************************************************************************************************************/ -ERROR AddMsgHandler(APTR Custom, LONG MsgType, FUNCTION *Routine, MsgHandler **Handle) +ERR AddMsgHandler(APTR Custom, LONG MsgType, FUNCTION *Routine, MsgHandler **Handle) { pf::Log log(__FUNCTION__); - if (!Routine) return log.warning(ERR_NullArgs); + if (!Routine) return log.warning(ERR::NullArgs); log.branch("Custom: %p, MsgType: %d", Custom, MsgType); if (auto lock = std::unique_lock{glmMsgHandler}) { MsgHandler *handler; - if (!AllocMemory(sizeof(MsgHandler), MEM::MANAGED, (APTR *)&handler, NULL)) { + if (AllocMemory(sizeof(MsgHandler), MEM::MANAGED, (APTR *)&handler, NULL) IS ERR::Okay) { set_memory_manager(handler, &glResourceMsgHandler); handler->Prev = NULL; @@ -161,11 +161,11 @@ ERROR AddMsgHandler(APTR Custom, LONG MsgType, FUNCTION *Routine, MsgHandler **H glLastMsgHandler = handler; if (Handle) *Handle = handler; - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } - else return log.warning(ERR_Lock); + else return log.warning(ERR::Lock); } /********************************************************************************************************************* @@ -176,7 +176,7 @@ GetMessage: Reads messages from message queues. The GetMessage() function is used to read messages that have been stored in the local message queue. You can use this function to read the next immediate message stored on the queue, or the first message on the queue that matches a particular Type. It is also possible to call this function in a loop to clear out all messages, until an error code -other than `ERR_Okay` is returned. +other than `ERR::Okay` is returned. Messages will often (although not always) carry data that is relevant to the message type. To retrieve this data you need to supply a buffer, preferably one that is large enough to receive all the data that you expect from your @@ -200,7 +200,7 @@ Search: No more messages are left on the queue, or no messages that match the gi *********************************************************************************************************************/ -ERROR GetMessage(LONG Type, MSF Flags, APTR Buffer, LONG BufferSize) +ERR GetMessage(LONG Type, MSF Flags, APTR Buffer, LONG BufferSize) { const std::lock_guard lock(glQueueLock); @@ -229,10 +229,10 @@ ERROR GetMessage(LONG Type, MSF Flags, APTR Buffer, LONG BufferSize) } glQueue.erase(it); - return ERR_Okay; + return ERR::Okay; } - return ERR_Search; + return ERR::Search; } /********************************************************************************************************************* @@ -251,11 +251,11 @@ consider calling ProcessMessages() at a rate of 50 times per second to ensure th User messages that are on the queue are passed to message handlers. If no message handler exists to interpret the message, then it is removed from the queue without being processed. Message handlers are added with the -~AddMsgHandler() function. If a message handler returns the error code `ERR_Terminate`, then ProcessMessages() -will stop processing the queue and returns immediately with `ERR_Okay`. +~AddMsgHandler() function. If a message handler returns the error code `ERR::Terminate`, then ProcessMessages() +will stop processing the queue and returns immediately with `ERR::Okay`. If a message with a `MSGID_QUIT` ID is found on the queue, then the function returns immediately with the error code -ERR_Terminate. The program must respond to the terminate request by exiting immediately. +ERR::Terminate. The program must respond to the terminate request by exiting immediately. -INPUT- int(PMF) Flags: Optional flags are specified here (clients should set a value of zero). @@ -269,12 +269,12 @@ Terminate: A MSGID_QUIT message type was found on the message queue. *********************************************************************************************************************/ -ERROR ProcessMessages(PMF Flags, LONG TimeOut) +ERR ProcessMessages(PMF Flags, LONG TimeOut) { pf::Log log(__FUNCTION__); // Message processing is only possible from the main thread (for system design and synchronisation reasons) - if (!tlMainThread) return log.warning(ERR_OutsideMainThread); + if (!tlMainThread) return log.warning(ERR::OutsideMainThread); // Ensure that all resources allocated by sub-routines are assigned to the Task object by default. pf::SwitchContext ctx(glCurrentTask); @@ -291,7 +291,7 @@ ERROR ProcessMessages(PMF Flags, LONG TimeOut) //log.msg("Do not call this function when inside a notification routine."); } else if (tlMsgRecursion > 8) { - return ERR_Recursion; + return ERR::Recursion; } tlMsgRecursion++; @@ -302,12 +302,12 @@ ERROR ProcessMessages(PMF Flags, LONG TimeOut) log.traceBranch("Flags: $%.8x, TimeOut: %d", LONG(Flags), TimeOut); - ERROR returncode = ERR_Okay; + ERR returncode = ERR::Okay; bool breaking = false; - ERROR error; + ERR error; auto granted = std::unique_lock{glmMsgHandler}; // A persistent lock on message handlers is optimal - if (!granted) return log.warning(ERR_SystemLocked); + if (!granted) return log.warning(ERR::SystemLocked); do { // Standard message handler for the core process. // Call all objects on the timer list (managed by SubscribeTimer()). To manage timer locking cleanly, the loop @@ -335,28 +335,28 @@ ERROR ProcessMessages(PMF Flags, LONG TimeOut) timer->Locked = true; // Prevents termination of the structure irrespective of having a TL_TIMER lock. bool relock = false; - if (timer->Routine.Type IS CALL_STDC) { // C/C++ callback + if (timer->Routine.isC()) { OBJECTPTR subscriber; if (!timer->SubscriberID) { // Internal subscriptions like process_janitor() don't have a subscriber - auto routine = (ERROR (*)(OBJECTPTR, LARGE, LARGE))timer->Routine.StdC.Routine; + auto routine = (ERR (*)(OBJECTPTR, LARGE, LARGE, APTR))timer->Routine.StdC.Routine; glmTimer.unlock(); relock = true; - error = routine(NULL, elapsed, current_time); + error = routine(NULL, elapsed, current_time, timer->Routine.StdC.Meta); } - else if (!AccessObject(timer->SubscriberID, 50, &subscriber)) { + else if (AccessObject(timer->SubscriberID, 50, &subscriber) IS ERR::Okay) { pf::SwitchContext context(subscriber); - auto routine = (ERROR (*)(OBJECTPTR, LARGE, LARGE))timer->Routine.StdC.Routine; + auto routine = (ERR (*)(OBJECTPTR, LARGE, LARGE, APTR))timer->Routine.StdC.Routine; glmTimer.unlock(); relock = true; - error = routine(subscriber, elapsed, current_time); + error = routine(subscriber, elapsed, current_time, timer->Routine.StdC.Meta); ReleaseObject(subscriber); } - else error = ERR_AccessObject; + else error = ERR::AccessObject; } - else if (timer->Routine.Type IS CALL_SCRIPT) { // Script callback + else if (timer->Routine.isScript()) { const ScriptArg scargs[] = { { "Subscriber", timer->SubscriberID, FDF_OBJECTID }, { "Elapsed", elapsed }, @@ -367,14 +367,14 @@ ERROR ProcessMessages(PMF Flags, LONG TimeOut) relock = true; auto script = (objScript *)timer->Routine.Script.Script; - if (scCallback(script, timer->Routine.Script.ProcedureID, scargs, ARRAYSIZE(scargs), &error)) error = ERR_Terminate; + if (scCallback(script, timer->Routine.Script.ProcedureID, scargs, std::ssize(scargs), &error) != ERR::Okay) error = ERR::Terminate; } - else error = ERR_Terminate; + else error = ERR::Terminate; timer->Locked = false; - if (error IS ERR_Terminate) { - if (timer->Routine.Type IS CALL_SCRIPT) { + if (error IS ERR::Terminate) { + if (timer->Routine.isScript()) { scDerefProcedure(timer->Routine.Script.Script, &timer->Routine); } @@ -403,13 +403,13 @@ ERROR ProcessMessages(PMF Flags, LONG TimeOut) for (auto hdl=glMsgHandlers; hdl; hdl=hdl->Next) { if ((!hdl->MsgType) or (hdl->MsgType IS glQueue[i].Type)) { - ERROR result = ERR_NoSupport; - if (hdl->Function.Type IS CALL_STDC) { - auto msghandler = (LONG (*)(APTR, LONG, LONG, APTR, LONG))hdl->Function.StdC.Routine; - if (glQueue[i].Size) result = msghandler(hdl->Custom, glQueue[i].UID, glQueue[i].Type, glQueue[i].getBuffer(), glQueue[i].Size); - else result = msghandler(hdl->Custom, glQueue[i].UID, glQueue[i].Type, NULL, 0); + ERR result = ERR::NoSupport; + if (hdl->Function.isC()) { + auto msghandler = (ERR (*)(APTR, LONG, LONG, APTR, LONG, APTR))hdl->Function.StdC.Routine; + if (glQueue[i].Size) result = msghandler(hdl->Custom, glQueue[i].UID, glQueue[i].Type, glQueue[i].getBuffer(), glQueue[i].Size, hdl->Function.StdC.Meta); + else result = msghandler(hdl->Custom, glQueue[i].UID, glQueue[i].Type, NULL, 0, hdl->Function.StdC.Meta); } - else if (hdl->Function.Type IS CALL_SCRIPT) { + else if (hdl->Function.isScript()) { const ScriptArg args[] = { { "Custom", hdl->Custom }, { "UID", glQueue[i].UID }, @@ -418,13 +418,13 @@ ERROR ProcessMessages(PMF Flags, LONG TimeOut) { "Size", glQueue[i].Size, FD_LONG|FD_BUFSIZE } }; auto &script = hdl->Function.Script; - if (scCallback(script.Script, script.ProcedureID, args, ARRAYSIZE(args), &result)) result = ERR_Terminate; + if (scCallback(script.Script, script.ProcedureID, args, std::ssize(args), &result) != ERR::Okay) result = ERR::Terminate; } - if (result IS ERR_Okay) { // If the message was handled, do not pass it to anyone else + if (result IS ERR::Okay) { // If the message was handled, do not pass it to anyone else break; } - else if (result IS ERR_Terminate) { // Terminate the ProcessMessages() loop, but don't quit the program + else if (result IS ERR::Terminate) { // Terminate the ProcessMessages() loop, but don't quit the program log.trace("Terminate request received from message handler."); timeout_end = 0; // Set to zero to indicate loop terminated break; @@ -500,13 +500,13 @@ ERROR ProcessMessages(PMF Flags, LONG TimeOut) else if (PreciseTime() >= timeout_end) { if (TimeOut) { log.trace("Breaking message loop - timeout of %dms.", TimeOut); - if (timeout_end > 0) returncode = ERR_TimeOut; + if (timeout_end > 0) returncode = ERR::TimeOut; } break; } } while (true); - if ((glTaskState IS TSTATE::STOPPING) and ((Flags & PMF::SYSTEM_NO_BREAK) IS PMF::NIL)) returncode = ERR_Terminate; + if ((glTaskState IS TSTATE::STOPPING) and ((Flags & PMF::SYSTEM_NO_BREAK) IS PMF::NIL)) returncode = ERR::Terminate; tlMsgRecursion--; return returncode; @@ -519,7 +519,7 @@ ScanMessages: Scans a message queue for multiple occurrences of a message type. Use the ScanMessages() function to scan the local message queue for information without affecting the state of the queue. To use this function effectively, make repeated calls to ScanMessages() to analyse the queue until it returns -an error code other than `ERR_Okay`. +an error code other than `ERR::Okay`. The following example illustrates a scan for `MSGID_QUIT` messages: @@ -547,22 +547,22 @@ Search: No more messages are left on the queue, or no messages that match the gi *********************************************************************************************************************/ -ERROR ScanMessages(LONG *Handle, LONG Type, APTR Buffer, LONG BufferSize) +ERR ScanMessages(LONG *Handle, LONG Type, APTR Buffer, LONG BufferSize) { pf::Log log(__FUNCTION__); - if (!Handle) return log.warning(ERR_NullArgs); + if (!Handle) return log.warning(ERR::NullArgs); if (!Buffer) BufferSize = 0; if (*Handle < 0) { *Handle = -1; - return ERR_Search; + return ERR::Search; } const std::lock_guard lock(glQueueLock); LONG index = *Handle; - if (index >= LONG(glQueue.size())) return ERR_OutOfRange; + if (index >= LONG(glQueue.size())) return ERR::OutOfRange; for (auto it = glQueue.begin() + index; it != glQueue.end(); it++) { if ((it->Type) and ((it->Type IS Type) or (!Type))) { @@ -581,12 +581,12 @@ ERROR ScanMessages(LONG *Handle, LONG Type, APTR Buffer, LONG BufferSize) } *Handle = index + 1; - return ERR_Okay; + return ERR::Okay; } } *Handle = -1; - return ERR_Search; + return ERR::Search; } /********************************************************************************************************************* @@ -611,7 +611,7 @@ Okay: The message was successfully written to the message queue. *********************************************************************************************************************/ -ERROR SendMessage(LONG Type, MSF Flags, APTR Data, LONG Size) +ERR SendMessage(LONG Type, MSF Flags, APTR Data, LONG Size) { pf::Log log(__FUNCTION__); @@ -623,7 +623,7 @@ ERROR SendMessage(LONG Type, MSF Flags, APTR Data, LONG Size) else log.branch("Type: %d, Data: %p, Size: %d", Type, Data, Size); } - if ((!Type) or (Size < 0)) return log.warning(ERR_Args); + if ((!Type) or (Size < 0)) return log.warning(ERR::Args); { const std::lock_guard lock(glQueueLock); @@ -631,7 +631,7 @@ ERROR SendMessage(LONG Type, MSF Flags, APTR Data, LONG Size) if ((Flags & (MSF::NO_DUPLICATE|MSF::UPDATE)) != MSF::NIL) { for (auto it=glQueue.begin(); it != glQueue.end(); it++) { if (it->Type IS Type) { - if ((Flags & MSF::NO_DUPLICATE) != MSF::NIL) return ERR_Okay; + if ((Flags & MSF::NO_DUPLICATE) != MSF::NIL) return ERR::Okay; else { // Delete the existing message before adding the new one when MF::UPDATE has been specified. it = glQueue.erase(it); break; @@ -645,7 +645,7 @@ ERROR SendMessage(LONG Type, MSF Flags, APTR Data, LONG Size) wake_task(); // Alert the process to indicate that there are messages available. - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -677,25 +677,25 @@ OutsideMainThread *********************************************************************************************************************/ -ERROR WaitForObjects(PMF Flags, LONG TimeOut, ObjectSignal *ObjectSignals) +ERR WaitForObjects(PMF Flags, LONG TimeOut, ObjectSignal *ObjectSignals) { // Refer to the Task class for the message interception routines pf::Log log(__FUNCTION__); - if (!glWFOList.empty()) return log.warning(ERR_Recursion); + if (!glWFOList.empty()) return log.warning(ERR::Recursion); // Message processing is only possible from the main thread (for system design and synchronisation reasons) - if (!tlMainThread) return log.warning(ERR_OutsideMainThread); + if (!tlMainThread) return log.warning(ERR::OutsideMainThread); log.branch("Flags: $%.8x, Timeout: %d, Signals: %p", LONG(Flags), TimeOut, ObjectSignals); pf::SwitchContext ctx(glCurrentTask); - ERROR error = ERR_Okay; + ERR error = ERR::Okay; glWFOList.clear(); if (ObjectSignals) { - for (LONG i=0; ((error IS ERR_Okay) and (ObjectSignals[i].Object)); i++) { + for (LONG i=0; ((error IS ERR::Okay) and (ObjectSignals[i].Object)); i++) { pf::ScopedObjectLock lock(ObjectSignals[i].Object); // For thread safety if (ObjectSignals[i].Object->defined(NF::SIGNALLED)) { @@ -705,22 +705,21 @@ ERROR WaitForObjects(PMF Flags, LONG TimeOut, ObjectSignal *ObjectSignals) else { // NB: An object being freed is treated as equivalent to it receiving a signal. // Refer to notify_signal_wfo() for notification handling and clearing of signals. - log.debug("Monitoring object #%d", ObjectSignals[i].Object->UID); - auto callback = make_function_stdc(notify_signal_wfo); - if ((!SubscribeAction(ObjectSignals[i].Object, AC_Free, &callback)) and - (!SubscribeAction(ObjectSignals[i].Object, AC_Signal, &callback))) { + log.detail("Monitoring object #%d", ObjectSignals[i].Object->UID); + if ((SubscribeAction(ObjectSignals[i].Object, AC_Free, FUNCTION(notify_signal_wfo)) IS ERR::Okay) and + (SubscribeAction(ObjectSignals[i].Object, AC_Signal, FUNCTION(notify_signal_wfo)) IS ERR::Okay)) { glWFOList.insert(std::make_pair(ObjectSignals[i].Object->UID, ObjectSignals[i])); } - else error = ERR_Failed; + else error = ERR::Failed; } } } - if (!error) { + if (error IS ERR::Okay) { if (TimeOut < 0) { // No time-out will apply if (glWFOList.empty()) error = ProcessMessages(Flags, 0); else { - while ((not glWFOList.empty()) and (!error)) { + while ((not glWFOList.empty()) and (error IS ERR::Okay)) { error = ProcessMessages(Flags, -1); } } @@ -728,14 +727,14 @@ ERROR WaitForObjects(PMF Flags, LONG TimeOut, ObjectSignal *ObjectSignals) else { auto current_time = PreciseTime(); auto end_time = current_time + (TimeOut * 1000LL); - while ((not glWFOList.empty()) and (current_time < end_time) and (!error)) { - log.debug("Waiting on %d objects.", (LONG)glWFOList.size()); + while ((not glWFOList.empty()) and (current_time < end_time) and (error IS ERR::Okay)) { + log.detail("Waiting on %d objects.", (LONG)glWFOList.size()); error = ProcessMessages(Flags, (end_time - current_time) / 1000LL); current_time = PreciseTime(); } } - if ((!error) and (not glWFOList.empty())) error = ERR_TimeOut; + if ((error IS ERR::Okay) and (not glWFOList.empty())) error = ERR::TimeOut; } if (not glWFOList.empty()) { // Clean up if there are dangling subscriptions @@ -747,7 +746,7 @@ ERROR WaitForObjects(PMF Flags, LONG TimeOut, ObjectSignal *ObjectSignals) glWFOList.clear(); } - if ((error > ERR_ExceptionThreshold) and (error != ERR_TimeOut)) log.warning(error); + if ((error > ERR::ExceptionThreshold) and (error != ERR::TimeOut)) log.warning(error); return error; } @@ -755,13 +754,13 @@ ERROR WaitForObjects(PMF Flags, LONG TimeOut, ObjectSignal *ObjectSignals) // This is the equivalent internal routine to SendMessage(), for the purpose of sending messages to other threads. #ifdef _WIN32 -ERROR send_thread_msg(WINHANDLE Handle, LONG Type, APTR Data, LONG Size) +ERR send_thread_msg(WINHANDLE Handle, LONG Type, APTR Data, LONG Size) #else -ERROR send_thread_msg(LONG Handle, LONG Type, APTR Data, LONG Size) +ERR send_thread_msg(LONG Handle, LONG Type, APTR Data, LONG Size) #endif { pf::Log log(__FUNCTION__); - ERROR error; + ERR error; log.function("Type: %d, Data: %p, Size: %d", Type, Data, Size); @@ -778,13 +777,13 @@ ERROR send_thread_msg(LONG Handle, LONG Type, APTR Data, LONG Size) // Write the main message. write = Size; if (!winWritePipe(Handle, Data, &write)) { - error = ERR_Okay; + error = ERR::Okay; } - else error = ERR_Write; + else error = ERR::Write; } - else error = ERR_Okay; + else error = ERR::Okay; } - else error = ERR_Write; + else error = ERR::Write; #else LARGE end_time = (PreciseTime() / 1000LL) + 10000LL; error = write_nonblock(Handle, &msg, sizeof(msg), end_time); @@ -793,7 +792,7 @@ ERROR send_thread_msg(LONG Handle, LONG Type, APTR Data, LONG Size) } #endif - if (error) log.warning(error); + if (error != ERR::Okay) log.warning(error); return error; } @@ -802,10 +801,10 @@ ERROR send_thread_msg(LONG Handle, LONG Type, APTR Data, LONG Size) // end-time is required so that a timeout will be signalled if the reader isn't keeping the buffer clear. #ifdef __unix__ -ERROR write_nonblock(LONG Handle, APTR Data, LONG Size, LARGE EndTime) +ERR write_nonblock(LONG Handle, APTR Data, LONG Size, LARGE EndTime) { LONG offset = 0; - ERROR error = ERR_Okay; + ERR error = ERR::Okay; while ((offset < Size) and (!error)) { LONG write_size = Size; @@ -824,17 +823,17 @@ ERROR write_nonblock(LONG Handle, APTR Data, LONG Size, LARGE EndTime) tv.tv_sec = (EndTime - (PreciseTime() / 1000LL)) / 1000LL; tv.tv_usec = 0; LONG total = select(1, &wfds, NULL, NULL, &tv); - if (total IS -1) error = ERR_SystemCall; - else if (!total) error = ERR_TimeOut; + if (total IS -1) error = ERR::SystemCall; + else if (!total) error = ERR::TimeOut; else break; } } - else if ((errno IS EINVAL) or (errno IS EBADF) or (errno IS EPIPE)) { error = ERR_InvalidHandle; break; } - else { error = ERR_Write; break; } + else if ((errno IS EINVAL) or (errno IS EBADF) or (errno IS EPIPE)) { error = ERR::InvalidHandle; break; } + else { error = ERR::Write; break; } } if ((PreciseTime() / 1000LL) > EndTime) { - error = ERR_TimeOut; + error = ERR::TimeOut; break; } } @@ -873,9 +872,9 @@ Search: The supplied ID does not refer to a message in the queue. *********************************************************************************************************************/ -ERROR UpdateMessage(LONG MessageID, LONG Type, APTR Buffer, LONG BufferSize) +ERR UpdateMessage(LONG MessageID, LONG Type, APTR Buffer, LONG BufferSize) { - if (!MessageID) return ERR_NullArgs; + if (!MessageID) return ERR::NullArgs; const std::lock_guard lock(glQueueLock); @@ -887,27 +886,27 @@ ERROR UpdateMessage(LONG MessageID, LONG Type, APTR Buffer, LONG BufferSize) if (Type IS -1) glQueue.erase(it); // Delete message from the queue else if (Type) it->Type = Type; - return ERR_Okay; + return ERR::Okay; } - return ERR_Search; + return ERR::Search; } //******************************************************************************************************************** // sleep_task() - Unix version #ifdef __unix__ -ERROR sleep_task(LONG Timeout) +ERR sleep_task(LONG Timeout) { pf::Log log(__FUNCTION__); if (!tlMainThread) { log.warning("Only the main thread can call this function."); - return ERR_Failed; + return ERR::Failed; } else if (tlPublicLockCount > 0) { log.warning("Cannot sleep while holding %d global locks.", tlPublicLockCount); - return ERR_Okay; + return ERR::Okay; } else if (tlPrivateLockCount != 0) { char buffer[120]; @@ -1058,7 +1057,7 @@ ERROR sleep_task(LONG Timeout) else log.warning("select() error %d: %s", errno, strerror(errno)); } - return ERR_Okay; + return ERR::Okay; } #endif @@ -1066,17 +1065,17 @@ ERROR sleep_task(LONG Timeout) // sleep_task() - Windows version #ifdef _WIN32 -ERROR sleep_task(LONG Timeout, BYTE SystemOnly) +ERR sleep_task(LONG Timeout, BYTE SystemOnly) { pf::Log log(__FUNCTION__); if (!tlMainThread) { log.warning("Only the main thread can call this function."); - return ERR_Failed; + return ERR::Failed; } else if (tlPublicLockCount > 0) { log.warning("You cannot sleep while still holding %d global locks!", tlPublicLockCount); - return ERR_Okay; + return ERR::Okay; } else if (tlPrivateLockCount != 0) { char buffer[120]; @@ -1191,7 +1190,7 @@ ERROR sleep_task(LONG Timeout, BYTE SystemOnly) else break; } - return ERR_Okay; + return ERR::Okay; } #endif // _WIN32 @@ -1211,11 +1210,11 @@ static void thread_socket_free(void *Socket) { close(PTR_TO_HOST(Socket)); } static void thread_socket_init(void) { pthread_key_create(&keySocket, thread_socket_free); } #endif -static ERROR wake_task(void) +static ERR wake_task(void) { pf::Log log(__FUNCTION__); - if (!glCurrentTask) return ERR_Okay; + if (!glCurrentTask) return ERR::Okay; if (tlPublicLockCount > 0) { if (glProgramStage != STAGE_SHUTDOWN) log.warning("Illegal call while holding %d global locks.", tlPublicLockCount); @@ -1246,7 +1245,7 @@ static ERROR wake_task(void) } else { log.warning("Failed to create a new socket communication point."); - return ERR_SystemCall; + return ERR::SystemCall; } } @@ -1266,5 +1265,5 @@ static ERROR wake_task(void) #endif - return ERR_Okay; + return ERR::Okay; } diff --git a/src/core/lib_objects.cpp b/src/core/lib_objects.cpp index 159fc1736..751572bd6 100644 --- a/src/core/lib_objects.cpp +++ b/src/core/lib_objects.cpp @@ -54,90 +54,96 @@ static void free_children(OBJECTPTR Object); //******************************************************************************************************************** -ERROR msg_free(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize) +ERR msg_free(APTR Custom, LONG MsgID, LONG MsgType, APTR Message, LONG MsgSize) { // Lock the object via conventional means to guarantee thread safety. OBJECTPTR obj; - if (!AccessObject(((OBJECTID *)Message)[0], 10000, &obj)) { + if (AccessObject(((OBJECTID *)Message)[0], 10000, &obj) IS ERR::Okay) { obj->Locked = false; // Required to allow the object to be freed while maintaining a lock via the Queue mechanism. FreeResource(obj); } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** // Object termination hook for FreeResource() -static ERROR object_free(BaseClass *Object) +static ERR object_free(BaseClass *Object) { pf::Log log("Free"); ScopedObjectAccess objlock(Object); - if (!objlock.granted()) return ERR_AccessObject; + if (!objlock.granted()) return ERR::AccessObject; ObjectContext new_context(Object, AC_Free); auto mc = Object->ExtClass; if (!mc) { log.trace("Object %p #%d is missing its class pointer.", Object, Object->UID); - return ERR_Okay; + return ERR::Okay; } - // Return if the object is currently in the process of being freed (i.e. avoid recursion) + // If the object is locked then we mark it for collection and return. + // Collection is achieved via the message queue for maximum safety. if (Object->Locked) { - log.debug("Object #%d locked; marking for deletion.", Object->UID); + log.detail("Object #%d locked; marking for deletion.", Object->UID); + if ((Object->Owner) and (Object->Owner->collecting())) Object->Owner = NULL; // The Owner pointer is no longer safe to use Object->Flags |= NF::FREE_ON_UNLOCK; - return ERR_InUse; + return ERR::InUse; } - // If the object is locked from LockObject() then we mark it for collection and return. - // Collection is achieved via the message queue as the safest and predictable option. - if (Object->terminating()) { - log.trace("Object already marked for termination."); - return ERR_InUse; + log.trace("Object already being terminated."); + return ERR::InUse; } if (Object->ActionDepth > 0) { // The object is still in use. This should only be triggered if the object wasn't locked with LockObject(). log.trace("Object in use; marking for collection."); + if ((Object->Owner) and (Object->Owner->collecting())) Object->Owner = NULL; if (!Object->defined(NF::COLLECT)) { Object->Flags |= NF::COLLECT; SendMessage(MSGID_FREE, MSF::NIL, &Object->UID, sizeof(OBJECTID)); } - return ERR_InUse; + return ERR::InUse; } - if (Object->Class->ClassID IS ID_METACLASS) log.branch("%s, Owner: %d", Object->className(), Object->OwnerID); - else if (Object->Class->ClassID IS ID_MODULE) log.branch("%s, Owner: %d", ((extModule *)Object)->Name, Object->OwnerID); - else if (Object->Name[0]) log.branch("Name: %s, Owner: %d", Object->Name, Object->OwnerID); - else log.branch("Owner: %d", Object->OwnerID); + if (Object->Class->ClassID IS ID_METACLASS) log.branch("%s, Owner: %d", Object->className(), Object->ownerID()); + else if (Object->Class->ClassID IS ID_MODULE) log.branch("%s, Owner: %d", ((extModule *)Object)->Name, Object->ownerID()); + else if (Object->Name[0]) log.branch("Name: %s, Owner: %d", Object->Name, Object->ownerID()); + else log.branch("Owner: %d", Object->ownerID()); // If the object wants to be warned when the free process is about to be executed, it will subscribe to the - // FreeWarning action. The process can be aborted by returning ERR_InUse. + // FreeWarning action. The process can be aborted by returning ERR::InUse. if (mc->ActionTable[AC_FreeWarning].PerformAction) { - if (mc->ActionTable[AC_FreeWarning].PerformAction(Object, NULL) IS ERR_InUse) { + if (mc->ActionTable[AC_FreeWarning].PerformAction(Object, NULL) IS ERR::InUse) { if (Object->collecting()) { // If the object is marked for deletion then it is not possible to avoid destruction (this prevents objects // from locking up the shutdown process). log.msg("Object will be destroyed despite being in use."); } - else return ERR_InUse; + else { + if ((Object->Owner) and (Object->Owner->collecting())) Object->Owner = NULL; + return ERR::InUse; + } } } if (mc->Base) { // Sub-class detected, so call the base class if (mc->Base->ActionTable[AC_FreeWarning].PerformAction) { - if (mc->Base->ActionTable[AC_FreeWarning].PerformAction(Object, NULL) IS ERR_InUse) { + if (mc->Base->ActionTable[AC_FreeWarning].PerformAction(Object, NULL) IS ERR::InUse) { if (Object->collecting()) { // If the object is marked for deletion then it is not possible to avoid destruction (this prevents // objects from locking up the shutdown process). log.msg("Object will be destroyed despite being in use."); } - else return ERR_InUse; + else { + if ((Object->Owner) and (Object->Owner->collecting())) Object->Owner = NULL; + return ERR::InUse; + } } } } @@ -147,7 +153,7 @@ static ERROR object_free(BaseClass *Object) Object->Flags = (Object->Flags|NF::FREE) & (~NF::FREE_ON_UNLOCK); - NotifySubscribers(Object, AC_Free, NULL, ERR_Okay); + NotifySubscribers(Object, AC_Free, NULL, ERR::Okay); if (mc->ActionTable[AC_Free].PerformAction) { // Could be sub-class or base-class mc->ActionTable[AC_Free].PerformAction(Object, NULL); @@ -167,7 +173,7 @@ static ERROR object_free(BaseClass *Object) // If a private child structure is present, remove it if (Object->ChildPrivate) { - if (FreeResource(Object->ChildPrivate)) log.warning("Invalid ChildPrivate address %p.", Object->ChildPrivate); + if (FreeResource(Object->ChildPrivate) != ERR::Okay) log.warning("Invalid ChildPrivate address %p.", Object->ChildPrivate); Object->ChildPrivate = NULL; } @@ -199,12 +205,12 @@ static ERROR object_free(BaseClass *Object) Object->Class = NULL; Object->UID = 0; - return ERR_Okay; + return ERR::Okay; } static ResourceManager glResourceObject = { "Object", - (ERROR (*)(APTR))&object_free + (ERR (*)(APTR))&object_free }; //******************************************************************************************************************** @@ -233,13 +239,13 @@ struct thread_data { BYTE Parameters; }; -static ERROR thread_action(extThread *Thread) +static ERR thread_action(extThread *Thread) { - ERROR error; + ERR error; auto data = (thread_data *)Thread->Data; OBJECTPTR obj = data->Object; - if (!(error = LockObject(obj, 5000))) { // Access the object and process the action. + if ((error = LockObject(obj, 5000)) IS ERR::Okay) { // Access the object and process the action. --obj->ThreadPending; error = Action(data->ActionID, obj, data->Parameters ? (data + 1) : NULL); @@ -287,8 +293,8 @@ static void free_children(OBJECTPTR Object) if (((mem.Flags & MEM::DELETE) != MEM::NIL) or (!mem.Object)) continue; - if (mem.Object->OwnerID != Object->UID) { - log.warning("Failed sanity test: Child object #%d has owner ID of #%d that does not match #%d.", mem.Object->UID, mem.Object->OwnerID, Object->UID); + if ((mem.Object->Owner) and (mem.Object->Owner != Object)) { + log.warning("Failed sanity test: Child object #%d has owner ID of #%d that does not match #%d.", mem.Object->UID, mem.Object->ownerID(), Object->UID); continue; } @@ -323,7 +329,7 @@ static void free_children(OBJECTPTR Object) else log.warning("Unfreed memory block %p, Size %d", mem.Address, mem.Size); } - if (FreeResource(mem.Address) != ERR_Okay) log.warning("Error freeing tracked address %p", mem.Address); + if (FreeResource(mem.Address) != ERR::Okay) log.warning("Error freeing tracked address %p", mem.Address); } } @@ -363,7 +369,7 @@ In all cases, action calls in C++ can be simplified by using their corresponding 2b. Window->move(30, 15, 0);
    -If the class of an object does not support the action ID, an error code of `ERR_NoSupport` is returned. To test +If the class of an object does not support the action ID, an error code of `ERR::NoSupport` is returned. To test an object to see if its class supports an action, use the ~CheckAction() function. In circumstances where an object ID is known without its pointer, the use of ~ActionMsg() or ~QueueAction() may be @@ -384,12 +390,12 @@ ObjectCorrupt: The object that was received is badly corrupted in a critical a **********************************************************************************************************************/ -ERROR Action(LONG ActionID, OBJECTPTR Object, APTR Parameters) +ERR Action(LONG ActionID, OBJECTPTR Object, APTR Parameters) { - if (!Object) return ERR_NullArgs; + if (!Object) return ERR::NullArgs; ScopedObjectAccess lock(Object); - if (!lock.granted()) return ERR_AccessObject; + if (!lock.granted()) return ERR::AccessObject; ObjectContext new_context(Object, ActionID); Object->ActionDepth++; @@ -399,11 +405,11 @@ ERROR Action(LONG ActionID, OBJECTPTR Object, APTR Parameters) auto log_depth = tlDepth; #endif - ERROR error; + ERR error; if (ActionID >= 0) { if (cl->ActionTable[ActionID].PerformAction) { // Can be a base-class or sub-class call error = cl->ActionTable[ActionID].PerformAction(Object, Parameters); - if (error IS ERR_NoAction) { + if (error IS ERR::NoAction) { if ((cl->Base) and (cl->Base->ActionTable[ActionID].PerformAction)) { // Base is set only if this is a sub-class error = cl->Base->ActionTable[ActionID].PerformAction(Object, Parameters); } @@ -412,24 +418,24 @@ ERROR Action(LONG ActionID, OBJECTPTR Object, APTR Parameters) else if ((cl->Base) and (cl->Base->ActionTable[ActionID].PerformAction)) { // Base is set only if this is a sub-class error = cl->Base->ActionTable[ActionID].PerformAction(Object, Parameters); } - else error = ERR_NoAction; + else error = ERR::NoAction; } else { // Method call - // Note that sub-classes may return ERR_NoAction if propagation to the base class is desirable. - auto routine = (ERROR (*)(OBJECTPTR, APTR))cl->Methods[-ActionID].Routine; + // Note that sub-classes may return ERR::NoAction if propagation to the base class is desirable. + auto routine = (ERR (*)(OBJECTPTR, APTR))cl->Methods[-ActionID].Routine; if (routine) error = routine(Object, Parameters); - else error = ERR_NoAction; + else error = ERR::NoAction; - if ((error IS ERR_NoAction) and (cl->Base)) { // If this is a child, check the base class - auto routine = (ERROR (*)(OBJECTPTR, APTR))cl->Base->Methods[-ActionID].Routine; + if ((error IS ERR::NoAction) and (cl->Base)) { // If this is a child, check the base class + auto routine = (ERR (*)(OBJECTPTR, APTR))cl->Base->Methods[-ActionID].Routine; if (routine) error = routine(Object, Parameters); } } // If the object has action subscribers, check if any of them are listening to this particular action, and if so, notify them. - if (error & ERF_Notified) { - error &= ~ERF_Notified; + if (LONG(error) & LONG(ERR::Notified)) { + error = ERR(LONG(error) & ~LONG(ERR::Notified)); } else if ((ActionID > 0) and (Object->NotifyFlags.load() & (1LL<<(ActionID & 63)))) { std::lock_guard lock(glSubLock); @@ -440,7 +446,7 @@ ERROR Action(LONG ActionID, OBJECTPTR Object, APTR Parameters) if (it->second.contains(ActionID)) { for (auto &list : it->second[ActionID]) { pf::SwitchContext ctx(list.Subscriber); - list.Callback(Object, ActionID, (error IS ERR_NoAction) ? ERR_Okay : error, Parameters); + list.Callback(Object, ActionID, (error IS ERR::NoAction) ? ERR::Okay : error, Parameters, list.Meta); } } } @@ -525,10 +531,10 @@ Failed: Failed to build buffered arguments. *********************************************************************************************************************/ -ERROR ActionMsg(LONG ActionID, OBJECTID ObjectID, APTR Args) +ERR ActionMsg(LONG ActionID, OBJECTID ObjectID, APTR Args) { OBJECTPTR object; - if (auto error = AccessObject(ObjectID, 3000, &object); !error) { + if (auto error = AccessObject(ObjectID, 3000, &object); error IS ERR::Okay) { error = Action(ActionID, object, Args); ReleaseObject(object); return error; @@ -549,7 +555,7 @@ action in parallel via a dynamically allocated thread. Please refer to the ~Act information on action execution. To receive feedback of the action's completion, use the Callback parameter and supply a function. The function -prototype for the callback routine is `callback(ACTIONID ActionID, OBJECTPTR Object, ERROR Error, LONG Key)` +prototype for the callback routine is `callback(ACTIONID ActionID, OBJECTPTR Object, ERR Error, LONG Key)` It is crucial that the target object is not destroyed while the thread is executing. Use the Callback routine to receive notification of the thread's completion and then free the object if desired. The callback will be processed @@ -579,19 +585,19 @@ Init *********************************************************************************************************************/ -ERROR ActionThread(ACTIONID ActionID, OBJECTPTR Object, APTR Parameters, FUNCTION *Callback, LONG Key) +ERR ActionThread(ACTIONID ActionID, OBJECTPTR Object, APTR Parameters, FUNCTION *Callback, LONG Key) { pf::Log log(__FUNCTION__); - if ((!ActionID) or (!Object)) return ERR_NullArgs; + if ((!ActionID) or (!Object)) return ERR::NullArgs; log.traceBranch("Action: %d, Object: %d, Parameters: %p, Callback: %p, Key: %d", ActionID, Object->UID, Parameters, Callback, Key); ++Object->ThreadPending; - ERROR error; + ERR error; extThread *thread = NULL; - if (!(error = threadpool_get(&thread))) { + if ((error = threadpool_get(&thread)) IS ERR::Okay) { // Prepare the parameter buffer for passing to the thread routine. LONG argssize; @@ -603,7 +609,7 @@ ERROR ActionThread(ACTIONID ActionID, OBJECTPTR Object, APTR Parameters, FUNCTIO if (ActionID > 0) { args = ActionTable[ActionID].Args; if ((argssize = ActionTable[ActionID].Size) > 0) { - if (!(error = copy_args(args, argssize, (BYTE *)Parameters, call_data + sizeof(thread_data), SIZE_ACTIONBUFFER, &argssize, ActionTable[ActionID].Name))) { + if ((error = copy_args(args, argssize, (BYTE *)Parameters, call_data + sizeof(thread_data), SIZE_ACTIONBUFFER, &argssize, ActionTable[ActionID].Name)) IS ERR::Okay) { free_args = true; } @@ -614,7 +620,7 @@ ERROR ActionThread(ACTIONID ActionID, OBJECTPTR Object, APTR Parameters, FUNCTIO else if (auto cl = Object->ExtClass) { args = cl->Methods[-ActionID].Args; if ((argssize = cl->Methods[-ActionID].Size) > 0) { - if (!(error = copy_args(args, argssize, (BYTE *)Parameters, call_data + sizeof(thread_data), SIZE_ACTIONBUFFER, &argssize, cl->Methods[-ActionID].Name))) { + if ((error = copy_args(args, argssize, (BYTE *)Parameters, call_data + sizeof(thread_data), SIZE_ACTIONBUFFER, &argssize, cl->Methods[-ActionID].Name)) IS ERR::Okay) { free_args = true; } } @@ -622,14 +628,14 @@ ERROR ActionThread(ACTIONID ActionID, OBJECTPTR Object, APTR Parameters, FUNCTIO argssize += sizeof(thread_data); } - else error = log.warning(ERR_MissingClass); + else error = log.warning(ERR::MissingClass); } else argssize = sizeof(thread_data); // Execute the thread that will call the action. Refer to thread_action() for the routine. - if (!error) { - thread->Routine = make_function_stdc(thread_action); + if (error IS ERR::Okay) { + thread->Routine = FUNCTION(thread_action); auto call = (thread_data *)call_data; call->Object = Object; @@ -644,14 +650,14 @@ ERROR ActionThread(ACTIONID ActionID, OBJECTPTR Object, APTR Parameters, FUNCTIO error = thread->activate(); } - if (error) { + if (error != ERR::Okay) { threadpool_release(thread); if (free_args) local_free_args(call_data + sizeof(thread_data), args); } } - else error = ERR_NewObject; + else error = ERR::NewObject; - if (error) --Object->ThreadPending; + if (error != ERR::Okay) --Object->ThreadPending; return error; } @@ -681,25 +687,26 @@ LostClass: The object has lost its class reference (object corrupt). *********************************************************************************************************************/ -ERROR CheckAction(OBJECTPTR Object, LONG ActionID) +ERR CheckAction(OBJECTPTR Object, LONG ActionID) { pf::Log log(__FUNCTION__); if (Object) { - if (Object->Class->ClassID IS ID_METACLASS) { - if (((extMetaClass *)Object)->ActionTable[ActionID].PerformAction) return ERR_Okay; - else return ERR_False; + if (!Object->Class) return ERR::False; + else if (Object->Class->ClassID IS ID_METACLASS) { + if (((extMetaClass *)Object)->ActionTable[ActionID].PerformAction) return ERR::Okay; + else return ERR::False; } else if (auto cl = Object->ExtClass) { - if (cl->ActionTable[ActionID].PerformAction) return ERR_Okay; + if (cl->ActionTable[ActionID].PerformAction) return ERR::Okay; else if (cl->Base) { - if (cl->Base->ActionTable[ActionID].PerformAction) return ERR_Okay; + if (cl->Base->ActionTable[ActionID].PerformAction) return ERR::Okay; } - return ERR_False; + return ERR::False; } - else return log.warning(ERR_LostClass); + else return log.warning(ERR::LostClass); } - else return log.warning(ERR_NullArgs); + else return log.warning(ERR::NullArgs); } /********************************************************************************************************************* @@ -719,20 +726,20 @@ False: The object ID does not exist. *********************************************************************************************************************/ -ERROR CheckObjectExists(OBJECTID ObjectID) +ERR CheckObjectExists(OBJECTID ObjectID) { if (auto lock = std::unique_lock{glmMemory}) { - LONG result = ERR_False; + ERR result = ERR::False; auto mem = glPrivateMemory.find(ObjectID); if ((mem != glPrivateMemory.end()) and (mem->second.Object)) { if (mem->second.Object->defined(NF::FREE_ON_UNLOCK)); - else result = ERR_True; + else result = ERR::True; } return result; } else { pf::Log log(__FUNCTION__); - return log.warning(ERR_LockFailed); + return log.warning(ERR::LockFailed); } } @@ -850,12 +857,12 @@ Search: No objects matching the given name could be found. *********************************************************************************************************************/ -ERROR FindObject(CSTRING InitialName, CLASSID ClassID, FOF Flags, OBJECTID *Result) +ERR FindObject(CSTRING InitialName, CLASSID ClassID, FOF Flags, OBJECTID *Result) { pf::Log log(__FUNCTION__); - if ((!Result) or (!InitialName)) return ERR_NullArgs; - if (!InitialName[0]) return log.warning(ERR_EmptyString); + if ((!Result) or (!InitialName)) return ERR::NullArgs; + if (!InitialName[0]) return log.warning(ERR::EmptyString); if ((Flags & FOF::SMART_NAMES) != FOF::NIL) { // If an integer based name (defined by #num) is passed, we translate it to an ObjectID rather than searching for @@ -877,24 +884,21 @@ ERROR FindObject(CSTRING InitialName, CLASSID ClassID, FOF Flags, OBJECTID *Resu if (number) { if (auto objectid = (OBJECTID)StrToInt(InitialName)) { - if (!CheckObjectExists(objectid)) { + if (CheckObjectExists(objectid) IS ERR::Okay) { *Result = objectid; - return ERR_Okay; + return ERR::Okay; } - else return ERR_Search; + else return ERR::Search; } - else return ERR_Search; + else return ERR::Search; } - if (!StrMatch("owner", InitialName)) { - if ((tlContext != &glTopContext) and (tlContext->object()->OwnerID)) { - if (!CheckObjectExists(tlContext->object()->OwnerID)) { - *Result = tlContext->object()->OwnerID; - return ERR_Okay; - } - else return ERR_DoesNotExist; + if (StrMatch("owner", InitialName) IS ERR::Okay) { + if ((tlContext != &glTopContext) and (tlContext->object()->Owner)) { + *Result = tlContext->object()->Owner->UID; + return ERR::Okay; } - else return ERR_DoesNotExist; + else return ERR::DoesNotExist; } } @@ -903,20 +907,20 @@ ERROR FindObject(CSTRING InitialName, CLASSID ClassID, FOF Flags, OBJECTID *Resu auto &list = glObjectLookup[InitialName]; if (!ClassID) { *Result = list.back()->UID; - return ERR_Okay; + return ERR::Okay; } for (auto it=list.rbegin(); it != list.rend(); it++) { auto obj = *it; if ((obj->Class->ClassID IS ClassID) or (obj->Class->BaseClassID IS ClassID)) { *Result = obj->UID; - return ERR_Okay; + return ERR::Okay; } } } } - return ERR_Search; + return ERR::Search; } /********************************************************************************************************************* @@ -1023,7 +1027,7 @@ OBJECTID GetOwnerID(OBJECTID ObjectID) { if (auto lock = std::unique_lock{glmMemory}) { if (auto mem = glPrivateMemory.find(ObjectID); mem != glPrivateMemory.end()) { - if (mem->second.Object) return mem->second.Object->OwnerID; + if (mem->second.Object) return mem->second.Object->ownerID(); } } return 0; @@ -1043,7 +1047,7 @@ load a JPEG file), the initialiser will search for a sub-class that can handle t provide ample support exists, a partial transfer of ownership will occur and the object's management will be shared between both the base class and the sub-class. -If an object does not support the data or its configuration, an error code of `ERR_NoSupport` will be returned. +If an object does not support the data or its configuration, an error code of `ERR::NoSupport` will be returned. Other appropriate error codes can be returned if initialisation fails. -INPUT- @@ -1056,7 +1060,7 @@ ObjectCorrupt *********************************************************************************************************************/ -ERROR InitObject(OBJECTPTR Object) +ERR InitObject(OBJECTPTR Object) { pf::Log log("Init"); @@ -1065,17 +1069,17 @@ ERROR InitObject(OBJECTPTR Object) auto cl = Object->ExtClass; if (Object->initialised()) { // Initialising twice does not cause an error, but send a warning and return - log.warning(ERR_DoubleInit); - return ERR_Okay; + log.warning(ERR::DoubleInit); + return ERR::Okay; } - if (Object->Name[0]) log.branch("%s #%d, Name: %s, Owner: %d", cl->ClassName, Object->UID, Object->Name, Object->OwnerID); - else log.branch("%s #%d, Owner: %d", cl->ClassName, Object->UID, Object->OwnerID); + if (Object->Name[0]) log.branch("%s #%d, Name: %s, Owner: %d", cl->ClassName, Object->UID, Object->Name, Object->ownerID()); + else log.branch("%s #%d, Owner: %d", cl->ClassName, Object->UID, Object->ownerID()); ObjectContext new_context(Object, AC_Init); bool use_subclass = false; - ERROR error = ERR_Okay; + ERR error = ERR::Okay; if (Object->isSubClass()) { // For sub-classes, the base-class gets called first. It should verify that // the object is sub-classed so as to prevent it from doing 'too much' initialisation. @@ -1084,12 +1088,12 @@ ERROR InitObject(OBJECTPTR Object) error = cl->Base->ActionTable[AC_Init].PerformAction(Object, NULL); } - if (!error) { + if (error IS ERR::Okay) { if (cl->ActionTable[AC_Init].PerformAction) { error = cl->ActionTable[AC_Init].PerformAction(Object, NULL); } - if (!error) Object->Flags |= NF::INITIALISED; + if (error IS ERR::Okay) Object->Flags |= NF::INITIALISED; } return error; @@ -1097,11 +1101,11 @@ ERROR InitObject(OBJECTPTR Object) else { // Meaning of special error codes: // - // ERR_NoSupport: The source data is not recognised. Search for a sub-class that might have better luck. Note + // ERR::NoSupport: The source data is not recognised. Search for a sub-class that might have better luck. Note // that in the first case we can only support classes that are already in memory. The second part of this // routine supports checking of sub-classes that aren't loaded yet. // - // ERR_UseSubClass: Similar to ERR_NoSupport, but avoids scanning of sub-classes that aren't loaded in memory. + // ERR::UseSubClass: Similar to ERR::NoSupport, but avoids scanning of sub-classes that aren't loaded in memory. std::array sublist; LONG sli = -1; @@ -1110,9 +1114,9 @@ ERROR InitObject(OBJECTPTR Object) if (Object->ExtClass->ActionTable[AC_Init].PerformAction) { error = Object->ExtClass->ActionTable[AC_Init].PerformAction(Object, NULL); } - else error = ERR_Okay; // If no initialiser defined, auto-OK + else error = ERR::Okay; // If no initialiser defined, auto-OK - if (!error) { + if (error IS ERR::Okay) { Object->Flags |= NF::INITIALISED; if (Object->ExtClass != cl) { @@ -1125,14 +1129,14 @@ ERROR InitObject(OBJECTPTR Object) Object->Flags |= NF::RECLASSED; // This flag indicates that the object originally belonged to the base-class } - return ERR_Okay; + return ERR::Okay; } - if (error IS ERR_UseSubClass) { + if (error IS ERR::UseSubClass) { log.trace("Requested to use registered sub-class."); use_subclass = TRUE; } - else if (error != ERR_NoSupport) break; + else if (error != ERR::NoSupport) break; if (sli IS -1) { // Initialise a list of all sub-classes already in memory for querying in sequence. @@ -1165,24 +1169,24 @@ ERROR InitObject(OBJECTPTR Object) // memory resources (loading each sub-class into memory just to check whether or not the data is supported is overkill). CSTRING path; - if (use_subclass) { // If ERR_UseSubClass was set and the sub-class was not registered, do not call IdentifyFile() - log.warning("ERR_UseSubClass was used but no suitable sub-class was registered."); + if (use_subclass) { // If ERR::UseSubClass was set and the sub-class was not registered, do not call IdentifyFile() + log.warning("ERR::UseSubClass was used but no suitable sub-class was registered."); } - else if ((error IS ERR_NoSupport) and (!GetField(Object, FID_Path|TSTR, &path)) and (path)) { + else if ((error IS ERR::NoSupport) and (GetField(Object, FID_Path|TSTR, &path) IS ERR::Okay) and (path)) { CLASSID class_id, subclass_id; - if (!IdentifyFile(path, &class_id, &subclass_id)) { + if (IdentifyFile(path, &class_id, &subclass_id) IS ERR::Okay) { if ((class_id IS Object->Class->ClassID) and (subclass_id)) { log.msg("Searching for subclass $%.8x", subclass_id); if ((Object->ExtClass = (extMetaClass *)FindClass(subclass_id))) { if (Object->ExtClass->ActionTable[AC_Init].PerformAction) { - if (!(error = Object->ExtClass->ActionTable[AC_Init].PerformAction(Object, NULL))) { + if ((error = Object->ExtClass->ActionTable[AC_Init].PerformAction(Object, NULL)) IS ERR::Okay) { log.msg("Object class switched to sub-class \"%s\".", Object->className()); Object->Flags |= NF::INITIALISED; Object->ExtClass->OpenCount++; - return ERR_Okay; + return ERR::Okay; } } - else return ERR_Okay; + else return ERR::Okay; } else log.warning("Failed to load module for class #%d.", subclass_id); } @@ -1217,11 +1221,11 @@ NullArgs *********************************************************************************************************************/ -ERROR ListChildren(OBJECTID ObjectID, pf::vector *List) +ERR ListChildren(OBJECTID ObjectID, pf::vector *List) { pf::Log log(__FUNCTION__); - if ((!ObjectID) or (!List)) return log.warning(ERR_NullArgs); + if ((!ObjectID) or (!List)) return log.warning(ERR::NullArgs); log.trace("#%d, List: %p", ObjectID, List); @@ -1236,9 +1240,9 @@ ERROR ListChildren(OBJECTID ObjectID, pf::vector *List) } } } - return ERR_Okay; + return ERR::Okay; } - else return ERR_LockFailed; + else return ERR::LockFailed; } /********************************************************************************************************************* @@ -1275,12 +1279,12 @@ ObjectExists: An object with the provided Name already exists in the system (app *********************************************************************************************************************/ -ERROR NewObject(LARGE ClassID, NF Flags, OBJECTPTR *Object) +ERR NewObject(LARGE ClassID, NF Flags, OBJECTPTR *Object) { pf::Log log(__FUNCTION__); auto class_id = ULONG(ClassID & 0xffffffff); - if ((!class_id) or (!Object)) return log.warning(ERR_NullArgs); + if ((!class_id) or (!Object)) return log.warning(ERR::NullArgs); auto mc = (extMetaClass *)FindClass(class_id); if (!mc) { @@ -1288,7 +1292,7 @@ ERROR NewObject(LARGE ClassID, NF Flags, OBJECTPTR *Object) log.function("Class %s was not found in the system.", glClassMap[class_id]->ClassName); } else log.function("Class $%.8x was not found in the system.", class_id); - return ERR_MissingClass; + return ERR::MissingClass; } if (Object) *Object = NULL; @@ -1309,7 +1313,7 @@ ERROR NewObject(LARGE ClassID, NF Flags, OBJECTPTR *Object) OBJECTPTR head = NULL; MEMORYID head_id; - if (!AllocMemory(mc->Size, MEM::MANAGED|MEM::OBJECT|MEM::NO_LOCK|(((Flags & NF::UNTRACKED) != NF::NIL) ? MEM::UNTRACKED : MEM::NIL), (APTR *)&head, &head_id)) { + if (AllocMemory(mc->Size, MEM::MANAGED|MEM::OBJECT|MEM::NO_LOCK|(((Flags & NF::UNTRACKED) != NF::NIL) ? MEM::UNTRACKED : MEM::NIL), (APTR *)&head, &head_id) IS ERR::Okay) { set_memory_manager(head, &glResourceObject); head->UID = head_id; @@ -1332,7 +1336,14 @@ ERROR NewObject(LARGE ClassID, NF Flags, OBJECTPTR *Object) } } else if (tlContext != &glTopContext) { // Track the object to the current context - SetOwner(head, tlContext->resource()); + auto obj = tlContext->resource(); + if (obj IS &glDummyObject) { + if (glCurrentTask) { + ScopedObjectAccess lock(glCurrentTask); + SetOwner(head, glCurrentTask); + } + } + else SetOwner(head, obj); } else if (glCurrentTask) { ScopedObjectAccess lock(glCurrentTask); @@ -1344,34 +1355,34 @@ ERROR NewObject(LARGE ClassID, NF Flags, OBJECTPTR *Object) pf::SwitchContext context(head); - ERROR error = ERR_Okay; + ERR error = ERR::Okay; if (mc->Base) { if (mc->Base->ActionTable[AC_NewObject].PerformAction) { - if ((error = mc->Base->ActionTable[AC_NewObject].PerformAction(head, NULL))) { + if ((error = mc->Base->ActionTable[AC_NewObject].PerformAction(head, NULL)) != ERR::Okay) { log.warning(error); } } - else error = log.warning(ERR_NoAction); + else error = log.warning(ERR::NoAction); } - if ((!error) and (mc->ActionTable[AC_NewObject].PerformAction)) { - if ((error = mc->ActionTable[AC_NewObject].PerformAction(head, NULL))) { + if ((error IS ERR::Okay) and (mc->ActionTable[AC_NewObject].PerformAction)) { + if ((error = mc->ActionTable[AC_NewObject].PerformAction(head, NULL)) != ERR::Okay) { log.warning(error); } } - if (!error) { + if (error IS ERR::Okay) { ((extMetaClass *)head->Class)->OpenCount++; if (mc->Base) mc->Base->OpenCount++; *Object = head; - return ERR_Okay; + return ERR::Okay; } FreeResource(head); return error; } - else return ERR_AllocMemory; + else return ERR::AllocMemory; } /********************************************************************************************************************* @@ -1387,7 +1398,7 @@ the original values. NOTE: Calling NotifySubscribers() does nothing to prevent the core from sending out an action notification as it normally would, thus causing duplication. To prevent this the client must logical-or the return code of -the action function with `ERF_Notified`, e.g. `ERR_Okay|ERF_Notified`. +the action function with `ERR::Notified`, e.g. `ERR::Okay|ERR::Notified`. -INPUT- obj Object: Pointer to the object that is to receive the notification message. @@ -1399,14 +1410,14 @@ error Error: The error code that is associated with the action result. *********************************************************************************************************************/ -void NotifySubscribers(OBJECTPTR Object, LONG ActionID, APTR Parameters, ERROR ErrorCode) +void NotifySubscribers(OBJECTPTR Object, LONG ActionID, APTR Parameters, ERR ErrorCode) { pf::Log log(__FUNCTION__); // No need for prv_access() since this function is called from within class action code only. - if (!Object) { log.warning(ERR_NullArgs); return; } - if ((ActionID <= 0) or (ActionID >= AC_END)) { log.warning(ERR_Args); return; } + if (!Object) { log.warning(ERR::NullArgs); return; } + if ((ActionID <= 0) or (ActionID >= AC_END)) { log.warning(ERR::Args); return; } if (!(Object->NotifyFlags.load() & (1LL<<(ActionID & 63)))) return; @@ -1417,7 +1428,7 @@ void NotifySubscribers(OBJECTPTR Object, LONG ActionID, APTR Parameters, ERROR E for (auto &sub : glSubscriptions[Object->UID][ActionID]) { if (sub.Subscriber) { pf::SwitchContext ctx(sub.Subscriber); - sub.Callback(Object, ActionID, ErrorCode, Parameters); + sub.Callback(Object, ActionID, ErrorCode, Parameters, sub.Meta); } } glSubReadOnly--; @@ -1425,7 +1436,7 @@ void NotifySubscribers(OBJECTPTR Object, LONG ActionID, APTR Parameters, ERROR E if (!glSubReadOnly) { if (!glDelayedSubscribe.empty()) { for (auto &entry : glDelayedSubscribe) { - glSubscriptions[entry.ObjectID][entry.ActionID].emplace_back(entry.Callback.StdC.Context, entry.Callback.StdC.Routine); + glSubscriptions[entry.ObjectID][entry.ActionID].emplace_back(entry.Callback.StdC.Context, entry.Callback.StdC.Routine, entry.Callback.StdC.Meta); } glDelayedSubscribe.clear(); } @@ -1435,7 +1446,7 @@ void NotifySubscribers(OBJECTPTR Object, LONG ActionID, APTR Parameters, ERROR E if (Object->UID IS entry.ObjectID) UnsubscribeAction(Object, ActionID); else { OBJECTPTR obj; - if (!AccessObject(entry.ObjectID, 3000, &obj)) { + if (AccessObject(entry.ObjectID, 3000, &obj) IS ERR::Okay) { UnsubscribeAction(obj, entry.ActionID); ReleaseObject(obj); } @@ -1478,12 +1489,12 @@ OutOfRange: The ActionID is invalid. *********************************************************************************************************************/ -ERROR QueueAction(LONG ActionID, OBJECTID ObjectID, APTR Args) +ERR QueueAction(LONG ActionID, OBJECTID ObjectID, APTR Args) { pf::Log log(__FUNCTION__); - if ((!ActionID) or (!ObjectID)) log.warning(ERR_NullArgs); - if (ActionID >= AC_END) return log.warning(ERR_OutOfRange); + if ((!ActionID) or (!ObjectID)) log.warning(ERR::NullArgs); + if (ActionID >= AC_END) return log.warning(ERR::OutOfRange); struct msgAction { ActionMessage Action; @@ -1504,9 +1515,9 @@ ERROR QueueAction(LONG ActionID, OBJECTID ObjectID, APTR Args) if (ActionTable[ActionID].Size) { auto fields = ActionTable[ActionID].Args; auto argssize = ActionTable[ActionID].Size; - if (copy_args(fields, argssize, (BYTE *)Args, msg.Buffer, SIZE_ACTIONBUFFER, &msgsize, ActionTable[ActionID].Name) != ERR_Okay) { + if (copy_args(fields, argssize, (BYTE *)Args, msg.Buffer, SIZE_ACTIONBUFFER, &msgsize, ActionTable[ActionID].Name) != ERR::Okay) { log.warning("Failed to buffer arguments for action \"%s\".", ActionTable[ActionID].Name); - return ERR_Failed; + return ERR::Failed; } msg.Action.SendArgs = true; @@ -1515,24 +1526,24 @@ ERROR QueueAction(LONG ActionID, OBJECTID ObjectID, APTR Args) else if (auto cl = (extMetaClass *)FindClass(GetClassID(ObjectID))) { auto fields = cl->Methods[-ActionID].Args; auto argssize = cl->Methods[-ActionID].Size; - if (copy_args(fields, argssize, (BYTE *)Args, msg.Buffer, SIZE_ACTIONBUFFER, &msgsize, cl->Methods[-ActionID].Name) != ERR_Okay) { + if (copy_args(fields, argssize, (BYTE *)Args, msg.Buffer, SIZE_ACTIONBUFFER, &msgsize, cl->Methods[-ActionID].Name) != ERR::Okay) { log.warning("Failed to buffer arguments for method \"%s\".", cl->Methods[-ActionID].Name); - return ERR_Failed; + return ERR::Failed; } msg.Action.SendArgs = true; } - else return log.warning(ERR_MissingClass); + else return log.warning(ERR::MissingClass); } - ERROR error = SendMessage(MSGID_ACTION, MSF::NIL, &msg.Action, msgsize + sizeof(ActionMessage)); + ERR error = SendMessage(MSGID_ACTION, MSF::NIL, &msg.Action, msgsize + sizeof(ActionMessage)); - if (error) { + if (error != ERR::Okay) { if (ActionID > 0) { - log.warning("Action %s on object #%d failed, SendMsg error: %s", ActionTable[ActionID].Name, ObjectID, glMessages[error]); + log.warning("Action %s on object #%d failed, SendMsg error: %s", ActionTable[ActionID].Name, ObjectID, glMessages[LONG(error)]); } - else log.warning("Method %d on object #%d failed, SendMsg error: %s", ActionID, ObjectID, glMessages[error]); + else log.warning("Method %d on object #%d failed, SendMsg error: %s", ActionID, ObjectID, glMessages[LONG(error)]); - if (error IS ERR_MemoryDoesNotExist) error = ERR_NoMatchingObject; + if (error IS ERR::MemoryDoesNotExist) error = ERR::NoMatchingObject; } return error; @@ -1560,7 +1571,7 @@ CLASSID ResolveClassName(CSTRING ClassName) { if ((!ClassName) or (!*ClassName)) { pf::Log log(__FUNCTION__); - log.warning(ERR_NullArgs); + log.warning(ERR::NullArgs); return 0; } @@ -1627,32 +1638,32 @@ Args *********************************************************************************************************************/ -ERROR SetOwner(OBJECTPTR Object, OBJECTPTR Owner) +ERR SetOwner(OBJECTPTR Object, OBJECTPTR Owner) { pf::Log log(__FUNCTION__); - if ((!Object) or (!Owner)) return log.warning(ERR_NullArgs); + if ((!Object) or (!Owner)) return log.warning(ERR::NullArgs); - if (Object->OwnerID IS Owner->UID) return ERR_Okay; + if (Object->Owner IS Owner) return ERR::Okay; if ((Object->ExtClass->Flags & CLF::NO_OWNERSHIP) != CLF::NIL) { log.traceWarning("Cannot set the object owner as CLF::NO_OWNERSHIP is set in its class."); - return ERR_Okay; + return ERR::Okay; } - if (Object IS Owner) return log.warning(ERR_Recursion); + if (Object IS Owner) return log.warning(ERR::Recursion); - //log.msg("Object: %d, New Owner: %d, Current Owner: %d", Object->UID, Owner->UID, Object->OwnerID); + //log.msg("Object: %d, New Owner: %d, Current Owner: %d", Object->UID, Owner->UID, Object->ownerID()); // Send a new child alert to the owner. If the owner returns an error then we return immediately. ScopedObjectAccess objlock(Object); - if (!CheckAction(Owner, AC_NewChild)) { + if (CheckAction(Owner, AC_NewChild) IS ERR::Okay) { struct acNewChild newchild = { .Object = Object }; - if (auto error = Action(AC_NewChild, Owner, &newchild); error != ERR_NoSupport) { - if (error) { // If the owner has passed the object through to another owner, return ERR_Okay, otherwise error. - if (error IS ERR_OwnerPassThrough) return ERR_Okay; + if (auto error = Action(AC_NewChild, Owner, &newchild); error != ERR::NoSupport) { + if (error != ERR::Okay) { // If the owner has passed the object through to another owner, return ERR::Okay, otherwise error. + if (error IS ERR::OwnerPassThrough) return ERR::Okay; else return error; } } @@ -1661,24 +1672,24 @@ ERROR SetOwner(OBJECTPTR Object, OBJECTPTR Owner) struct acNewOwner newowner = { .NewOwner = Owner }; Action(AC_NewOwner, Object, &newowner); - //if (Object->OwnerID) log.trace("SetOwner:","Changing the owner for object %d from %d to %d.", Object->UID, Object->OwnerID, Owner->UID); + //if (Object->Owner) log.trace("SetOwner:","Changing the owner for object %d from %d to %d.", Object->UID, Object->ownerID(), Owner->UID); // Track the object's memory header to the new owner if (auto lock = std::unique_lock{glmMemory}) { auto mem = glPrivateMemory.find(Object->UID); - if (mem IS glPrivateMemory.end()) return log.warning(ERR_SystemCorrupt); + if (mem IS glPrivateMemory.end()) return log.warning(ERR::SystemCorrupt); mem->second.OwnerID = Owner->UID; // Remove reference from the now previous owner - if (Object->OwnerID) glObjectChildren[Object->OwnerID].erase(Object->UID); + if (Object->Owner) glObjectChildren[Object->Owner->UID].erase(Object->UID); - Object->OwnerID = Owner->UID; + Object->Owner = Owner; glObjectChildren[Owner->UID].insert(Object->UID); - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_SystemLocked); + else return log.warning(ERR::SystemLocked); } /********************************************************************************************************************* @@ -1778,11 +1789,11 @@ static const char sn_lookup[256] = { '_', '_', '_', '_', '_', '_', '_', '_', '_', '_', '_', '_', '_', '_', '_', '_', '_', '_' }; -ERROR SetName(OBJECTPTR Object, CSTRING NewName) +ERR SetName(OBJECTPTR Object, CSTRING NewName) { pf::Log log(__FUNCTION__); - if ((!Object) or (!NewName)) return log.warning(ERR_NullArgs); + if ((!Object) or (!NewName)) return log.warning(ERR::NullArgs); ScopedObjectAccess objlock(Object); @@ -1796,9 +1807,9 @@ ERROR SetName(OBJECTPTR Object, CSTRING NewName) Object->Name[i] = 0; if (Object->Name[0]) glObjectLookup[Object->Name].push_back(Object); - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_LockFailed); + else return log.warning(ERR::LockFailed); } /********************************************************************************************************************* @@ -1816,29 +1827,28 @@ The following example illustrates how to listen to a Surface object's Redimensio events:
    -auto callback = make_function_stdc(notify_resize);
    -SubscribeAction(surface, AC_Redimension, &callback);
    +SubscribeAction(surface, AC_Redimension, FUNCTION(notify_resize, meta_ptr));
     
    The template below illustrates how the Callback function should be constructed:
    -void notify_resize(OBJECTPTR Object, ACTIONID Action, ERROR Result, APTR Parameters)
    +void notify_resize(OBJECTPTR Object, ACTIONID Action, ERR Result, APTR Parameters, APTR CallbackMeta)
     {
        auto Self = (objClassType *)CurrentContext();
     
        // Code here...
    -   if ((Result == ERR_Okay) and (Parameters)) {
    +   if ((Result == ERR::Okay) and (Parameters)) {
           auto resize = (struct acRedimension *)Parameters;
        }
     }
     
    The Object is the original subscription target, as-is the Action ID. The Result is the error code that was generated -at the end of the action call. If this is not set to `ERR_Okay`, assume that the action did not have an effect on +at the end of the action call. If this is not set to `ERR::Okay`, assume that the action did not have an effect on state. The Parameters are the original arguments provided by the client - be aware that these can legitimately be NULL even if an action specifies a required parameter structure. Notice that because subscriptions are context -sensitive, we can use ~CurrentContext() to get a reference to the object that initiated the subscription. +sensitive, ~CurrentContext() can be used to get a reference to the object that initiated the subscription. To terminate an action subscription, use the ~UnsubscribeAction() function. Subscriptions are not resource tracked, so it is critical to match the original call with an unsubscription. @@ -1856,14 +1866,14 @@ OutOfRange: The Action parameter is invalid. *********************************************************************************************************************/ -ERROR SubscribeAction(OBJECTPTR Object, ACTIONID ActionID, FUNCTION *Callback) +ERR SubscribeAction(OBJECTPTR Object, ACTIONID ActionID, FUNCTION *Callback) { pf::Log log(__FUNCTION__); - if ((!Object) or (!Callback)) return log.warning(ERR_NullArgs); - if ((ActionID < 0) or (ActionID >= AC_END)) return log.warning(ERR_OutOfRange); - if (Callback->Type != CALL_STDC) return log.warning(ERR_Args); - if (Object->collecting()) return ERR_Okay; + if ((!Object) or (!Callback)) return log.warning(ERR::NullArgs); + if ((ActionID < 0) or (ActionID >= AC_END)) return log.warning(ERR::OutOfRange); + if (!Callback->isC()) return log.warning(ERR::Args); + if (Object->collecting()) return ERR::Okay; if (glSubReadOnly) { glDelayedSubscribe.emplace_back(Object->UID, ActionID, *Callback); @@ -1872,11 +1882,11 @@ ERROR SubscribeAction(OBJECTPTR Object, ACTIONID ActionID, FUNCTION *Callback) else { std::lock_guard lock(glSubLock); - glSubscriptions[Object->UID][ActionID].emplace_back(Callback->StdC.Context, Callback->StdC.Routine); + glSubscriptions[Object->UID][ActionID].emplace_back(Callback->StdC.Context, Callback->StdC.Routine, Callback->StdC.Meta); Object->NotifyFlags.fetch_or(1LL<<(ActionID & 63), std::memory_order::relaxed); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1900,16 +1910,16 @@ int(AC) Action: The ID of the action that will be unsubscribed, or zero for all *********************************************************************************************************************/ -ERROR UnsubscribeAction(OBJECTPTR Object, ACTIONID ActionID) +ERR UnsubscribeAction(OBJECTPTR Object, ACTIONID ActionID) { pf::Log log(__FUNCTION__); - if (!Object) return log.warning(ERR_NullArgs); - if ((ActionID < 0) or (ActionID >= AC_END)) return log.warning(ERR_Args); + if (!Object) return log.warning(ERR::NullArgs); + if ((ActionID < 0) or (ActionID >= AC_END)) return log.warning(ERR::Args); if (glSubReadOnly) { glDelayedUnsubscribe.emplace_back(Object->UID, ActionID); - return ERR_Okay; + return ERR::Okay; } std::lock_guard lock(glSubLock); @@ -1958,5 +1968,5 @@ ERROR UnsubscribeAction(OBJECTPTR Object, ACTIONID ActionID) } } - return ERR_Okay; + return ERR::Okay; } diff --git a/src/core/lib_strings.cpp b/src/core/lib_strings.cpp index d99e10463..ace7a4b81 100644 --- a/src/core/lib_strings.cpp +++ b/src/core/lib_strings.cpp @@ -241,18 +241,18 @@ void free_iconv(void) -FUNCTION- StrCompare: Compares strings to see if they are identical. -This function compares two strings against each other. If the strings match then it returns `ERR_Okay`, otherwise it -returns `ERR_False`. By default the function is not case sensitive, but you can turn on case sensitivity by +This function compares two strings against each other. If the strings match then it returns `ERR::Okay`, otherwise it +returns `ERR::False`. By default the function is not case sensitive, but you can turn on case sensitivity by specifying the `STR::CASE` flag. If you set the Length to 0, the function will compare both strings for differences until a string terminates. If all -characters matched up until the termination, `ERR_Okay` will be returned regardless of whether or not one of the strings +characters matched up until the termination, `ERR::Okay` will be returned regardless of whether or not one of the strings happened to be longer than the other. If the Length is not 0, then the comparison will stop once the specified number of characters to match has been -reached. If one of the strings terminates before the specified Length is matched, `ERR_False` will be returned. +reached. If one of the strings terminates before the specified Length is matched, `ERR::False` will be returned. -If the `STR::MATCH_LEN` flag is specified, you can force the function into returning an `ERR_Okay` code only on the +If the `STR::MATCH_LEN` flag is specified, you can force the function into returning an `ERR::Okay` code only on the condition that both strings are of matching lengths. This flag is typically specified if the Length argument has been set to 0. @@ -273,7 +273,7 @@ False: The strings do not match. *********************************************************************************************************************/ -ERROR StrCompare(CSTRING String1, CSTRING String2, LONG Length, STR Flags) +ERR StrCompare(CSTRING String1, CSTRING String2, LONG Length, STR Flags) { LONG len, i, j; UBYTE char1, char2; @@ -281,9 +281,9 @@ ERROR StrCompare(CSTRING String1, CSTRING String2, LONG Length, STR Flags) CSTRING Original; #define Wildcard String1 - if ((!String1) or (!String2)) return ERR_Args; + if ((!String1) or (!String2)) return ERR::Args; - if (String1 IS String2) return ERR_Okay; // Return a match if both addresses are equal + if (String1 IS String2) return ERR::Okay; // Return a match if both addresses are equal if (!Length) len = 0x7fffffff; else len = Length; @@ -291,7 +291,7 @@ ERROR StrCompare(CSTRING String1, CSTRING String2, LONG Length, STR Flags) Original = String2; if ((Flags & STR::WILDCARD) != STR::NIL) { - if (!Wildcard[0]) return ERR_Okay; + if (!Wildcard[0]) return ERR::Okay; while ((*Wildcard) and (*String2)) { fail = false; @@ -300,7 +300,7 @@ ERROR StrCompare(CSTRING String1, CSTRING String2, LONG Length, STR Flags) for (i=0; (Wildcard[i]) and (Wildcard[i] != '*') and (Wildcard[i] != '|'); i++); // Count the number of printable characters after the '*' - if (i IS 0) return ERR_Okay; // Nothing left to compare as wildcard string terminates with a *, so return match + if (i IS 0) return ERR::Okay; // Nothing left to compare as wildcard string terminates with a *, so return match if ((!Wildcard[i]) or (Wildcard[i] IS '|')) { // Scan to the end of the string for wildcard situation like "*.txt" @@ -365,22 +365,22 @@ ERROR StrCompare(CSTRING String1, CSTRING String2, LONG Length, STR Flags) Wildcard++; String2 = Original; } - else return ERR_False; + else return ERR::False; } } if (!String2[0]) { - if (!Wildcard[0]) return ERR_Okay; - else if (Wildcard[0] IS '|') return ERR_Okay; + if (!Wildcard[0]) return ERR::Okay; + else if (Wildcard[0] IS '|') return ERR::Okay; } - if ((Wildcard[0] IS '*') and (Wildcard[1] IS 0)) return ERR_Okay; + if ((Wildcard[0] IS '*') and (Wildcard[1] IS 0)) return ERR::Okay; - return ERR_False; + return ERR::False; } else if ((Flags & STR::CASE) != STR::NIL) { while ((len) and (*String1) and (*String2)) { - if (*String1++ != *String2++) return ERR_False; + if (*String1++ != *String2++) return ERR::False; len--; } } @@ -390,7 +390,7 @@ ERROR StrCompare(CSTRING String1, CSTRING String2, LONG Length, STR Flags) char2 = *String2; if ((char1 >= 'A') and (char1 <= 'Z')) char1 = char1 - 'A' + 'a'; if ((char2 >= 'A') and (char2 <= 'Z')) char2 = char2 - 'A' + 'a'; - if (char1 != char2) return ERR_False; + if (char1 != char2) return ERR::False; String1++; String2++; len--; @@ -401,11 +401,11 @@ ERROR StrCompare(CSTRING String1, CSTRING String2, LONG Length, STR Flags) // requested to check. if ((Flags & (STR::MATCH_LEN|STR::WILDCARD)) != STR::NIL) { - if ((*String1 IS 0) and (*String2 IS 0)) return ERR_Okay; - else return ERR_False; + if ((*String1 IS 0) and (*String2 IS 0)) return ERR::Okay; + else return ERR::False; } - else if ((Length) and (len > 0)) return ERR_False; - else return ERR_Okay; + else if ((Length) and (len > 0)) return ERR::False; + else return ERR::Okay; } /********************************************************************************************************************* @@ -535,11 +535,11 @@ NoData: Locale information is not available. *********************************************************************************************************************/ -ERROR StrReadLocale(CSTRING Key, CSTRING *Value) +ERR StrReadLocale(CSTRING Key, CSTRING *Value) { pf::Log log(__FUNCTION__); - if ((!Key) or (!Value)) return ERR_NullArgs; + if ((!Key) or (!Value)) return ERR::NullArgs; #ifdef __ANDROID__ // Android doesn't have locale.cfg, we have to load that information from the system. @@ -578,22 +578,22 @@ ERROR StrReadLocale(CSTRING Key, CSTRING *Value) log.msg("Android language code: %s", code); - if (code[0]) { *Value = code; return ERR_Okay; } - else return ERR_Failed; + if (code[0]) { *Value = code; return ERR::Okay; } + else return ERR::Failed; } #endif if (!glLocale) { if (!(glLocale = objConfig::create::untracked(fl::Path("user:config/locale.cfg")))) { - return ERR_NoData; + return ERR::NoData; } } - if (!cfgReadValue(glLocale, "LOCALE", Key, Value)) { + if (cfgReadValue(glLocale, "LOCALE", Key, Value) IS ERR::Okay) { if (!*Value) *Value = ""; // It is OK for some values to be empty strings. - return ERR_Okay; + return ERR::Okay; } - else return ERR_Search; + else return ERR::Search; } //******************************************************************************************************************** diff --git a/src/core/lib_unicode.cpp b/src/core/lib_unicode.cpp index 4bbf76697..a6915a350 100644 --- a/src/core/lib_unicode.cpp +++ b/src/core/lib_unicode.cpp @@ -418,7 +418,7 @@ CSTRING UTF8ValidEncoding(CSTRING String, CSTRING Encoding) buffersize = 4096; if (buffersize < in) buffersize = in + 1024; - if (AllocMemory(buffersize, MEM::STRING|MEM::NO_CLEAR, (APTR *)&glIconvBuffer, NULL) != ERR_Okay) { + if (AllocMemory(buffersize, MEM::STRING|MEM::NO_CLEAR, (APTR *)&glIconvBuffer, NULL) != ERR::Okay) { tlContext = context; return NULL; } @@ -432,7 +432,7 @@ CSTRING UTF8ValidEncoding(CSTRING String, CSTRING Encoding) // Check/Expand the buffer size if (out+12 > buffersize) { - if (ReallocMemory(glIconvBuffer, buffersize + 4096, (APTR *)&glIconvBuffer, NULL)) { + if (ReallocMemory(glIconvBuffer, buffersize + 4096, (APTR *)&glIconvBuffer, NULL) != ERR::Okay) { tlContext = context; return NULL; } diff --git a/src/core/microsoft/processes.cpp b/src/core/microsoft/processes.cpp index 2bebcd77d..efa5bf98c 100644 --- a/src/core/microsoft/processes.cpp +++ b/src/core/microsoft/processes.cpp @@ -360,15 +360,15 @@ extern "C" LONG winLaunchProcess(APTR Task, LPSTR commandline, LPSTR InitialDir, //******************************************************************************************************************** -extern "C" LONG winGetExitCodeProcess(struct winprocess *Process, LPDWORD Code) +extern "C" ERR winGetExitCodeProcess(struct winprocess *Process, LPDWORD Code) { if (Process) { GetExitCodeProcess(Process->Handle, Code); - return ERR_Okay; + return ERR::Okay; } else { *Code = 0; - return ERR_Failed; + return ERR::Failed; } } diff --git a/src/core/microsoft/windows.cpp b/src/core/microsoft/windows.cpp index 7b6107479..d72df5d34 100644 --- a/src/core/microsoft/windows.cpp +++ b/src/core/microsoft/windows.cpp @@ -77,7 +77,7 @@ WINBASEAPI VOID WINAPI WakeAllConditionVariable(PCONDITION_VARIABLE ConditionVar WINBASEAPI VOID WINAPI WakeConditionVariable(PCONDITION_VARIABLE ConditionVariable); #endif -extern "C" LONG plAllocPrivateSemaphore(HANDLE *Semaphore, LONG InitialValue); +extern "C" ERR plAllocPrivateSemaphore(HANDLE *Semaphore, LONG InitialValue); extern "C" void plFreePrivateSemaphore(HANDLE *Semaphore); extern "C" long long winGetTickCount(void); @@ -145,13 +145,13 @@ typedef unsigned char UBYTE; typedef struct DateTime { - LONG Year; - LONG Month; - LONG Day; - LONG Hour; - LONG Minute; - LONG Second; - LONG TimeZone; + WORD Year; + BYTE Month; + BYTE Day; + BYTE Hour; + BYTE Minute; + BYTE Second; + BYTE TimeZone; } DateTime; #define IS == @@ -236,7 +236,7 @@ struct FileFeedback { }; extern "C" LONG CALL_FEEDBACK(struct FileFeedback *); -extern "C" LONG convert_errno(LONG Error, LONG Default); +extern "C" ERR convert_errno(LONG Error, ERR Default); extern "C" LONG winReadPipe(HANDLE FD, APTR Buffer, DWORD *Size); //******************************************************************************************************************** @@ -394,7 +394,7 @@ static const char *glMsgClass = "RKLMessageClass"; using BREAK_HANDLER = void (*)(); -extern "C" LONG winInitialise(unsigned int *PathHash, BREAK_HANDLER BreakHandler) +extern "C" ERR winInitialise(unsigned int *PathHash, BREAK_HANDLER BreakHandler) { MEMORY_BASIC_INFORMATION mbiInfo; char path[255]; @@ -442,7 +442,7 @@ extern "C" LONG winInitialise(unsigned int *PathHash, BREAK_HANDLER BreakHandler // Register a blocking (message style) semaphore for signalling that process validation is required. - if (plAllocPrivateSemaphore(&glValidationSemaphore, 1)) return ERR_Failed; + if (plAllocPrivateSemaphore(&glValidationSemaphore, 1) != ERR::Okay) return ERR::Failed; glDeadProcessMsg = RegisterWindowMessage("RKL_DeadProcess"); @@ -462,21 +462,21 @@ extern "C" LONG winInitialise(unsigned int *PathHash, BREAK_HANDLER BreakHandler HWND_MESSAGE, (HMENU)NULL, glInstance, NULL); } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** // Platform specific semaphore handling functions. -extern "C" LONG plAllocPrivateSemaphore(HANDLE *Semaphore, LONG InitialValue) +extern "C" ERR plAllocPrivateSemaphore(HANDLE *Semaphore, LONG InitialValue) { SECURITY_ATTRIBUTES security = { .nLength = sizeof(SECURITY_ATTRIBUTES), .lpSecurityDescriptor = NULL, .bInheritHandle = FALSE }; - if (!(*Semaphore = CreateSemaphore(&security, 0, InitialValue, NULL))) return ERR_Failed; - else return ERR_Okay; + if (!(*Semaphore = CreateSemaphore(&security, 0, InitialValue, NULL))) return ERR::Failed; + else return ERR::Okay; } extern "C" void plFreePrivateSemaphore(HANDLE *Semaphore) @@ -569,7 +569,7 @@ static HANDLE handle_cache(LONG OtherProcess, HANDLE OtherHandle, BYTE *Free) //******************************************************************************************************************** // The SysLock() function uses these publicly accessible handles for synchronising Core processes. -extern "C" int alloc_public_waitlock(HANDLE *Lock, const char *Name) +extern "C" ERR alloc_public_waitlock(HANDLE *Lock, const char *Name) { #ifdef WAITLOCK_EVENTS HANDLE event; @@ -577,7 +577,7 @@ extern "C" int alloc_public_waitlock(HANDLE *Lock, const char *Name) if (Name) { if ((event = OpenEvent(SYNCHRONIZE|EVENT_MODIFY_STATE, FALSE, Name))) { *Lock = event; - return ERR_Okay; + return ERR::Okay; } } @@ -588,17 +588,17 @@ extern "C" int alloc_public_waitlock(HANDLE *Lock, const char *Name) if ((event = CreateEvent(&sa, FALSE, FALSE, Name))) { *Lock = event; - return ERR_Okay; + return ERR::Okay; } - else return ERR_SystemCall; + else return ERR::SystemCall; #else SECURITY_ATTRIBUTES security; security.nLength = sizeof(SECURITY_ATTRIBUTES); security.lpSecurityDescriptor = NULL; security.bInheritHandle = FALSE; - if ((*Lock = CreateSemaphore(&security, 0, 1, Name))) return ERR_Okay; - else return ERR_SystemCall; + if ((*Lock = CreateSemaphore(&security, 0, 1, Name))) return ERR::Okay; + else return ERR::SystemCall; #endif } @@ -607,24 +607,24 @@ extern "C" void free_public_waitlock(HANDLE Lock) CloseHandle(Lock); } -extern "C" LONG wake_waitlock(HANDLE Lock, LONG TotalSleepers) +extern "C" ERR wake_waitlock(HANDLE Lock, LONG TotalSleepers) { - if (!Lock) return ERR_NullArgs; + if (!Lock) return ERR::NullArgs; - LONG error = ERR_Okay; + ERR error = ERR::Okay; #ifdef WAITLOCK_EVENTS while (TotalSleepers-- > 0) { if (!SetEvent(Lock)) { char msg[100]; fprintf(stderr, "SetEvent() failed: %s\n", winFormatMessage(GetLastError(), msg, sizeof(msg))); - error = ERR_SystemCall; + error = ERR::SystemCall; break; } } #else LONG prev; - if (!ReleaseSemaphore(Lock, 1, &prev)) error = ERR_SystemCall; + if (!ReleaseSemaphore(Lock, 1, &prev)) error = ERR::SystemCall; #endif return error; @@ -990,7 +990,7 @@ extern "C" LONG winWritePipe(HANDLE FD, APTR Buffer, DWORD *Size) //******************************************************************************************************************** // Used by class_thread.c only. -extern "C" LONG winCreatePipe(HANDLE *Read, HANDLE *Write) +extern "C" ERR winCreatePipe(HANDLE *Read, HANDLE *Write) { SECURITY_ATTRIBUTES sa; @@ -999,9 +999,9 @@ extern "C" LONG winCreatePipe(HANDLE *Read, HANDLE *Write) sa.bInheritHandle = FALSE; if (CreatePipe(Read, Write, &sa, 0)) { - return ERR_Okay; + return ERR::Okay; } - else return ERR_Failed; + else return ERR::Failed; } //******************************************************************************************************************** @@ -1087,10 +1087,10 @@ extern "C" void winTerminateThread(HANDLE Handle) //******************************************************************************************************************** -extern "C" LONG winWaitThread(HANDLE Handle, LONG TimeOut) +extern "C" ERR winWaitThread(HANDLE Handle, LONG TimeOut) { - if (WaitForSingleObject(Handle, TimeOut) IS WAIT_TIMEOUT) return ERR_TimeOut; - else return ERR_Okay; + if (WaitForSingleObject(Handle, TimeOut) IS WAIT_TIMEOUT) return ERR::TimeOut; + else return ERR::Okay; } //******************************************************************************************************************** @@ -1185,16 +1185,16 @@ extern "C" void winSelect(int FD, char *Read, char *Write) static BOOL CALLBACK TerminateAppEnum( HWND hwnd, LPARAM lParam ) ; -extern "C" int winTerminateApp(int dwPID, int dwTimeout) +extern "C" ERR winTerminateApp(int dwPID, int dwTimeout) { HANDLE hProc ; - int dwRet ; + ERR dwRet; // If we can't open the process with PROCESS_TERMINATE rights, then we give up immediately. hProc = OpenProcess(SYNCHRONIZE|PROCESS_TERMINATE, FALSE, dwPID); - if (hProc IS NULL) return ERR_Failed; + if (hProc IS NULL) return ERR::Failed; // TerminateAppEnum() posts WM_CLOSE to all windows whose PID matches your process's. @@ -1203,9 +1203,9 @@ extern "C" int winTerminateApp(int dwPID, int dwTimeout) // Wait on the handle. If it signals, great. If it times out, then you kill it. if (WaitForSingleObject(hProc, dwTimeout) != WAIT_OBJECT_0) { - dwRet = (TerminateProcess(hProc,0) ? ERR_Okay : ERR_Failed); + dwRet = (TerminateProcess(hProc,0) ? ERR::Okay : ERR::Failed); } - else dwRet = ERR_Okay; + else dwRet = ERR::Okay; CloseHandle(hProc); return dwRet; @@ -1347,12 +1347,12 @@ static void convert_time(FILETIME *Source, struct DateTime *Dest) //******************************************************************************************************************** -extern "C" int winGetFileAttributesEx(const char *Path, BYTE *Hidden, BYTE *ReadOnly, BYTE *Archive, BYTE *Folder, LARGE *Size, +extern "C" ERR winGetFileAttributesEx(const char *Path, BYTE *Hidden, BYTE *ReadOnly, BYTE *Archive, BYTE *Folder, LARGE *Size, struct DateTime *LastWrite, struct DateTime *LastAccess, struct DateTime *LastCreate) { WIN32_FILE_ATTRIBUTE_DATA info; - if (!GetFileAttributesEx(Path, GetFileExInfoStandard, &info)) return ERR_Failed; + if (!GetFileAttributesEx(Path, GetFileExInfoStandard, &info)) return ERR::Failed; if (info.dwFileAttributes & FILE_ATTRIBUTE_HIDDEN) *Hidden = TRUE; else *Hidden = FALSE; @@ -1376,19 +1376,19 @@ extern "C" int winGetFileAttributesEx(const char *Path, BYTE *Hidden, BYTE *Read if (LastAccess) convert_time(&info.ftLastWriteTime, LastAccess); if (LastCreate) convert_time(&info.ftLastWriteTime, LastCreate); - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -extern "C" int winCreateDir(const char *Path) +extern "C" ERR winCreateDir(const char *Path) { - if (auto result = CreateDirectory(Path, NULL)) return ERR_Okay; + if (auto result = CreateDirectory(Path, NULL)) return ERR::Okay; else { result = GetLastError(); - if (result IS ERROR_ALREADY_EXISTS) return ERR_FileExists; - else if (result IS ERROR_PATH_NOT_FOUND) return ERR_FileNotFound; - else return ERR_Failed; + if (result IS ERROR_ALREADY_EXISTS) return ERR::FileExists; + else if (result IS ERROR_PATH_NOT_FOUND) return ERR::FileNotFound; + else return ERR::Failed; } } @@ -1462,9 +1462,9 @@ extern "C" void winSetDllDirectory(LPCSTR Path) //******************************************************************************************************************** -extern "C" LONG winWatchFile(LONG Flags, CSTRING Path, APTR WatchBuffer, HANDLE *Handle, LONG *WinFlags) +extern "C" ERR winWatchFile(LONG Flags, CSTRING Path, APTR WatchBuffer, HANDLE *Handle, LONG *WinFlags) { - if ((!Path) or (!Path[0])) return ERR_Args; + if ((!Path) or (!Path[0])) return ERR::Args; LONG nflags = 0; if (Flags & MFF_READ) nflags |= FILE_NOTIFY_CHANGE_LAST_ACCESS; @@ -1498,19 +1498,19 @@ extern "C" LONG winWatchFile(LONG Flags, CSTRING Path, APTR WatchBuffer, HANDLE CloseHandle(*Handle); *Handle = NULL; - return ERR_SystemCall; + return ERR::SystemCall; } } *WinFlags = nflags; - return ERR_Okay; + return ERR::Okay; } - else return ERR_NoSupport; + else return ERR::NoSupport; } //******************************************************************************************************************** -extern "C" LONG winReadChanges(HANDLE Handle, APTR WatchBuffer, LONG NotifyFlags, char *PathOutput, LONG PathSize, LONG *Status) +extern "C" ERR winReadChanges(HANDLE Handle, APTR WatchBuffer, LONG NotifyFlags, char *PathOutput, LONG PathSize, LONG *Status) { DWORD bytes_out; auto ovlap = (OVERLAPPED *)WatchBuffer; @@ -1535,11 +1535,11 @@ extern "C" LONG winReadChanges(HANDLE Handle, APTR WatchBuffer, LONG NotifyFlags DWORD empty; ReadDirectoryChangesW(Handle, fni, sizeof(FILE_NOTIFY_INFORMATION) + MAX_PATH - 1, TRUE, NotifyFlags, &empty, ovlap, NULL); - return ERR_Okay; + return ERR::Okay; } - else return ERR_NothingDone; + else return ERR::NothingDone; } - else return ERR_NothingDone; + else return ERR::NothingDone; } //******************************************************************************************************************** @@ -1783,7 +1783,7 @@ extern "C" LONG winTestLocation(STRING Location, BYTE CaseSensitive) //******************************************************************************************************************** -extern "C" LONG delete_tree(STRING Path, int Size, struct FileFeedback *Feedback) +extern "C" ERR delete_tree(STRING Path, int Size, struct FileFeedback *Feedback) { LONG len, cont, i; WIN32_FIND_DATA find; @@ -1792,8 +1792,8 @@ extern "C" LONG delete_tree(STRING Path, int Size, struct FileFeedback *Feedback if (Feedback) { Feedback->Path = Path; i = CALL_FEEDBACK(Feedback); - if (i IS FFR_ABORT) return ERR_Cancelled; - else if (i IS FFR_SKIP) return ERR_Okay; + if (i IS FFR_ABORT) return ERR::Cancelled; + else if (i IS FFR_SKIP) return ERR::Okay; } for (len=0; Path[len]; len++); @@ -1842,17 +1842,17 @@ extern "C" LONG delete_tree(STRING Path, int Size, struct FileFeedback *Feedback } if (attrib & FILE_ATTRIBUTE_DIRECTORY) { - if (RemoveDirectory(Path)) return ERR_Okay; - else return ERR_Failed; + if (RemoveDirectory(Path)) return ERR::Okay; + else return ERR::Failed; } else if (!unlink(Path)) { - return ERR_Okay; + return ERR::Okay; } else { #ifdef __CYGWIN__ - return convert_errno(*__errno(), ERR_Failed); + return convert_errno(*__errno(), ERR::Failed); #else - return convert_errno(errno, ERR_Failed); + return convert_errno(errno, ERR::Failed); #endif } } diff --git a/src/core/prototypes.h b/src/core/prototypes.h index 7f39d9a40..773d681d8 100644 --- a/src/core/prototypes.h +++ b/src/core/prototypes.h @@ -1,105 +1,105 @@ // Auto-generated by idl-c.fluid extern "C" { -ERROR AccessMemory(MEMORYID Memory, MEM Flags, LONG MilliSeconds, APTR * Result); -ERROR Action(LONG Action, OBJECTPTR Object, APTR Parameters); +ERR AccessMemory(MEMORYID Memory, MEM Flags, LONG MilliSeconds, APTR * Result); +ERR Action(LONG Action, OBJECTPTR Object, APTR Parameters); void ActionList(struct ActionTable ** Actions, LONG * Size); -ERROR ActionMsg(LONG Action, OBJECTID Object, APTR Args); +ERR ActionMsg(LONG Action, OBJECTID Object, APTR Args); CSTRING ResolveClassID(CLASSID ID); LONG AllocateID(IDTYPE Type); -ERROR AllocMemory(LONG Size, MEM Flags, APTR * Address, MEMORYID * ID); -ERROR AccessObject(OBJECTID Object, LONG MilliSeconds, OBJECTPTR * Result); -ERROR CheckAction(OBJECTPTR Object, LONG Action); -ERROR CheckMemoryExists(MEMORYID ID); -ERROR CheckObjectExists(OBJECTID Object); -ERROR InitObject(OBJECTPTR Object); -ERROR VirtualVolume(CSTRING Name, ...); +ERR AllocMemory(LONG Size, MEM Flags, APTR * Address, MEMORYID * ID); +ERR AccessObject(OBJECTID Object, LONG MilliSeconds, OBJECTPTR * Result); +ERR CheckAction(OBJECTPTR Object, LONG Action); +ERR CheckMemoryExists(MEMORYID ID); +ERR CheckObjectExists(OBJECTID Object); +ERR InitObject(OBJECTPTR Object); +ERR VirtualVolume(CSTRING Name, ...); OBJECTPTR CurrentContext(); -ERROR GetFieldArray(OBJECTPTR Object, FIELD Field, APTR * Result, LONG * Elements); +ERR GetFieldArray(OBJECTPTR Object, FIELD Field, APTR * Result, LONG * Elements); LONG AdjustLogLevel(LONG Adjust); -ERROR ReadFileToBuffer(CSTRING Path, APTR Buffer, LONG BufferSize, LONG * Result); -ERROR FindObject(CSTRING Name, CLASSID ClassID, FOF Flags, OBJECTID * ObjectID); +ERR ReadFileToBuffer(CSTRING Path, APTR Buffer, LONG BufferSize, LONG * Result); +ERR FindObject(CSTRING Name, CLASSID ClassID, FOF Flags, OBJECTID * ObjectID); objMetaClass * FindClass(CLASSID ClassID); -ERROR AnalysePath(CSTRING Path, LOC * Type); +ERR AnalysePath(CSTRING Path, LOC * Type); LONG UTF8Copy(CSTRING Src, STRING Dest, LONG Chars, LONG Size); -ERROR FreeResource(MEMORYID ID); +ERR FreeResource(MEMORYID ID); CLASSID GetClassID(OBJECTID Object); OBJECTID GetOwnerID(OBJECTID Object); -ERROR GetField(OBJECTPTR Object, FIELD Field, APTR Result); -ERROR GetFieldVariable(OBJECTPTR Object, CSTRING Field, STRING Buffer, LONG Size); -ERROR CompareFilePaths(CSTRING PathA, CSTRING PathB); +ERR GetField(OBJECTPTR Object, FIELD Field, APTR Result); +ERR GetFieldVariable(OBJECTPTR Object, CSTRING Field, STRING Buffer, LONG Size); +ERR CompareFilePaths(CSTRING PathA, CSTRING PathB); const struct SystemState * GetSystemState(); -ERROR ListChildren(OBJECTID Object, pf::vector * List); -ERROR Base64Decode(struct pfBase64Decode * State, CSTRING Input, LONG InputSize, APTR Output, LONG * Written); -ERROR RegisterFD(HOSTHANDLE FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR) , APTR Data); -ERROR ResolvePath(CSTRING Path, RSF Flags, STRING * Result); -ERROR MemoryIDInfo(MEMORYID ID, struct MemInfo * MemInfo, LONG Size); -ERROR MemoryPtrInfo(APTR Address, struct MemInfo * MemInfo, LONG Size); -ERROR NewObject(LARGE ClassID, NF Flags, OBJECTPTR * Object); -void NotifySubscribers(OBJECTPTR Object, LONG Action, APTR Args, ERROR Error); -ERROR StrReadLocale(CSTRING Key, CSTRING * Value); +ERR ListChildren(OBJECTID Object, pf::vector * List); +ERR Base64Decode(struct pfBase64Decode * State, CSTRING Input, LONG InputSize, APTR Output, LONG * Written); +ERR RegisterFD(HOSTHANDLE FD, RFD Flags, void (*Routine)(HOSTHANDLE, APTR) , APTR Data); +ERR ResolvePath(CSTRING Path, RSF Flags, STRING * Result); +ERR MemoryIDInfo(MEMORYID ID, struct MemInfo * MemInfo, LONG Size); +ERR MemoryPtrInfo(APTR Address, struct MemInfo * MemInfo, LONG Size); +ERR NewObject(LARGE ClassID, NF Flags, OBJECTPTR * Object); +void NotifySubscribers(OBJECTPTR Object, LONG Action, APTR Args, ERR Error); +ERR StrReadLocale(CSTRING Key, CSTRING * Value); CSTRING UTF8ValidEncoding(CSTRING String, CSTRING Encoding); -ERROR ProcessMessages(PMF Flags, LONG TimeOut); -ERROR IdentifyFile(CSTRING Path, CLASSID * Class, CLASSID * SubClass); -ERROR ReallocMemory(APTR Memory, ULONG Size, APTR * Address, MEMORYID * ID); -ERROR GetMessage(LONG Type, MSF Flags, APTR Buffer, LONG Size); -ERROR ReleaseMemory(MEMORYID MemoryID); +ERR ProcessMessages(PMF Flags, LONG TimeOut); +ERR IdentifyFile(CSTRING Path, CLASSID * Class, CLASSID * SubClass); +ERR ReallocMemory(APTR Memory, ULONG Size, APTR * Address, MEMORYID * ID); +ERR GetMessage(LONG Type, MSF Flags, APTR Buffer, LONG Size); +ERR ReleaseMemory(MEMORYID MemoryID); CLASSID ResolveClassName(CSTRING Name); -ERROR SendMessage(LONG Type, MSF Flags, APTR Data, LONG Size); -ERROR SetOwner(OBJECTPTR Object, OBJECTPTR Owner); +ERR SendMessage(LONG Type, MSF Flags, APTR Data, LONG Size); +ERR SetOwner(OBJECTPTR Object, OBJECTPTR Owner); OBJECTPTR SetContext(OBJECTPTR Object); -ERROR SetField(OBJECTPTR Object, FIELD Field, ...); +ERR SetField(OBJECTPTR Object, FIELD Field, ...); CSTRING FieldName(ULONG FieldID); -ERROR ScanDir(struct DirInfo * Info); -ERROR SetName(OBJECTPTR Object, CSTRING Name); +ERR ScanDir(struct DirInfo * Info); +ERR SetName(OBJECTPTR Object, CSTRING Name); void LogReturn(); -ERROR StrCompare(CSTRING String1, CSTRING String2, LONG Length, STR Flags); -ERROR SubscribeAction(OBJECTPTR Object, LONG Action, FUNCTION * Callback); -ERROR SubscribeEvent(LARGE Event, FUNCTION * Callback, APTR Custom, APTR * Handle); -ERROR SubscribeTimer(DOUBLE Interval, FUNCTION * Callback, APTR * Subscription); -ERROR UpdateTimer(APTR Subscription, DOUBLE Interval); -ERROR UnsubscribeAction(OBJECTPTR Object, LONG Action); +ERR StrCompare(CSTRING String1, CSTRING String2, LONG Length, STR Flags); +ERR SubscribeAction(OBJECTPTR Object, LONG Action, FUNCTION * Callback); +ERR SubscribeEvent(LARGE Event, FUNCTION * Callback, APTR Custom, APTR * Handle); +ERR SubscribeTimer(DOUBLE Interval, FUNCTION * Callback, APTR * Subscription); +ERR UpdateTimer(APTR Subscription, DOUBLE Interval); +ERR UnsubscribeAction(OBJECTPTR Object, LONG Action); void UnsubscribeEvent(APTR Handle); -ERROR BroadcastEvent(APTR Event, LONG EventSize); +ERR BroadcastEvent(APTR Event, LONG EventSize); void WaitTime(LONG Seconds, LONG MicroSeconds); LARGE GetEventID(EVG Group, CSTRING SubGroup, CSTRING Event); ULONG GenCRC32(ULONG CRC, APTR Data, ULONG Length); LARGE GetResource(RES Resource); LARGE SetResource(RES Resource, LARGE Value); -ERROR ScanMessages(LONG * Handle, LONG Type, APTR Buffer, LONG Size); +ERR ScanMessages(LONG * Handle, LONG Type, APTR Buffer, LONG Size); STT StrDatatype(CSTRING String); void UnloadFile(struct CacheFile * Cache); -ERROR CreateFolder(CSTRING Path, PERMIT Permissions); -ERROR LoadFile(CSTRING Path, LDF Flags, struct CacheFile ** Cache); -ERROR SetVolume(CSTRING Name, CSTRING Path, CSTRING Icon, CSTRING Label, CSTRING Device, VOLUME Flags); -ERROR DeleteVolume(CSTRING Name); -ERROR MoveFile(CSTRING Source, CSTRING Dest, FUNCTION * Callback); -ERROR UpdateMessage(LONG Message, LONG Type, APTR Data, LONG Size); -ERROR AddMsgHandler(APTR Custom, LONG MsgType, FUNCTION * Routine, struct MsgHandler ** Handle); -ERROR QueueAction(LONG Action, OBJECTID Object, APTR Args); +ERR CreateFolder(CSTRING Path, PERMIT Permissions); +ERR LoadFile(CSTRING Path, LDF Flags, struct CacheFile ** Cache); +ERR SetVolume(CSTRING Name, CSTRING Path, CSTRING Icon, CSTRING Label, CSTRING Device, VOLUME Flags); +ERR DeleteVolume(CSTRING Name); +ERR MoveFile(CSTRING Source, CSTRING Dest, FUNCTION * Callback); +ERR UpdateMessage(LONG Message, LONG Type, APTR Data, LONG Size); +ERR AddMsgHandler(APTR Custom, LONG MsgType, FUNCTION * Routine, struct MsgHandler ** Handle); +ERR QueueAction(LONG Action, OBJECTID Object, APTR Args); LARGE PreciseTime(); -ERROR OpenDir(CSTRING Path, RDF Flags, struct DirInfo ** Info); +ERR OpenDir(CSTRING Path, RDF Flags, struct DirInfo ** Info); OBJECTPTR GetObjectPtr(OBJECTID Object); struct Field * FindField(OBJECTPTR Object, ULONG FieldID, OBJECTPTR * Target); -CSTRING GetErrorMsg(ERROR Error); +CSTRING GetErrorMsg(ERR Error); struct Message * GetActionMsg(); -ERROR FuncError(CSTRING Header, ERROR Error); -ERROR SetArray(OBJECTPTR Object, FIELD Field, APTR Array, LONG Elements); +ERR FuncError(CSTRING Header, ERR Error); +ERR SetArray(OBJECTPTR Object, FIELD Field, APTR Array, LONG Elements); ULONG StrHash(CSTRING String, LONG CaseSensitive); -ERROR LockObject(OBJECTPTR Object, LONG MilliSeconds); +ERR LockObject(OBJECTPTR Object, LONG MilliSeconds); void ReleaseObject(OBJECTPTR Object); -ERROR ActionThread(LONG Action, OBJECTPTR Object, APTR Args, FUNCTION * Callback, LONG Key); -ERROR AddInfoTag(struct FileInfo * Info, CSTRING Name, CSTRING Value); +ERR ActionThread(LONG Action, OBJECTPTR Object, APTR Args, FUNCTION * Callback, LONG Key); +ERR AddInfoTag(struct FileInfo * Info, CSTRING Name, CSTRING Value); void SetDefaultPermissions(LONG User, LONG Group, PERMIT Permissions); void VLogF(VLF Flags, CSTRING Header, CSTRING Message, va_list Args); LONG Base64Encode(struct pfBase64Encode * State, const void * Input, LONG InputSize, STRING Output, LONG OutputSize); -ERROR ReadInfoTag(struct FileInfo * Info, CSTRING Name, CSTRING * Value); -ERROR SetResourcePath(RP PathType, CSTRING Path); +ERR ReadInfoTag(struct FileInfo * Info, CSTRING Name, CSTRING * Value); +ERR SetResourcePath(RP PathType, CSTRING Path); objTask * CurrentTask(); CSTRING ResolveGroupID(LONG Group); CSTRING ResolveUserID(LONG User); -ERROR CreateLink(CSTRING From, CSTRING To); -ERROR DeleteFile(CSTRING Path, FUNCTION * Callback); +ERR CreateLink(CSTRING From, CSTRING To); +ERR DeleteFile(CSTRING Path, FUNCTION * Callback); LONG UTF8CharOffset(CSTRING String, LONG Offset); LONG UTF8Length(CSTRING String); LONG UTF8OffsetToChar(CSTRING String, LONG Offset); @@ -107,7 +107,7 @@ LONG UTF8PrevLength(CSTRING String, LONG Offset); LONG UTF8CharLength(CSTRING String); ULONG UTF8ReadValue(CSTRING String, LONG * Length); LONG UTF8WriteValue(LONG Value, STRING Buffer, LONG Size); -ERROR CopyFile(CSTRING Source, CSTRING Dest, FUNCTION * Callback); -ERROR WaitForObjects(PMF Flags, LONG TimeOut, struct ObjectSignal * ObjectSignals); +ERR CopyFile(CSTRING Source, CSTRING Dest, FUNCTION * Callback); +ERR WaitForObjects(PMF Flags, LONG TimeOut, struct ObjectSignal * ObjectSignals); } // extern c diff --git a/src/core/static_modules.cpp b/src/core/static_modules.cpp index 0544a9f9a..987f00da6 100644 --- a/src/core/static_modules.cpp +++ b/src/core/static_modules.cpp @@ -3,6 +3,7 @@ extern "C" ModHeader * register_audio_module(); extern "C" ModHeader * register_display_module(); +extern "C" ModHeader * register_document_module(); extern "C" ModHeader * register_fluid_module(); extern "C" ModHeader * register_font_module(); extern "C" ModHeader * register_http_module(); @@ -30,6 +31,10 @@ static void register_static_modules(void) glStaticModules["display"] = register_display_module(); #endif + #ifdef INC_MOD_DOCUMENT + glStaticModules["document"] = register_document_module(); + #endif + #ifdef INC_MOD_FLUID glStaticModules["fluid"] = register_fluid_module(); #endif diff --git a/src/display/class_bitmap.cpp b/src/display/class_bitmap.cpp index 3d41cedfe..7f7a5d68c 100644 --- a/src/display/class_bitmap.cpp +++ b/src/display/class_bitmap.cpp @@ -50,7 +50,7 @@ DLLCALL LONG WINAPI SetPixel(APTR, LONG, LONG, LONG); DLLCALL LONG WINAPI GetPixel(APTR, LONG, LONG); #endif -static LONG CalculatePixelRoutines(extBitmap *); +static ERR CalculatePixelRoutines(extBitmap *); //******************************************************************************************************************** // Pixel and pen based functions. @@ -147,15 +147,15 @@ static void DrawRGBPixelPlanar(objBitmap *, LONG X, LONG Y, RGB8 *); //******************************************************************************************************************** -static ERROR GET_Handle(extBitmap *, APTR *); +static ERR GET_Handle(extBitmap *, APTR *); -static ERROR SET_Bkgd(extBitmap *, RGB8 *); -static ERROR SET_BkgdIndex(extBitmap *, LONG); -static ERROR SET_Trans(extBitmap *, RGB8 *); -static ERROR SET_TransIndex(extBitmap *, LONG); -static ERROR SET_Data(extBitmap *, UBYTE *); -static ERROR SET_Handle(extBitmap *, APTR); -static ERROR SET_Palette(extBitmap *, RGBPalette *); +static ERR SET_Bkgd(extBitmap *, RGB8 *); +static ERR SET_BkgdIndex(extBitmap *, LONG); +static ERR SET_Trans(extBitmap *, RGB8 *); +static ERR SET_TransIndex(extBitmap *, LONG); +static ERR SET_Data(extBitmap *, UBYTE *); +static ERR SET_Handle(extBitmap *, APTR); +static ERR SET_Palette(extBitmap *, RGBPalette *); static const FieldDef clDataFlags[] = { { "Video", MEM::VIDEO }, { "Blit", MEM::TEXTURE }, { "NoClear", MEM::NO_CLEAR }, { "Data", 0 }, @@ -180,31 +180,31 @@ FDEF argsReadUCRIndex[] = { { "Void", FD_VOID }, { "Bitmap", FD_OBJECTPTR }, { #ifdef _WIN32 -ERROR lock_surface(extBitmap *Bitmap, WORD Access) +ERR lock_surface(extBitmap *Bitmap, WORD Access) { if (!Bitmap->Data) { pf::Log log(__FUNCTION__); log.warning("[Bitmap:%d] Bitmap is missing the Data field.", Bitmap->UID); - return ERR_FieldNotSet; + return ERR::FieldNotSet; } - return ERR_Okay; + return ERR::Okay; } -ERROR unlock_surface(extBitmap *Bitmap) +ERR unlock_surface(extBitmap *Bitmap) { - return ERR_Okay; + return ERR::Okay; } #elif __xwindows__ -ERROR lock_surface(extBitmap *Bitmap, WORD Access) +ERR lock_surface(extBitmap *Bitmap, WORD Access) { LONG size; WORD alignment; if (((Bitmap->Flags & BMF::X11_DGA) != BMF::NIL) and (glDGAAvailable)) { - return ERR_Okay; + return ERR::Okay; } else if ((Bitmap->x11.drawable) and (Access & SURFACE_READ)) { // If there is an existing readable area, try to reuse it if possible @@ -216,7 +216,7 @@ ERROR lock_surface(extBitmap *Bitmap, WORD Access) Bitmap->Clip.Bottom - Bitmap->Clip.Top, 0xffffffff, ZPixmap, Bitmap->x11.readable, Bitmap->XOffset + Bitmap->Clip.Left, Bitmap->YOffset + Bitmap->Clip.Top); } - return ERR_Okay; + return ERR::Okay; } else XDestroyImage(Bitmap->x11.readable); } @@ -242,21 +242,21 @@ ERROR lock_surface(extBitmap *Bitmap, WORD Access) Bitmap->Clip.Bottom - Bitmap->Clip.Top, 0xffffffff, ZPixmap, Bitmap->x11.readable, Bitmap->XOffset + Bitmap->Clip.Left, Bitmap->YOffset + Bitmap->Clip.Top); } - return ERR_Okay; + return ERR::Okay; } - else return ERR_Failed; + else return ERR::Failed; } - return ERR_Okay; + return ERR::Okay; } -ERROR unlock_surface(extBitmap *Bitmap) +ERR unlock_surface(extBitmap *Bitmap) { - return ERR_Okay; + return ERR::Okay; } #elif _GLES_ -ERROR lock_surface(extBitmap *Bitmap, WORD Access) +ERR lock_surface(extBitmap *Bitmap, WORD Access) { pf::Log log(__FUNCTION__); @@ -270,8 +270,8 @@ ERROR lock_surface(extBitmap *Bitmap, WORD Access) log.warning("Warning: Locking of OpenGL video surfaces for CPU access is bad practice (bitmap: #%d, mem: $%.8x)", Bitmap->UID, Bitmap->DataFlags); if (!Bitmap->Data) { - if (AllocMemory(Bitmap->Size, MEM::NO_BLOCKING|MEM::NO_POOL|MEM::NO_CLEAR|Bitmap->DataFlags, &Bitmap->Data) != ERR_Okay) { - return log.warning(ERR_AllocMemory); + if (AllocMemory(Bitmap->Size, MEM::NO_BLOCKING|MEM::NO_POOL|MEM::NO_CLEAR|Bitmap->DataFlags, &Bitmap->Data) != ERR::Okay) { + return log.warning(ERR::AllocMemory); } Bitmap->prvAFlags |= BF_DATA; } @@ -288,24 +288,24 @@ ERROR lock_surface(extBitmap *Bitmap, WORD Access) unlock_graphics(); } - return ERR_Okay; + return ERR::Okay; } else if ((Bitmap->DataFlags & MEM::TEXTURE) != MEM::NIL) { // Using the CPU on BLIT bitmaps is banned - it is considered to be poor programming. Instead, // MEM::DATA bitmaps should be used when R/W CPU access is desired to a bitmap. - return log.warning(ERR_NoSupport); + return log.warning(ERR::NoSupport); } if (!Bitmap->Data) { log.warning("[Bitmap:%d] Bitmap is missing the Data field. Memory flags: $%.8x", Bitmap->UID, Bitmap->DataFlags); - return ERR_FieldNotSet; + return ERR::FieldNotSet; } - return ERR_Okay; + return ERR::Okay; } -ERROR unlock_surface(extBitmap *Bitmap) +ERR unlock_surface(extBitmap *Bitmap) { if (((Bitmap->DataFlags & MEM::VIDEO) != MEM::NIL) and (Bitmap->prvWriteBackBuffer)) { if (!lock_graphics_active(__func__)) { @@ -327,11 +327,11 @@ ERROR unlock_surface(extBitmap *Bitmap) glBindTexture(GL_TEXTURE_2D, 0); eglSwapBuffers(glEGLDisplay, glEGLSurface); } - else log.warning(ERR_OpenGL); + else log.warning(ERR::OpenGL); glDeleteTextures(1, &texture_id); } - else log.warning(ERR_OpenGL); + else log.warning(ERR::OpenGL); #endif unlock_graphics(); @@ -340,7 +340,7 @@ ERROR unlock_surface(extBitmap *Bitmap) Bitmap->prvWriteBackBuffer = FALSE; } - return ERR_Okay; + return ERR::Okay; } #endif @@ -348,25 +348,25 @@ ERROR unlock_surface(extBitmap *Bitmap) //******************************************************************************************************************** #ifdef __xwindows__ -static ERROR alloc_shm(LONG Size, UBYTE **Data, LONG *ID) +static ERR alloc_shm(LONG Size, UBYTE **Data, LONG *ID) { pf::Log log(__FUNCTION__); auto id = shmget(IPC_PRIVATE, Size, IPC_CREAT|IPC_EXCL|S_IRWXO|S_IRWXG|S_IRWXU); if (id IS -1) { log.warning("shmget() returned: %s", strerror(errno)); - return ERR_Memory; + return ERR::Memory; } auto addr = shmat(id, NULL, 0); if ((addr != (APTR)-1) and (addr != NULL)) { *Data = (UBYTE *)addr; *ID = id; - return ERR_Okay; + return ERR::Okay; } else { log.warning("shmat() returned: %s", strerror(errno)); - return ERR_LockFailed; + return ERR::LockFailed; } } @@ -436,7 +436,7 @@ If the bitmap supports alpha blending, the alpha blend bits will be reset to 'cl *********************************************************************************************************************/ -static ERROR BITMAP_Clear(extBitmap *Self, APTR Void) +static ERR BITMAP_Clear(extBitmap *Self, APTR Void) { #ifdef _GLES_ if ((Self->DataFlags & MEM::VIDEO) != MEM::NIL) { @@ -444,9 +444,9 @@ static ERROR BITMAP_Clear(extBitmap *Self, APTR Void) glClearColorx(Self->BkgdRGB.Red, Self->BkgdRGB.Green, Self->BkgdRGB.Blue, 255); glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT); unlock_graphics(); - return ERR_Okay; + return ERR::Okay; } - else return ERR_LockFailed; + else return ERR::LockFailed; } #endif @@ -454,7 +454,7 @@ static ERROR BITMAP_Clear(extBitmap *Self, APTR Void) Self->Opacity = 255; gfxDrawRectangle(Self, 0, 0, Self->Width, Self->Height, Self->BkgdIndex, BAF::FILL); Self->Opacity = opacity; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -485,18 +485,18 @@ CreateObject: A Compression object could not be created. *********************************************************************************************************************/ -static ERROR BITMAP_Compress(extBitmap *Self, struct bmpCompress *Args) +static ERR BITMAP_Compress(extBitmap *Self, struct bmpCompress *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); if ((Self->DataFlags & (MEM::VIDEO|MEM::TEXTURE)) != MEM::NIL) { log.warning("Cannot compress video bitmaps."); - return ERR_Failed; + return ERR::Failed; } - if (Self->Size < 8192) return ERR_Okay; + if (Self->Size < 8192) return ERR::Okay; log.traceBranch(""); @@ -508,36 +508,36 @@ static ERROR BITMAP_Compress(extBitmap *Self, struct bmpCompress *Args) Self->Data = NULL; } - return ERR_Okay; + return ERR::Okay; } - ERROR error = ERR_Okay; + ERR error = ERR::Okay; if (!glCompress) { if (!(glCompress = objCompression::create::global())) { - return log.warning(ERR_CreateObject); + return log.warning(ERR::CreateObject); } SetOwner(glCompress, glModule); } APTR buffer; - if (!AllocMemory(Self->Size, MEM::NO_CLEAR, &buffer)) { + if (AllocMemory(Self->Size, MEM::NO_CLEAR, &buffer) IS ERR::Okay) { struct cmpCompressBuffer cbuf; cbuf.Input = Self->Data; cbuf.InputSize = Self->Size; cbuf.Output = buffer; cbuf.OutputSize = Self->Size; - if (!Action(MT_CmpCompressBuffer, glCompress, &cbuf)) { - if (!AllocMemory(cbuf.Result, MEM::NO_CLEAR, &Self->prvCompress)) { + if (Action(MT_CmpCompressBuffer, glCompress, &cbuf) IS ERR::Okay) { + if (AllocMemory(cbuf.Result, MEM::NO_CLEAR, &Self->prvCompress) IS ERR::Okay) { CopyMemory(buffer, Self->prvCompress, cbuf.Result); FreeResource(buffer); } - else error = ERR_ReallocMemory; + else error = ERR::ReallocMemory; } - else error = ERR_Failed; + else error = ERR::Failed; } - else error = ERR_AllocMemory; + else error = ERR::AllocMemory; - if (!error) { // Free the original data + if (error IS ERR::Okay) { // Free the original data if ((Self->Data) and (Self->prvAFlags & BF_DATA)) { FreeResource(Self->Data); Self->Data = NULL; @@ -569,18 +569,18 @@ InvalidDimension: The clipping region is invalid. -END- *********************************************************************************************************************/ -ERROR BITMAP_ConvertToLinear(extBitmap *Self, APTR Void) +ERR BITMAP_ConvertToLinear(extBitmap *Self, APTR Void) { pf::Log log; - if (Self->ColourSpace IS CS::LINEAR_RGB) return log.warning(ERR_NothingDone); - if (Self->BytesPerPixel != 4) return log.warning(ERR_InvalidState); + if (Self->ColourSpace IS CS::LINEAR_RGB) return log.warning(ERR::NothingDone); + if (Self->BytesPerPixel != 4) return log.warning(ERR::InvalidState); const auto w = (LONG)(Self->Clip.Right - Self->Clip.Left); const auto h = (LONG)(Self->Clip.Bottom - Self->Clip.Top); - if (Self->Clip.Left + w > Self->Width) return log.warning(ERR_InvalidDimension); - if (Self->Clip.Top + h > Self->Height) return log.warning(ERR_InvalidDimension); + if (Self->Clip.Left + w > Self->Width) return log.warning(ERR::InvalidDimension); + if (Self->Clip.Top + h > Self->Height) return log.warning(ERR::InvalidDimension); if ((Self->Flags & BMF::ALPHA_CHANNEL) != BMF::NIL) { const UBYTE R = Self->ColourFormat->RedPos>>3; @@ -621,7 +621,7 @@ ERROR BITMAP_ConvertToLinear(extBitmap *Self, APTR Void) } Self->ColourSpace = CS::LINEAR_RGB; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -645,18 +645,18 @@ InvalidDimension: The clipping region is invalid. *********************************************************************************************************************/ -ERROR BITMAP_ConvertToRGB(extBitmap *Self, APTR Void) +ERR BITMAP_ConvertToRGB(extBitmap *Self, APTR Void) { pf::Log log(__FUNCTION__); - if (Self->ColourSpace IS CS::SRGB) return log.warning(ERR_NothingDone); - if (Self->BytesPerPixel != 4) return log.warning(ERR_InvalidState); + if (Self->ColourSpace IS CS::SRGB) return log.warning(ERR::NothingDone); + if (Self->BytesPerPixel != 4) return log.warning(ERR::InvalidState); const auto w = (LONG)(Self->Clip.Right - Self->Clip.Left); const auto h = (LONG)(Self->Clip.Bottom - Self->Clip.Top); - if (Self->Clip.Left + w > Self->Width) return log.warning(ERR_InvalidDimension); - if (Self->Clip.Top + h > Self->Height) return log.warning(ERR_InvalidDimension); + if (Self->Clip.Left + w > Self->Width) return log.warning(ERR::InvalidDimension); + if (Self->Clip.Top + h > Self->Height) return log.warning(ERR::InvalidDimension); if ((Self->Flags & BMF::ALPHA_CHANNEL) != BMF::NIL) { const UBYTE R = Self->ColourFormat->RedPos>>3; @@ -697,7 +697,7 @@ ERROR BITMAP_ConvertToRGB(extBitmap *Self, APTR Void) } Self->ColourSpace = CS::SRGB; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -724,10 +724,10 @@ Mismatch: The target bitmap is not a close enough match to the source bitmap in *********************************************************************************************************************/ -static ERROR BITMAP_CopyArea(objBitmap *Self, struct bmpCopyArea *Args) +static ERR BITMAP_CopyArea(objBitmap *Self, struct bmpCopyArea *Args) { if (Args) return gfxCopyArea((extBitmap *)Self, (extBitmap *)Args->DestBitmap, Args->Flags, Args->X, Args->Y, Args->Width, Args->Height, Args->XDest, Args->YDest); - else return ERR_NullArgs; + else return ERR::NullArgs; } /********************************************************************************************************************* @@ -750,28 +750,28 @@ AllocMemory: Insufficient memory in recreating the bitmap data buffer. *********************************************************************************************************************/ -static ERROR BITMAP_Decompress(extBitmap *Self, struct bmpDecompress *Args) +static ERR BITMAP_Decompress(extBitmap *Self, struct bmpDecompress *Args) { pf::Log log; struct cmpDecompressBuffer dbuf; - if (!Self->prvCompress) return ERR_Okay; + if (!Self->prvCompress) return ERR::Okay; - log.msg(VLF::BRANCH|VLF::EXTAPI, "Size: %d, Retain: %d", Self->Size, (Args) ? Args->RetainData : FALSE); + log.msg(VLF::BRANCH|VLF::DETAIL, "Size: %d, Retain: %d", Self->Size, (Args) ? Args->RetainData : FALSE); // Note: If the decompression fails, we'll keep the bitmap data in memory in order to stop code from failing if it // accesses the Data address following attempted decompression. if (!Self->Data) { - if (!AllocMemory(Self->Size, MEM::NO_BLOCKING|MEM::NO_POOL|MEM::NO_CLEAR|Self->DataFlags, &Self->Data)) { + if (AllocMemory(Self->Size, MEM::NO_BLOCKING|MEM::NO_POOL|MEM::NO_CLEAR|Self->DataFlags, &Self->Data) IS ERR::Okay) { Self->prvAFlags |= BF_DATA; } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } if (!glCompress) { if (!(glCompress = objCompression::create::global())) { - return log.warning(ERR_CreateObject); + return log.warning(ERR::CreateObject); } SetOwner(glCompress, glModule); } @@ -779,8 +779,8 @@ static ERROR BITMAP_Decompress(extBitmap *Self, struct bmpDecompress *Args) dbuf.Input = Self->prvCompress; dbuf.Output = Self->Data; dbuf.OutputSize = Self->Size; - ERROR error = Action(MT_CmpDecompressBuffer, glCompress, &dbuf); - if (error IS ERR_BufferOverflow) error = ERR_Okay; + ERR error = Action(MT_CmpDecompressBuffer, glCompress, &dbuf); + if (error IS ERR::BufferOverflow) error = ERR::Okay; if ((Args) and (Args->RetainData IS TRUE)) { // Keep the source compression data @@ -806,12 +806,12 @@ This action features automatic clipping and remapping, for occasions where the b *********************************************************************************************************************/ -static ERROR BITMAP_CopyData(extBitmap *Self, struct acCopyData *Args) +static ERR BITMAP_CopyData(extBitmap *Self, struct acCopyData *Args) { pf::Log log; - if ((!Args) or (!Args->Dest)) return log.warning(ERR_NullArgs); - if ((Args->Dest->Class->ClassID != ID_BITMAP)) return log.warning(ERR_Args); + if ((!Args) or (!Args->Dest)) return log.warning(ERR::NullArgs); + if ((Args->Dest->Class->ClassID != ID_BITMAP)) return log.warning(ERR::Args); auto target = (extBitmap *)Args->Dest; @@ -831,7 +831,7 @@ static ERROR BITMAP_CopyData(extBitmap *Self, struct acCopyData *Args) gfxDrawRectangle(target, 0, Self->Height, target->Width, target->Height - Self->Height, target->BkgdIndex, BAF::FILL); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -840,7 +840,8 @@ static ERROR BITMAP_CopyData(extBitmap *Self, struct acCopyData *Args) Demultiply: Reverses the conversion process performed by Premultiply(). Use Demultiply to normalise RGB values that have previously been converted by #Premultiply(). This method will -return immediately if the bitmap values are already normalised. +return immediately if the bitmap values are already normalised, as determined by the presence of the `PREMUL` value +in #Flags. -ERRORS- Okay @@ -850,7 +851,7 @@ InvalidDimension: The clipping region is invalid. *********************************************************************************************************************/ -static ERROR BITMAP_Demultiply(extBitmap *Self, APTR Void) +static ERR BITMAP_Demultiply(extBitmap *Self, APTR Void) { pf::Log log; @@ -858,26 +859,26 @@ static ERROR BITMAP_Demultiply(extBitmap *Self, APTR Void) if (!glDemultiply) { const std::lock_guard lock(mutex); if (!glDemultiply) { - if (!AllocMemory(256 * 256, MEM::NO_CLEAR|MEM::UNTRACKED, &glDemultiply)) { + if (AllocMemory(256 * 256, MEM::NO_CLEAR|MEM::UNTRACKED, &glDemultiply) IS ERR::Okay) { for (LONG a=1; a <= 255; a++) { for (LONG i=0; i <= 255; i++) { glDemultiply[(a<<8) + i] = (i * 0xff) / a; } } } - else return ERR_AllocMemory; + else return ERR::AllocMemory; } } - if ((Self->Flags & BMF::PREMUL) IS BMF::NIL) return log.warning(ERR_NothingDone); - if (Self->BitsPerPixel != 32) return log.warning(ERR_InvalidState); - if ((Self->Flags & BMF::ALPHA_CHANNEL) IS BMF::NIL) return log.warning(ERR_InvalidState); + if ((Self->Flags & BMF::PREMUL) IS BMF::NIL) return log.warning(ERR::NothingDone); + if (Self->BitsPerPixel != 32) return log.warning(ERR::InvalidState); + if ((Self->Flags & BMF::ALPHA_CHANNEL) IS BMF::NIL) return log.warning(ERR::InvalidState); const auto w = (LONG)(Self->Clip.Right - Self->Clip.Left); const auto h = (LONG)(Self->Clip.Bottom - Self->Clip.Top); - if (Self->Clip.Left + w > Self->Width) return log.warning(ERR_InvalidDimension); - if (Self->Clip.Top + h > Self->Height) return log.warning(ERR_InvalidDimension); + if (Self->Clip.Left + w > Self->Width) return log.warning(ERR::InvalidDimension); + if (Self->Clip.Top + h > Self->Height) return log.warning(ERR::InvalidDimension); const UBYTE A = Self->ColourFormat->AlphaPos>>3; const UBYTE R = Self->ColourFormat->RedPos>>3; @@ -906,7 +907,7 @@ static ERROR BITMAP_Demultiply(extBitmap *Self, APTR Void) } Self->Flags &= ~BMF::PREMUL; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -916,10 +917,10 @@ Draw: Clears a bitmap's image to its assigned background colour. *********************************************************************************************************************/ -static ERROR BITMAP_Draw(extBitmap *Self, APTR Void) +static ERR BITMAP_Draw(extBitmap *Self, APTR Void) { gfxDrawRectangle(Self, 0, 0, Self->Width, Self->Height, Self->BkgdIndex, BAF::FILL); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -946,11 +947,11 @@ Args *********************************************************************************************************************/ -static ERROR BITMAP_DrawRectangle(extBitmap *Self, struct bmpDrawRectangle *Args) +static ERR BITMAP_DrawRectangle(extBitmap *Self, struct bmpDrawRectangle *Args) { - if (!Args) return ERR_NullArgs; + if (!Args) return ERR::NullArgs; gfxDrawRectangle(Self, Args->X, Args->Y, Args->Width, Args->Height, Args->Colour, Args->Flags); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -970,17 +971,17 @@ NullArgs *********************************************************************************************************************/ -static ERROR BITMAP_Flip(extBitmap *Self, struct bmpFlip *Args) +static ERR BITMAP_Flip(extBitmap *Self, struct bmpFlip *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); // NB: A faster way to flip a Bitmap would be to use CopyArea() to do the transfer in strips, but would require a // temporary memory area to hold the information. if (Args->Orientation IS FLIP::HORIZONTAL) { - if (!lock_surface(Self, SURFACE_READWRITE)) { + if (lock_surface(Self, SURFACE_READWRITE) IS ERR::Okay) { for (LONG y=0; y < Self->Height/2; y++) { for (LONG x=0; x < Self->Width; x++) { LONG c1 = Self->ReadUCPixel(Self, x, Self->Height - y - 1); @@ -993,7 +994,7 @@ static ERROR BITMAP_Flip(extBitmap *Self, struct bmpFlip *Args) } } else if (Args->Orientation IS FLIP::VERTICAL) { - if (!lock_surface(Self, SURFACE_READWRITE)) { + if (lock_surface(Self, SURFACE_READWRITE) IS ERR::Okay) { // Palette based Bitmap for (LONG x=0; x < Self->Width/2; x++) { for (LONG y=0; y < Self->Height; y++) { @@ -1006,9 +1007,9 @@ static ERROR BITMAP_Flip(extBitmap *Self, struct bmpFlip *Args) unlock_surface(Self); } } - else return log.warning(ERR_Args); + else return log.warning(ERR::Args); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1025,7 +1026,7 @@ You do not have to use this function if you stick to using the graphics function *********************************************************************************************************************/ -static ERROR BITMAP_Flush(extBitmap *Self, APTR Void) +static ERR BITMAP_Flush(extBitmap *Self, APTR Void) { #ifdef _GLES_ if (!lock_graphics_active(__func__)) { @@ -1033,12 +1034,12 @@ static ERROR BITMAP_Flush(extBitmap *Self, APTR Void) unlock_graphics(); } #endif - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR BITMAP_Free(extBitmap *Self, APTR Void) +static ERR BITMAP_Free(extBitmap *Self, APTR Void) { #ifdef __xwindows__ if (Self->x11.XShmImage) { @@ -1068,7 +1069,7 @@ static ERROR BITMAP_Free(extBitmap *Self, APTR Void) } #ifdef __xwindows__ - if (Self->x11.drawable) { + if ((Self->x11.drawable) and (Self->x11.window != Self->x11.drawable)) { if (XDisplay) XFreePixmap(XDisplay, Self->x11.drawable); Self->x11.drawable = 0; } @@ -1086,7 +1087,7 @@ static ERROR BITMAP_Free(extBitmap *Self, APTR Void) } #endif - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1110,9 +1111,9 @@ NullArgs *********************************************************************************************************************/ -static ERROR BITMAP_GetColour(extBitmap *Self, struct bmpGetColour *Args) +static ERR BITMAP_GetColour(extBitmap *Self, struct bmpGetColour *Args) { - if (!Args) return ERR_NullArgs; + if (!Args) return ERR::NullArgs; if (Self->BitsPerPixel > 8) { Args->Colour = Self->packPixel(Args->Red, Args->Green, Args->Blue, Args->Alpha); @@ -1126,7 +1127,7 @@ static ERROR BITMAP_GetColour(extBitmap *Self, struct bmpGetColour *Args) Args->Colour = RGBToValue(&rgb, Self->Palette); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1144,11 +1145,11 @@ This action will not work unless you have defined the #Width and #Height fields *********************************************************************************************************************/ -static ERROR BITMAP_Init(extBitmap *Self, APTR Void) +static ERR BITMAP_Init(extBitmap *Self, APTR Void) { pf::Log log; - if (acQuery(Self) != ERR_Okay) return log.warning(ERR_Query); + if (acQuery(Self) != ERR::Okay) return log.warning(ERR::Query); log.branch("Size: %dx%d @ %d bit, %d bytes, Mem: $%.8x, Flags: $%.8x", Self->Width, Self->Height, Self->BitsPerPixel, Self->BytesPerPixel, LONG(Self->DataFlags), LONG(Self->Flags)); @@ -1186,16 +1187,16 @@ static ERROR BITMAP_Init(extBitmap *Self, APTR Void) if ((Self->Flags & BMF::NO_DATA) IS BMF::NIL) { Self->DataFlags &= ~MEM::VIDEO; // Video memory not available for allocation in X11 (may be set to identify X11 windows only) - if (!Self->Size) return log.warning(ERR_FieldNotSet); + if (!Self->Size) return log.warning(ERR::FieldNotSet); if (glHeadless) { if (!AllocMemory(Self->Size, MEM::NO_BLOCKING|MEM::NO_POOL|MEM::NO_CLEAR|Self->DataFlags, &Self->Data)) { Self->prvAFlags |= BF_DATA; } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } else if (!Self->x11.XShmImage) { - log.extmsg("Allocating a memory based XImage."); + log.detail("Allocating a memory based XImage."); if (!alloc_shm(Self->Size, &Self->Data, &Self->x11.ShmInfo.shmid)) { Self->prvAFlags |= BF_DATA; @@ -1235,12 +1236,11 @@ static ERROR BITMAP_Init(extBitmap *Self, APTR Void) if (XShmAttach(XDisplay, &Self->x11.ShmInfo)) { Self->x11.XShmImage = true; - XSync(XDisplay, TRUE); } - else log.warning(ERR_SystemCall); + else log.warning(ERR::SystemCall); } } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } } } @@ -1253,16 +1253,16 @@ static ERROR BITMAP_Init(extBitmap *Self, APTR Void) if (!Self->Data) { if ((Self->Flags & BMF::NO_DATA) IS BMF::NIL) { - if (!Self->Size) return log.warning(ERR_FieldNotSet); + if (!Self->Size) return log.warning(ERR::FieldNotSet); if ((Self->DataFlags & MEM::VIDEO) != MEM::NIL) { Self->prvAFlags |= BF_WINVIDEO; - if (!(Self->win.Drawable = winCreateCompatibleDC())) return log.warning(ERR_SystemCall); + if (!(Self->win.Drawable = winCreateCompatibleDC())) return log.warning(ERR::SystemCall); } - else if (!AllocMemory(Self->Size, MEM::NO_BLOCKING|MEM::NO_POOL|MEM::NO_CLEAR|Self->DataFlags, &Self->Data)) { + else if (AllocMemory(Self->Size, MEM::NO_BLOCKING|MEM::NO_POOL|MEM::NO_CLEAR|Self->DataFlags, &Self->Data) IS ERR::Okay) { Self->prvAFlags |= BF_DATA; } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } else if ((Self->DataFlags & MEM::VIDEO) != MEM::NIL) Self->prvAFlags |= BF_WINVIDEO; } @@ -1275,7 +1275,7 @@ static ERROR BITMAP_Init(extBitmap *Self, APTR Void) if (!Self->Data) { if ((Self->Flags & BMF::NO_DATA) IS BMF::NIL) { - if (Self->Size <= 0) log.warning(ERR_FieldNotSet); + if (Self->Size <= 0) log.warning(ERR::FieldNotSet); if ((Self->DataFlags & MEM::VIDEO) != MEM::NIL) { // Do nothing - the bitmap merely represents the video display and does not hold content. @@ -1285,12 +1285,12 @@ static ERROR BITMAP_Init(extBitmap *Self, APTR Void) // bitmap type - the developer should use MEM::DATA if that is desired. log.warning("Support for MEM::TEXTURE not included yet."); - return ERR_NoSupport; + return ERR::NoSupport; } else if (!AllocMemory(Self->Size, Self->DataFlags|MEM::NO_BLOCKING|MEM::NO_POOL|MEM::NO_CLEAR, &Self->Data)) { Self->prvAFlags |= BF_DATA; } - else return ERR_AllocMemory; + else return ERR::AllocMemory; } } @@ -1324,7 +1324,7 @@ static ERROR BITMAP_Init(extBitmap *Self, APTR Void) if ((Self->DataFlags & MEM::VIDEO) != MEM::NIL) { LONG red, green, blue, alpha; - if (winGetPixelFormat(&red, &green, &blue, &alpha) IS ERR_Okay) { + if (!winGetPixelFormat(&red, &green, &blue, &alpha)) { gfxGetColourFormat(Self->ColourFormat, Self->BitsPerPixel, red, green, blue, alpha); } else gfxGetColourFormat(Self->ColourFormat, Self->BitsPerPixel, 0, 0, 0, 0); @@ -1344,7 +1344,7 @@ static ERROR BITMAP_Init(extBitmap *Self, APTR Void) #endif - if (auto error = CalculatePixelRoutines(Self)) return error; + if (auto error = CalculatePixelRoutines(Self); error != ERR::Okay) return error; if (Self->BitsPerPixel > 8) { Self->TransIndex = (((Self->TransRGB.Red >> Self->prvColourFormat.RedShift) & Self->prvColourFormat.RedMask) << Self->prvColourFormat.RedPos) | @@ -1374,7 +1374,7 @@ static ERROR BITMAP_Init(extBitmap *Self, APTR Void) // Self->prvColourFormat.BlueMask, Self->prvColourFormat.BlueShift, Self->prvColourFormat.BluePos, // Self->prvColourFormat.AlphaMask, Self->prvColourFormat.AlphaShift, Self->prvColourFormat.AlphaPos); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1383,7 +1383,7 @@ Lock: Locks the bitmap surface so that you can manipulate the graphics directly. -END- *********************************************************************************************************************/ -static ERROR BITMAP_Lock(extBitmap *Self, APTR Void) +static ERR BITMAP_Lock(extBitmap *Self, APTR Void) { #ifdef __xwindows__ if (Self->x11.drawable) { @@ -1398,7 +1398,7 @@ static ERROR BITMAP_Lock(extBitmap *Self, APTR Void) Self->YOffset + Self->Clip.Top, Self->Clip.Right - Self->Clip.Left, Self->Clip.Bottom - Self->Clip.Top, 0xffffffff, ZPixmap, Self->x11.readable, Self->XOffset + Self->Clip.Left, Self->YOffset + Self->Clip.Top); - return ERR_Okay; + return ERR::Okay; } else XDestroyImage(Self->x11.readable); } @@ -1425,10 +1425,10 @@ static ERROR BITMAP_Lock(extBitmap *Self, APTR Void) Self->Clip.Bottom - Self->Clip.Top, 0xffffffff, ZPixmap, Self->x11.readable, Self->XOffset + Self->Clip.Left, Self->YOffset + Self->Clip.Top); } - else return ERR_Failed; + else return ERR::Failed; } - return ERR_Okay; + return ERR::Okay; #else @@ -1439,7 +1439,7 @@ static ERROR BITMAP_Lock(extBitmap *Self, APTR Void) //******************************************************************************************************************** -static ERROR BITMAP_NewObject(extBitmap *Self, APTR Void) +static ERR BITMAP_NewObject(extBitmap *Self, APTR Void) { #define CBANK 5 RGB8 *RGB; @@ -1507,7 +1507,7 @@ static ERROR BITMAP_NewObject(extBitmap *Self, APTR Void) } } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1531,22 +1531,22 @@ InvalidDimension: The clipping region is invalid. *********************************************************************************************************************/ -static ERROR BITMAP_Premultiply(extBitmap *Self, APTR Void) +static ERR BITMAP_Premultiply(extBitmap *Self, APTR Void) { pf::Log log; if ((Self->Flags & BMF::PREMUL) != BMF::NIL) { - return log.warning(ERR_NothingDone); + return log.warning(ERR::NothingDone); } - if (Self->BitsPerPixel != 32) return log.warning(ERR_InvalidState); - if ((Self->Flags & BMF::ALPHA_CHANNEL) IS BMF::NIL) return log.warning(ERR_InvalidState); + if (Self->BitsPerPixel != 32) return log.warning(ERR::InvalidState); + if ((Self->Flags & BMF::ALPHA_CHANNEL) IS BMF::NIL) return log.warning(ERR::InvalidState); const auto w = (LONG)(Self->Clip.Right - Self->Clip.Left); const auto h = (LONG)(Self->Clip.Bottom - Self->Clip.Top); - if (Self->Clip.Left + w > Self->Width) return log.warning(ERR_InvalidDimension); - if (Self->Clip.Top + h > Self->Height) return log.warning(ERR_InvalidDimension); + if (Self->Clip.Left + w > Self->Width) return log.warning(ERR::InvalidDimension); + if (Self->Clip.Top + h > Self->Height) return log.warning(ERR::InvalidDimension); const UBYTE A = Self->ColourFormat->AlphaPos>>3; const UBYTE R = Self->ColourFormat->RedPos>>3; @@ -1572,7 +1572,7 @@ static ERROR BITMAP_Premultiply(extBitmap *Self, APTR Void) } Self->Flags |= BMF::PREMUL; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1589,17 +1589,17 @@ you set the #BytesPerPixel field to 2 then it will determine that the bitmap is *********************************************************************************************************************/ -static ERROR BITMAP_Query(extBitmap *Self, APTR Void) +static ERR BITMAP_Query(extBitmap *Self, APTR Void) { pf::Log log; objDisplay *display; OBJECTID display_id; LONG i; - log.msg(VLF::BRANCH|VLF::EXTAPI, "Bitmap: %p, Depth: %d, Width: %d, Height: %d", Self, Self->BitsPerPixel, Self->Width, Self->Height); + log.msg(VLF::BRANCH|VLF::DETAIL, "Bitmap: %p, Depth: %d, Width: %d, Height: %d", Self, Self->BitsPerPixel, Self->Width, Self->Height); if ((Self->Width <= 0) or (Self->Height <= 0)) { - return log.warning(ERR_InvalidDimension); + return log.warning(ERR::InvalidDimension); } #ifdef _GLES_ @@ -1687,8 +1687,8 @@ static ERROR BITMAP_Query(extBitmap *Self, APTR Void) Self->BitsPerPixel = 32; Self->BytesPerPixel = 4; #if 1 - if (!FindObject("SystemDisplay", ID_DISPLAY, FOF::NIL, &display_id)) { - if (!AccessObject(display_id, 3000, &display)) { + if (FindObject("SystemDisplay", ID_DISPLAY, FOF::NIL, &display_id) IS ERR::Okay) { + if (AccessObject(display_id, 3000, &display) IS ERR::Okay) { Self->AmtColours = display->Bitmap->AmtColours; Self->BytesPerPixel = display->Bitmap->BytesPerPixel; Self->BitsPerPixel = display->Bitmap->BitsPerPixel; @@ -1752,7 +1752,7 @@ static ERROR BITMAP_Query(extBitmap *Self, APTR Void) else Self->Size = Self->LineWidth * Self->Height; Self->Flags |= BMF::QUERIED; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1761,17 +1761,17 @@ Read: Reads raw image data from a bitmap object. -END- *********************************************************************************************************************/ -static ERROR BITMAP_Read(extBitmap *Self, struct acRead *Args) +static ERR BITMAP_Read(extBitmap *Self, struct acRead *Args) { - if (!Self->Data) return ERR_NoData; - if ((!Args) or (!Args->Buffer)) return ERR_NullArgs; + if (!Self->Data) return ERR::NoData; + if ((!Args) or (!Args->Buffer)) return ERR::NullArgs; LONG len = Args->Length; if (Self->Position + len > Self->Size) len = Self->Size - Self->Position; CopyMemory(Self->Data + Self->Position, Args->Buffer, len); Self->Position += len; Args->Result = len; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1779,10 +1779,10 @@ static ERROR BITMAP_Read(extBitmap *Self, struct acRead *Args) -ACTION- Resize: Resizes a bitmap object's dimensions. -Resizing a bitmap will change its width, height and optionally bit depth. Existing image data is not retained after +Resizing a bitmap will change its width, height and optionally bit depth. Existing image data is not retained by this process. -The image data is cleared with #BkgdRGB if the CLEAR flag is defined in #Flags. +The image data is cleared with #BkgdRGB if the `CLEAR` flag is defined in #Flags. -ERRORS- Okay @@ -1792,12 +1792,12 @@ FieldNotSet *********************************************************************************************************************/ -static ERROR BITMAP_Resize(extBitmap *Self, struct acResize *Args) +static ERR BITMAP_Resize(extBitmap *Self, struct acResize *Args) { pf::Log log; LONG width, height, bytewidth, bpp, amtcolours, size; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); auto origbpp = Self->BitsPerPixel; @@ -1820,7 +1820,7 @@ static ERROR BITMAP_Resize(extBitmap *Self, struct acResize *Args) // Return if there is no change in the bitmap size if ((Self->Width IS width) and (Self->Height IS height) and (Self->BitsPerPixel IS bpp)) { - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } // Calculate type-dependent values @@ -1846,7 +1846,7 @@ static ERROR BITMAP_Resize(extBitmap *Self, struct acResize *Args) if (Self->Type IS BMP::PLANAR) size = linewidth * height * bpp; else size = linewidth * height; - if (GetClassID(Self->ownerID()) IS ID_DISPLAY) goto setfields; + if ((Self->Owner) and (Self->Owner->Class->ClassID IS ID_DISPLAY)) goto setfields; #ifdef __xwindows__ @@ -1856,12 +1856,12 @@ static ERROR BITMAP_Resize(extBitmap *Self, struct acResize *Args) // XFreePixmap(XDisplay, Self->x11.drawable); // Self->x11.drawable = drawable; // } - // else return log.warning(ERR_AllocMemory); + // else return log.warning(ERR::AllocMemory); // goto setfields; //} #elif _WIN32 - if (Self->prvAFlags & BF_WINVIDEO) return ERR_NoSupport; + if (Self->prvAFlags & BF_WINVIDEO) return ERR::NoSupport; #endif if ((Self->Flags & BMF::NO_DATA) != BMF::NIL); @@ -1873,13 +1873,13 @@ static ERROR BITMAP_Resize(extBitmap *Self, struct acResize *Args) if ((size <= Self->Size) and (size / Self->Size > 0.5)) { // Do nothing when shrinking unless able to save considerable resources size = Self->Size; } - else if (!AllocMemory(size, MEM::NO_BLOCKING|MEM::NO_POOL|Self->DataFlags|MEM::NO_CLEAR, &data)) { + else if (AllocMemory(size, MEM::NO_BLOCKING|MEM::NO_POOL|Self->DataFlags|MEM::NO_CLEAR, &data) IS ERR::Okay) { if (Self->Data) FreeResource(Self->Data); Self->Data = data; } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } - else return log.warning(ERR_UndefinedField); + else return log.warning(ERR::UndefinedField); setfields: Self->Width = width; @@ -1971,10 +1971,7 @@ static ERROR BITMAP_Resize(extBitmap *Self, struct acResize *Args) gfxDrawRectangle(Self, 0, 0, Self->Width, Self->Height, Self->getColour(Self->BkgdRGB), BAF::FILL); } -#ifdef __xwindows__ - if (!glHeadless) XSync(XDisplay, False); -#endif - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1983,7 +1980,7 @@ SaveImage: Saves a bitmap's image to a data object of your choosing in PCX forma -END- *********************************************************************************************************************/ -static ERROR BITMAP_SaveImage(extBitmap *Self, struct acSaveImage *Args) +static ERR BITMAP_SaveImage(extBitmap *Self, struct acSaveImage *Args) { pf::Log log; struct { @@ -2007,7 +2004,7 @@ static ERROR BITMAP_SaveImage(extBitmap *Self, struct acSaveImage *Args) UBYTE *buffer, lastpixel, newpixel; LONG i, j, p, size; - if ((!Args) or (!Args->Dest)) return log.warning(ERR_NullArgs); + if ((!Args) or (!Args->Dest)) return log.warning(ERR::NullArgs); log.branch("Save To #%d", Args->Dest->UID); @@ -2035,7 +2032,7 @@ static ERROR BITMAP_SaveImage(extBitmap *Self, struct acSaveImage *Args) else pcx.NumPlanes = 3; size = width * height * pcx.NumPlanes; - if (!AllocMemory(size, MEM::DATA|MEM::NO_CLEAR, &buffer)) { + if (AllocMemory(size, MEM::DATA|MEM::NO_CLEAR, &buffer) IS ERR::Okay) { acWrite(Args->Dest, &pcx, sizeof(pcx), NULL); LONG dp = 0; @@ -2060,7 +2057,7 @@ static ERROR BITMAP_SaveImage(extBitmap *Self, struct acSaveImage *Args) if (dp >= (size - 10)) { FreeResource(buffer); - return log.warning(ERR_BufferOverflow); + return log.warning(ERR::BufferOverflow); } } } @@ -2141,10 +2138,10 @@ static ERROR BITMAP_SaveImage(extBitmap *Self, struct acSaveImage *Args) acWrite(Args->Dest, palette, sizeof(palette), NULL); } - return ERR_Okay; + return ERR::Okay; } - else return ERR_AllocMemory; + else return ERR::AllocMemory; } /********************************************************************************************************************* @@ -2153,17 +2150,17 @@ Seek: Changes the current byte position for read/write operations. *********************************************************************************************************************/ -static ERROR BITMAP_Seek(extBitmap *Self, struct acSeek *Args) +static ERR BITMAP_Seek(extBitmap *Self, struct acSeek *Args) { if (Args->Position IS SEEK::START) Self->Position = (LONG)Args->Offset; else if (Args->Position IS SEEK::END) Self->Position = (LONG)(Self->Size - Args->Offset); else if (Args->Position IS SEEK::CURRENT) Self->Position = (LONG)(Self->Position + Args->Offset); - else return ERR_Args; + else return ERR::Args; if (Self->Position > Self->Size) Self->Position = Self->Size; else if (Self->Position < 0) Self->Position = 0; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2187,12 +2184,12 @@ NullArgs *********************************************************************************************************************/ -static ERROR BITMAP_SetClipRegion(extBitmap *Self, struct bmpSetClipRegion *Args) +static ERR BITMAP_SetClipRegion(extBitmap *Self, struct bmpSetClipRegion *Args) { - if (!Args) return ERR_NullArgs; + if (!Args) return ERR::NullArgs; gfxSetClipRegion(Self, Args->Number, Args->Left, Args->Top, Args->Right, Args->Bottom, Args->Terminate); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2201,12 +2198,12 @@ Unlock: Unlocks the bitmap surface once direct access is no longer required. *********************************************************************************************************************/ -static ERROR BITMAP_Unlock(extBitmap *Self, APTR Void) +static ERR BITMAP_Unlock(extBitmap *Self, APTR Void) { #ifndef __xwindows__ unlock_surface(Self); #endif - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2215,7 +2212,7 @@ Write: Writes raw image data to a bitmap object. -END- *********************************************************************************************************************/ -static ERROR BITMAP_Write(extBitmap *Self, struct acWrite *Args) +static ERR BITMAP_Write(extBitmap *Self, struct acWrite *Args) { if (Self->Data) { auto Data = (BYTE *)Self->Data + Self->Position; @@ -2226,9 +2223,9 @@ static ERROR BITMAP_Write(extBitmap *Self, struct acWrite *Args) amt_bytes++; } Self->Position += amt_bytes; - return ERR_Okay; + return ERR::Okay; } - else return ERR_NoData; + else return ERR::NoData; } /********************************************************************************************************************* @@ -2252,7 +2249,7 @@ The #BkgdIndex will be updated as a result of setting this field. *********************************************************************************************************************/ -static ERROR SET_Bkgd(extBitmap *Self, RGB8 *Value) +static ERR SET_Bkgd(extBitmap *Self, RGB8 *Value) { Self->BkgdRGB = *Value; @@ -2263,7 +2260,7 @@ static ERROR SET_Bkgd(extBitmap *Self, RGB8 *Value) (((Self->BkgdRGB.Alpha>>Self->prvColourFormat.AlphaShift) & Self->prvColourFormat.AlphaMask) << Self->prvColourFormat.AlphaPos); } else Self->BkgdIndex = RGBToValue(&Self->BkgdRGB, Self->Palette); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2277,12 +2274,12 @@ directly. *********************************************************************************************************************/ -static ERROR SET_BkgdIndex(extBitmap *Self, LONG Index) +static ERR SET_BkgdIndex(extBitmap *Self, LONG Index) { - if ((Index < 0) or (Index > 255)) return ERR_OutOfRange; + if ((Index < 0) or (Index > 255)) return ERR::OutOfRange; Self->BkgdIndex = Index; Self->BkgdRGB = Self->Palette->Col[Self->BkgdIndex]; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2347,16 +2344,16 @@ Clip: Defines the bitmap's clipping region. *********************************************************************************************************************/ -static ERROR GET_Clip(extBitmap *Self, ClipRectangle **Value) +static ERR GET_Clip(extBitmap *Self, ClipRectangle **Value) { *Value = &Self->Clip; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_Clip(extBitmap *Self, ClipRectangle *Value) +static ERR SET_Clip(extBitmap *Self, ClipRectangle *Value) { Self->Clip = *Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2418,10 +2415,10 @@ initialisation process to allocate the correct amount of memory for you by not i *********************************************************************************************************************/ -ERROR SET_Data(extBitmap *Self, UBYTE *Value) +ERR SET_Data(extBitmap *Self, UBYTE *Value) { #ifdef __xwindows__ - if (Self->x11.XShmImage) return ERR_NotPossible; + if (Self->x11.XShmImage) return ERR::NotPossible; #endif // This code gets the correct memory flags to define the pixel drawing functions @@ -2432,7 +2429,7 @@ ERROR SET_Data(extBitmap *Self, UBYTE *Value) if (Self->DataFlags IS MEM::NIL) { MemInfo info; - if (MemoryPtrInfo(Value, &info) != ERR_Okay) { + if (MemoryPtrInfo(Value, &info) != ERR::Okay) { pf::Log log; log.warning("Could not obtain flags from address %p.", Value); } @@ -2443,7 +2440,7 @@ ERROR SET_Data(extBitmap *Self, UBYTE *Value) } } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2505,31 +2502,31 @@ Handle: Private. Platform dependent field for referencing video memory. *********************************************************************************************************************/ -static ERROR GET_Handle(extBitmap *Self, APTR *Value) +static ERR GET_Handle(extBitmap *Self, APTR *Value) { #ifdef _WIN32 *Value = (APTR)Self->win.Drawable; - return ERR_Okay; + return ERR::Okay; #elif __xwindows__ *Value = (APTR)Self->x11.drawable; - return ERR_Okay; + return ERR::Okay; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } -static ERROR SET_Handle(extBitmap *Self, APTR Value) +static ERR SET_Handle(extBitmap *Self, APTR Value) { // Note: The only area of the system allowed to set this field are the Display/Surface classes for video management. #ifdef _WIN32 Self->win.Drawable = Value; - return ERR_Okay; + return ERR::Okay; #elif __xwindows__ Self->x11.drawable = (MAXINT)Value; - return ERR_Okay; + return ERR::Okay; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -2583,19 +2580,19 @@ to be propagated to the video display. *********************************************************************************************************************/ -ERROR SET_Palette(extBitmap *Self, RGBPalette *SrcPalette) +ERR SET_Palette(extBitmap *Self, RGBPalette *SrcPalette) { pf::Log log; // The objective here is to copy the given source palette to the bitmap's palette. To see how the hook is set up, // refer to the bitmap's object definition structure that is compiled into the module. - if (!SrcPalette) return ERR_Okay; + if (!SrcPalette) return ERR::Okay; if (SrcPalette->AmtColours <= 256) { if (!Self->Palette) { - if (AllocMemory(sizeof(RGBPalette), MEM::NO_CLEAR, &Self->Palette) != ERR_Okay) { - log.warning(ERR_AllocMemory); + if (AllocMemory(sizeof(RGBPalette), MEM::NO_CLEAR, &Self->Palette) != ERR::Okay) { + log.warning(ERR::AllocMemory); } } @@ -2605,11 +2602,11 @@ ERROR SET_Palette(extBitmap *Self, RGBPalette *SrcPalette) Self->Palette->Col[i] = SrcPalette->Col[i]; i--; } - return ERR_Okay; + return ERR::Okay; } else { log.warning("Corruption in Palette at %p.", SrcPalette); - return ERR_ObjectCorrupt; + return ERR::ObjectCorrupt; } } @@ -2679,7 +2676,7 @@ NOTE: This field should never be set if the bitmap utilises alpha transparency. *********************************************************************************************************************/ -static ERROR SET_Trans(extBitmap *Self, RGB8 *Value) +static ERR SET_Trans(extBitmap *Self, RGB8 *Value) { Self->TransRGB = *Value; @@ -2692,7 +2689,7 @@ static ERROR SET_Trans(extBitmap *Self, RGB8 *Value) else Self->TransIndex = RGBToValue(&Self->TransRGB, Self->Palette); if ((Self->DataFlags & MEM::VIDEO) IS MEM::NIL) Self->Flags |= BMF::TRANSPARENT; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2708,15 +2705,15 @@ NOTE: This field should never be set if the bitmap utilises alpha transparency. *********************************************************************************************************************/ -static ERROR SET_TransIndex(extBitmap *Self, LONG Index) +static ERR SET_TransIndex(extBitmap *Self, LONG Index) { - if ((Index < 0) or (Index > 255)) return ERR_OutOfRange; + if ((Index < 0) or (Index > 255)) return ERR::OutOfRange; Self->TransIndex = Index; Self->TransRGB = Self->Palette->Col[Self->TransIndex]; if ((Self->DataFlags & MEM::VIDEO) IS MEM::NIL) Self->Flags |= BMF::TRANSPARENT; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2740,7 +2737,7 @@ YOffset: Private. Provided for surface/video drawing purposes - considered too a //******************************************************************************************************************** -static ERROR CalculatePixelRoutines(extBitmap *Self) +static ERR CalculatePixelRoutines(extBitmap *Self) { pf::Log log; @@ -2751,12 +2748,12 @@ static ERROR CalculatePixelRoutines(extBitmap *Self) Self->DrawUCPixel = MemDrawPixelPlanar; Self->DrawUCRPixel = DrawRGBPixelPlanar; Self->DrawUCRIndex = NULL; - return ERR_Okay; + return ERR::Okay; } if (Self->Type != BMP::CHUNKY) { log.warning("Unsupported Bitmap->Type %d.", LONG(Self->Type)); - return ERR_Failed; + return ERR::Failed; } #ifdef _WIN32 @@ -2768,7 +2765,7 @@ static ERROR CalculatePixelRoutines(extBitmap *Self) Self->DrawUCPixel = &VideoDrawPixel; Self->DrawUCRPixel = &VideoDrawRGBPixel; Self->DrawUCRIndex = &VideoDrawRGBIndex; - return ERR_Okay; + return ERR::Okay; } #else @@ -2813,9 +2810,9 @@ static ERROR CalculatePixelRoutines(extBitmap *Self) default: log.warning("Unsupported Bitmap->BytesPerPixel %d.", Self->BytesPerPixel); - return ERR_Failed; + return ERR::Failed; } - return ERR_Okay; + return ERR::Okay; } #endif @@ -2868,10 +2865,10 @@ static ERROR CalculatePixelRoutines(extBitmap *Self) default: log.warning("Unsupported Bitmap->BytesPerPixel %d.", Self->BytesPerPixel); - return ERR_Failed; + return ERR::Failed; } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -2936,7 +2933,7 @@ static const FieldArray clBitmapFields[] = { //******************************************************************************************************************** -ERROR create_bitmap_class(void) +ERR create_bitmap_class(void) { clBitmap = objMetaClass::create::global( fl::ClassVersion(VER_BITMAP), @@ -2948,6 +2945,6 @@ ERROR create_bitmap_class(void) fl::Size(sizeof(extBitmap)), fl::Path(MOD_PATH)); - return clBitmap ? ERR_Okay : ERR_AddClass; + return clBitmap ? ERR::Okay : ERR::AddClass; } diff --git a/src/display/class_clipboard.cpp b/src/display/class_clipboard.cpp index fcbffbc08..0dc32c7b1 100644 --- a/src/display/class_clipboard.cpp +++ b/src/display/class_clipboard.cpp @@ -29,6 +29,7 @@ there is a fixed limit to the clip count and the oldest members are automaticall *********************************************************************************************************************/ #include "defs.h" +#include #ifdef _WIN32 using namespace display; @@ -57,9 +58,38 @@ static LONG glLastClipID = -1; //******************************************************************************************************************** static std::string get_datatype(CLIPTYPE); -static ERROR add_clip(CLIPTYPE, const std::vector &, CEF = CEF::NIL); -static ERROR add_clip(CSTRING); -static ERROR CLIPBOARD_AddObjects(objClipboard *, struct clipAddObjects *); +static ERR add_clip(CLIPTYPE, const std::vector &, CEF = CEF::NIL); +static ERR add_clip(CSTRING); +static ERR CLIPBOARD_AddObjects(objClipboard *, struct clipAddObjects *); + +//******************************************************************************************************************** +// Remove stale clipboard files that are over 24hrs old + +void clean_clipboard(void) +{ + auto time = objTime::create { }; + if (!time.ok()) return; + + time->query(); + LARGE now = time->get(FID_TimeStamp) / 1000000LL; + LARGE yesterday = now - (24 * 60LL * 60LL); + + DirInfo *dir; + if (OpenDir("clipboard:", RDF::FILE|RDF::DATE, &dir) IS ERR::Okay) { + GuardedResource free_dir(dir); + + while (ScanDir(dir) IS ERR::Okay) { + const std::regex txt_regex("^\\d+(?:_text|_image|_file|_object)\\d*\\.\\d{3}$"); + if (std::regex_match(dir->Info->Name, txt_regex)) { + if (dir->Info->TimeStamp < yesterday) { + std::string path("clipboard:"); + path.append(dir->Info->Name); + DeleteFile(path.c_str(), NULL); + } + } + } + } +} //******************************************************************************************************************** @@ -86,19 +116,19 @@ static std::string get_datatype(CLIPTYPE Datatype) //******************************************************************************************************************** -static void notify_script_free(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, APTR Args) +static void notify_script_free(OBJECTPTR Object, ACTIONID ActionID, ERR Result, APTR Args) { auto Self = (objClipboard *)CurrentContext(); - Self->RequestHandler.Type = CALL_NONE; + Self->RequestHandler.clear(); } //******************************************************************************************************************** -static ERROR add_file_to_host(objClipboard *Self, const std::vector &Items, bool Cut) +static ERR add_file_to_host(objClipboard *Self, const std::vector &Items, bool Cut) { pf::Log log; - if ((Self->Flags & CPF::DRAG_DROP) != CPF::NIL) return ERR_NoSupport; + if ((Self->Flags & CPF::DRAG_DROP) != CPF::NIL) return ERR::NoSupport; #ifdef _WIN32 // Build a list of resolved path names in a new buffer that is suitable for passing to Windows. @@ -106,7 +136,7 @@ static ERROR add_file_to_host(objClipboard *Self, const std::vector &I std::stringstream list; for (auto &item : Items) { STRING path; - if (!ResolvePath(item.Path.c_str(), RSF::NIL, &path)) { + if (ResolvePath(item.Path.c_str(), RSF::NIL, &path) IS ERR::Okay) { list << path << '\0'; FreeResource(path); } @@ -115,19 +145,19 @@ static ERROR add_file_to_host(objClipboard *Self, const std::vector &I auto str = list.str(); winAddClip(LONG(CLIPTYPE::FILE), str.c_str(), str.size(), Cut); - return ERR_Okay; + return ERR::Okay; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } //******************************************************************************************************************** -static ERROR add_text_to_host(objClipboard *Self, CSTRING String, LONG Length = 0x7fffffff) +static ERR add_text_to_host(objClipboard *Self, CSTRING String, LONG Length = 0x7fffffff) { pf::Log log(__FUNCTION__); - if ((Self->Flags & CPF::DRAG_DROP) != CPF::NIL) return ERR_NoSupport; + if ((Self->Flags & CPF::DRAG_DROP) != CPF::NIL) return ERR::NoSupport; #ifdef _WIN32 // Copy text to the windows clipboard. This requires a conversion from UTF-8 to UTF-16. @@ -149,11 +179,11 @@ static ERROR add_text_to_host(objClipboard *Self, CSTRING String, LONG Length = } utf16[i] = 0; - auto error = winAddClip(LONG(CLIPTYPE::TEXT), utf16.data(), utf16.size() * sizeof(UWORD), false); - if (error) log.warning(error); + ERR error = (ERR)winAddClip(LONG(CLIPTYPE::TEXT), utf16.data(), utf16.size() * sizeof(UWORD), false); + if (error != ERR::Okay) log.warning(error); return error; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -188,18 +218,18 @@ MissingPath: The Files argument was not correctly specified. *********************************************************************************************************************/ -static ERROR CLIPBOARD_AddFile(objClipboard *Self, struct clipAddFile *Args) +static ERR CLIPBOARD_AddFile(objClipboard *Self, struct clipAddFile *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); - if ((!Args->Path) or (!Args->Path[0])) return log.warning(ERR_MissingPath); + if (!Args) return log.warning(ERR::NullArgs); + if ((!Args->Path) or (!Args->Path[0])) return log.warning(ERR::MissingPath); log.branch("Path: %s", Args->Path); std::vector items = { std::string(Args->Path) }; - if (!add_file_to_host(Self, items, ((Args->Flags & CEF::DELETE) != CEF::NIL) ? true : false)) { - if (glHistoryLimit <= 1) return ERR_Okay; + if (add_file_to_host(Self, items, ((Args->Flags & CEF::DELETE) != CEF::NIL) ? true : false) IS ERR::Okay) { + if (glHistoryLimit <= 1) return ERR::Okay; } return add_clip(Args->Datatype, items, Args->Flags & (CEF::DELETE|CEF::EXTEND)); @@ -238,11 +268,11 @@ Args *********************************************************************************************************************/ -static ERROR CLIPBOARD_AddObjects(objClipboard *Self, struct clipAddObjects *Args) +static ERR CLIPBOARD_AddObjects(objClipboard *Self, struct clipAddObjects *Args) { pf::Log log; - if ((!Args) or (!Args->Objects) or (!Args->Objects[0])) return log.warning(ERR_NullArgs); + if ((!Args) or (!Args->Objects) or (!Args->Objects[0])) return log.warning(ERR::NullArgs); log.branch(); @@ -267,16 +297,16 @@ static ERROR CLIPBOARD_AddObjects(objClipboard *Self, struct clipAddObjects *Arg snprintf(idx, sizeof(idx), ".%.3d", i); auto path = std::string("clipboard:") + glProcessID + "_" + get_datatype(datatype) + std::to_string(counter) + idx; - objFile::create file = { fl::Path(path), fl::Flags(FL::WRITE|FL::NEW) }; + auto file = objFile::create { fl::Path(path), fl::Flags(FL::WRITE|FL::NEW) }; if (file.ok()) acSaveToObject(*object, *file); - else return ERR_CreateFile; + else return ERR::CreateFile; } } - else return ERR_Lock; + else return ERR::Lock; } - if (!add_file_to_host(Self, items, ((Args->Flags & CEF::DELETE) != CEF::NIL) ? true : false)) { - if (glHistoryLimit <= 1) return ERR_Okay; + if (add_file_to_host(Self, items, ((Args->Flags & CEF::DELETE) != CEF::NIL) ? true : false) IS ERR::Okay) { + if (glHistoryLimit <= 1) return ERR::Okay; } return add_clip(datatype, items, Args->Flags & CEF::EXTEND); @@ -300,15 +330,15 @@ CreateFile *********************************************************************************************************************/ -static ERROR CLIPBOARD_AddText(objClipboard *Self, struct clipAddText *Args) +static ERR CLIPBOARD_AddText(objClipboard *Self, struct clipAddText *Args) { pf::Log log; - if ((!Args) or (!Args->String)) return log.warning(ERR_NullArgs); - if (!Args->String[0]) return ERR_Okay; + if ((!Args) or (!Args->String)) return log.warning(ERR::NullArgs); + if (!Args->String[0]) return ERR::Okay; - if (!add_text_to_host(Self, Args->String)) { - if (glHistoryLimit <= 1) return ERR_Okay; + if (add_text_to_host(Self, Args->String) IS ERR::Okay) { + if (glHistoryLimit <= 1) return ERR::Okay; } return add_clip(Args->String); @@ -320,17 +350,17 @@ Clear: Destroys all cached data that is stored in the clipboard. -END- *********************************************************************************************************************/ -static ERROR CLIPBOARD_Clear(objClipboard *Self, APTR Void) +static ERR CLIPBOARD_Clear(objClipboard *Self, APTR Void) { STRING path; - if (!ResolvePath("clipboard:", RSF::NO_FILE_CHECK, &path)) { + if (ResolvePath("clipboard:", RSF::NO_FILE_CHECK, &path) IS ERR::Okay) { DeleteFile(path, NULL); CreateFolder(path, PERMIT::READ|PERMIT::WRITE); FreeResource(path); } glClips.clear(); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -343,11 +373,11 @@ given data type. -END- *********************************************************************************************************************/ -static ERROR CLIPBOARD_DataFeed(objClipboard *Self, struct acDataFeed *Args) +static ERR CLIPBOARD_DataFeed(objClipboard *Self, struct acDataFeed *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); if (Args->Datatype IS DATA::TEXT) { log.msg("Copying text to the clipboard."); @@ -355,13 +385,13 @@ static ERROR CLIPBOARD_DataFeed(objClipboard *Self, struct acDataFeed *Args) add_text_to_host(Self, (CSTRING)Args->Buffer, Args->Size); std::vector items = { std::string("clipboard:") + glProcessID + "_text" + std::to_string(glCounter++) + std::string(".000") }; - if (auto error = add_clip(CLIPTYPE::TEXT, items); !error) { - objFile::create file = { fl::Path(items[0].Path), fl::Flags(FL::NEW|FL::WRITE), fl::Permissions(PERMIT::READ|PERMIT::WRITE) }; + if (auto error = add_clip(CLIPTYPE::TEXT, items); error IS ERR::Okay) { + auto file = objFile::create { fl::Path(items[0].Path), fl::Flags(FL::NEW|FL::WRITE), fl::Permissions(PERMIT::READ|PERMIT::WRITE) }; if (file.ok()) { - if (file->write(Args->Buffer, Args->Size, 0)) return log.warning(ERR_Write); - return ERR_Okay; + if (file->write(Args->Buffer, Args->Size, 0) != ERR::Okay) return log.warning(ERR::Write); + return ERR::Okay; } - else return log.warning(ERR_CreateObject); + else return log.warning(ERR::CreateObject); } else return log.warning(error); } @@ -369,13 +399,13 @@ static ERROR CLIPBOARD_DataFeed(objClipboard *Self, struct acDataFeed *Args) auto request = (struct dcRequest *)Args->Buffer; log.branch("Data request from #%d received for item %d, datatype %d", Args->Object->UID, request->Item, request->Preference[0]); - ERROR error = ERR_Okay; - if (Self->RequestHandler.Type IS CALL_STDC) { - auto routine = (ERROR (*)(objClipboard *, OBJECTPTR, LONG, char *))Self->RequestHandler.StdC.Routine; + ERR error = ERR::Okay; + if (Self->RequestHandler.isC()) { + auto routine = (ERR (*)(objClipboard *, OBJECTPTR, LONG, char *, APTR))Self->RequestHandler.StdC.Routine; pf::SwitchContext ctx(Self->RequestHandler.StdC.Context); - error = routine(Self, Args->Object, request->Item, request->Preference); + error = routine(Self, Args->Object, request->Item, request->Preference, Self->RequestHandler.StdC.Meta); } - else if (Self->RequestHandler.Type IS CALL_SCRIPT) { + else if (Self->RequestHandler.isScript()) { const ScriptArg args[] = { { "Clipboard", Self, FD_OBJECTPTR }, { "Requester", Args->Object, FD_OBJECTPTR }, @@ -384,29 +414,29 @@ static ERROR CLIPBOARD_DataFeed(objClipboard *Self, struct acDataFeed *Args) { "Size", LONG(ARRAYSIZE(request->Preference)), FD_LONG|FD_ARRAYSIZE } }; auto script = Self->RequestHandler.Script.Script; - if (scCallback(script, Self->RequestHandler.Script.ProcedureID, args, ARRAYSIZE(args), &error)) error = ERR_Terminate; + if (scCallback(script, Self->RequestHandler.Script.ProcedureID, args, std::ssize(args), &error) != ERR::Okay) error = ERR::Terminate; } - else error = log.warning(ERR_FieldNotSet); + else error = log.warning(ERR::FieldNotSet); - if (error IS ERR_Terminate) Self->RequestHandler.Type = 0; + if (error IS ERR::Terminate) Self->RequestHandler.Type = 0; - return ERR_Okay; + return ERR::Okay; } else log.warning("Unrecognised data type %d.", LONG(Args->Datatype)); - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR CLIPBOARD_Free(objClipboard *Self, APTR Void) +static ERR CLIPBOARD_Free(objClipboard *Self, APTR Void) { - if (Self->RequestHandler.Type IS CALL_SCRIPT) { + if (Self->RequestHandler.isScript()) { UnsubscribeAction(Self->RequestHandler.Script.Script, AC_Free); - Self->RequestHandler.Type = CALL_NONE; + Self->RequestHandler.clear(); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -418,7 +448,7 @@ This method returns a list of items that are on the clipboard. The caller must supports (or zero if all datatypes are recognised). The most recently clipped datatype is always returned. To scan for all available clip items, set the Datatype -parameter to zero and repeatedly call this method with incremented Index numbers until the error code ERR_OutOfRange +parameter to zero and repeatedly call this method with incremented Index numbers until the error code ERR::OutOfRange is returned. On success this method will return a list of files (terminated with a NULL entry) in the Files parameter. Each file is @@ -445,11 +475,11 @@ NoData: No clip was available that matched the requested data type. *********************************************************************************************************************/ -static ERROR CLIPBOARD_GetFiles(objClipboard *Self, struct clipGetFiles *Args) +static ERR CLIPBOARD_GetFiles(objClipboard *Self, struct clipGetFiles *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); log.branch("Datatype: $%.8x", LONG(Args->Datatype)); @@ -462,7 +492,7 @@ static ERROR CLIPBOARD_GetFiles(objClipboard *Self, struct clipGetFiles *Args) #endif } - if (glClips.empty()) return ERR_NoData; + if (glClips.empty()) return ERR::NoData; ClipRecord *clip = &glClips.front(); @@ -470,7 +500,7 @@ static ERROR CLIPBOARD_GetFiles(objClipboard *Self, struct clipGetFiles *Args) if ((Self->Flags & CPF::HISTORY_BUFFER) != CPF::NIL) { if (Args->Datatype IS CLIPTYPE::NIL) { // Retrieve the most recent clip item, or the one indicated in the Index parameter. - if ((Args->Index < 0) or (Args->Index >= LONG(glClips.size()))) return log.warning(ERR_OutOfRange); + if ((Args->Index < 0) or (Args->Index >= LONG(glClips.size()))) return log.warning(ERR::OutOfRange); std::advance(clip, Args->Index); } else { @@ -485,18 +515,18 @@ static ERROR CLIPBOARD_GetFiles(objClipboard *Self, struct clipGetFiles *Args) if (!found) { log.warning("No clips available for datatype $%x", LONG(Args->Datatype)); - return ERR_NoData; + return ERR::NoData; } } } else if (Args->Datatype != CLIPTYPE::NIL) { - if ((clip->Datatype & Args->Datatype) IS CLIPTYPE::NIL) return ERR_NoData; + if ((clip->Datatype & Args->Datatype) IS CLIPTYPE::NIL) return ERR::NoData; } CSTRING *list = NULL; LONG str_len = 0; for (auto &item : clip->Items) str_len += item.Path.size() + 1; - if (!AllocMemory(((clip->Items.size()+1) * sizeof(STRING)) + str_len, MEM::NO_CLEAR|MEM::CALLER, &list)) { + if (AllocMemory(((clip->Items.size()+1) * sizeof(STRING)) + str_len, MEM::NO_CLEAR|MEM::CALLER, &list) IS ERR::Okay) { Args->Files = list; Args->Flags = clip->Flags; Args->Datatype = clip->Datatype; @@ -509,14 +539,14 @@ static ERROR CLIPBOARD_GetFiles(objClipboard *Self, struct clipGetFiles *Args) } *list = NULL; - return ERR_Okay; + return ERR::Okay; } - else return ERR_AllocMemory; + else return ERR::AllocMemory; } //******************************************************************************************************************** -static ERROR CLIPBOARD_Init(objClipboard *Self, APTR Void) +static ERR CLIPBOARD_Init(objClipboard *Self, APTR Void) { if ((Self->Flags & CPF::HISTORY_BUFFER) != CPF::NIL) glHistoryLimit = MAX_CLIPS; @@ -524,14 +554,14 @@ static ERROR CLIPBOARD_Init(objClipboard *Self, APTR Void) CreateFolder("clipboard:", PERMIT::READ|PERMIT::WRITE); - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR CLIPBOARD_NewObject(objClipboard *Self, APTR Void) +static ERR CLIPBOARD_NewObject(objClipboard *Self, APTR Void) { - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -553,11 +583,11 @@ AccessMemory: The clipboard memory data was not accessible. *********************************************************************************************************************/ -static ERROR CLIPBOARD_Remove(objClipboard *Self, struct clipRemove *Args) +static ERR CLIPBOARD_Remove(objClipboard *Self, struct clipRemove *Args) { pf::Log log; - if ((!Args) or (Args->Datatype IS CLIPTYPE::NIL)) return log.warning(ERR_NullArgs); + if ((!Args) or (Args->Datatype IS CLIPTYPE::NIL)) return log.warning(ERR::NullArgs); log.branch("Datatype: $%x", LONG(Args->Datatype)); @@ -573,7 +603,7 @@ static ERROR CLIPBOARD_Remove(objClipboard *Self, struct clipRemove *Args) else it++; } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -589,46 +619,45 @@ Clipboard's DataFeed action. Doing so will result in a callback to the function RequestHandler, which must be defined by the source application. The RequestHandler function must follow this template: -`ERROR RequestHandler(*Clipboard, OBJECTPTR Requester, LONG Item, BYTE Datatypes[4])` +`ERR RequestHandler(*Clipboard, OBJECTPTR Requester, LONG Item, BYTE Datatypes[4])` The function will be expected to send a `DATA::RECEIPT` to the object referenced in the Requester paramter. The receipt must provide coverage for the referenced Item and use one of the indicated Datatypes as the data format. -If this cannot be achieved then `ERR_NoSupport` should be returned by the function. +If this cannot be achieved then `ERR::NoSupport` should be returned by the function. *********************************************************************************************************************/ -static ERROR GET_RequestHandler(objClipboard *Self, FUNCTION **Value) +static ERR GET_RequestHandler(objClipboard *Self, FUNCTION **Value) { - if (Self->RequestHandler.Type != CALL_NONE) { + if (Self->RequestHandler.defined()) { *Value = &Self->RequestHandler; - return ERR_Okay; + return ERR::Okay; } - else return ERR_FieldNotSet; + else return ERR::FieldNotSet; } -static ERROR SET_RequestHandler(objClipboard *Self, FUNCTION *Value) +static ERR SET_RequestHandler(objClipboard *Self, FUNCTION *Value) { if (Value) { - if (Self->RequestHandler.Type IS CALL_SCRIPT) UnsubscribeAction(Self->RequestHandler.Script.Script, AC_Free); + if (Self->RequestHandler.isScript()) UnsubscribeAction(Self->RequestHandler.Script.Script, AC_Free); Self->RequestHandler = *Value; - if (Self->RequestHandler.Type IS CALL_SCRIPT) { - auto callback = make_function_stdc(notify_script_free); - SubscribeAction(Self->RequestHandler.Script.Script, AC_Free, &callback); + if (Self->RequestHandler.isScript()) { + SubscribeAction(Self->RequestHandler.Script.Script, AC_Free, FUNCTION(notify_script_free)); } } - else Self->RequestHandler.Type = CALL_NONE; - return ERR_Okay; + else Self->RequestHandler.clear(); + return ERR::Okay; } //******************************************************************************************************************** -static ERROR add_clip(CLIPTYPE Datatype, const std::vector &Items, CEF Flags) +static ERR add_clip(CLIPTYPE Datatype, const std::vector &Items, CEF Flags) { pf::Log log(__FUNCTION__); log.branch("Datatype: $%x, Flags: $%x, Total Items: %d", LONG(Datatype), LONG(Flags), LONG(Items.size())); - if (Items.empty()) return ERR_Args; + if (Items.empty()) return ERR::Args; if ((Flags & CEF::EXTEND) != CEF::NIL) { // Search for an existing clip that matches the requested datatype @@ -643,7 +672,7 @@ static ERROR add_clip(CLIPTYPE Datatype, const std::vector &Items, CEF glClips.erase(it); glClips.insert(glClips.begin(), clip); - return ERR_Okay; + return ERR::Okay; } } } @@ -658,24 +687,24 @@ static ERROR add_clip(CLIPTYPE Datatype, const std::vector &Items, CEF if (LONG(glClips.size()) > glHistoryLimit) glClips.pop_back(); // Remove oldest clip if history buffer is full. glClips.emplace_front(Datatype, Flags & CEF::DELETE, Items); - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR add_clip(CSTRING String) +static ERR add_clip(CSTRING String) { pf::Log log(__FUNCTION__); log.branch(); std::vector items = { std::string("clipboard:") + glProcessID + "_text" + std::to_string(glCounter++) + ".000" }; - if (auto error = add_clip(CLIPTYPE::TEXT, items); !error) { + if (auto error = add_clip(CLIPTYPE::TEXT, items); error IS ERR::Okay) { pf::Create file = { fl::Path(items[0].Path), fl::Flags(FL::WRITE|FL::NEW), fl::Permissions(PERMIT::READ|PERMIT::WRITE) }; if (file.ok()) { file->write(String, StrLength(String), 0); - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_CreateFile); + else return log.warning(ERR::CreateFile); } else return log.warning(error); } @@ -782,7 +811,7 @@ static const FieldArray clFields[] = { //******************************************************************************************************************** -ERROR create_clipboard_class(void) +ERR create_clipboard_class(void) { clClipboard = objMetaClass::create::global( fl::BaseClassID(ID_CLIPBOARD), @@ -796,7 +825,7 @@ ERROR create_clipboard_class(void) fl::Path(MOD_PATH)); LONG pid; - if (!CurrentTask()->get(FID_ProcessID, &pid)) glProcessID = std::to_string(pid); + if (CurrentTask()->get(FID_ProcessID, &pid) IS ERR::Okay) glProcessID = std::to_string(pid); - return clClipboard ? ERR_Okay : ERR_AddClass; + return clClipboard ? ERR::Okay : ERR::AddClass; } diff --git a/src/display/class_display.cpp b/src/display/class_display.cpp index 616396cec..efaa308c5 100644 --- a/src/display/class_display.cpp +++ b/src/display/class_display.cpp @@ -30,7 +30,7 @@ using namespace display; // Class definition at end of this source file. -static ERROR DISPLAY_Resize(extDisplay *, struct acResize *); +static ERR DISPLAY_Resize(extDisplay *, struct acResize *); static CSTRING dpms_name(DPMS Index); static void alloc_display_buffer(extDisplay *Self); @@ -91,7 +91,7 @@ static void printConfig(EGLDisplay display, EGLConfig config) { log.branch(); - for (LONG i=0; i < ARRAYSIZE(attributes); i++) { + for (LONG i=0; i < std::ssize(attributes); i++) { int attribute = attributes[i]; CSTRING name = names[i]; if (eglGetConfigAttrib(display, config, attribute, value)) { @@ -144,7 +144,7 @@ static void get_resolutions(extDisplay *Self) static void update_displayinfo(extDisplay *Self) { - if (StrMatch("SystemDisplay", Self->Name) != ERR_Okay) return; + if (StrMatch("SystemDisplay", Self->Name) != ERR::Okay) return; glDisplayInfo.DisplayID = 0; get_display_info(Self->UID, &glDisplayInfo, sizeof(DISPLAYINFO)); @@ -158,12 +158,12 @@ void resize_feedback(FUNCTION *Feedback, OBJECTID DisplayID, LONG X, LONG Y, LON log.traceBranch("%dx%d, %dx%d", X, Y, Width, Height); - if (Feedback->Type IS CALL_STDC) { - auto routine = (ERROR (*)(OBJECTID, LONG, LONG, LONG, LONG))Feedback->StdC.Routine; + if (Feedback->isC()) { + auto routine = (ERR (*)(OBJECTID, LONG, LONG, LONG, LONG, APTR))Feedback->StdC.Routine; pf::SwitchContext ctx(Feedback->StdC.Context); - routine(DisplayID, X, Y, Width, Height); + routine(DisplayID, X, Y, Width, Height, Feedback->StdC.Meta); } - else if (Feedback->Type IS CALL_SCRIPT) { + else if (Feedback->isScript()) { const ScriptArg args[] = { { "Display", DisplayID, FD_OBJECTID }, { "X", X }, @@ -171,15 +171,15 @@ void resize_feedback(FUNCTION *Feedback, OBJECTID DisplayID, LONG X, LONG Y, LON { "Width", Width }, { "Height", Height } }; - scCallback(Feedback->Script.Script, Feedback->Script.ProcedureID, args, ARRAYSIZE(args), NULL); + scCallback(Feedback->Script.Script, Feedback->Script.ProcedureID, args, std::ssize(args), NULL); } } //******************************************************************************************************************** -static void notify_resize_free(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, APTR Args) +static void notify_resize_free(OBJECTPTR Object, ACTIONID ActionID, ERR Result, APTR Args) { - ((extDisplay *)CurrentContext())->ResizeFeedback.Type = CALL_NONE; + ((extDisplay *)CurrentContext())->ResizeFeedback.clear(); } /********************************************************************************************************************* @@ -188,7 +188,7 @@ Activate: Activating a display has the same effect as calling the Show action. -END- *********************************************************************************************************************/ -static ERROR DISPLAY_Activate(extDisplay *Self, APTR Void) +static ERR DISPLAY_Activate(extDisplay *Self, APTR Void) { return acShow(Self); } @@ -202,7 +202,7 @@ Private -END- *********************************************************************************************************************/ -static ERROR DISPLAY_CheckXWindow(extDisplay *Self, APTR Void) +static ERR DISPLAY_CheckXWindow(extDisplay *Self, APTR Void) { #ifdef __xwindows__ @@ -222,7 +222,7 @@ static ERROR DISPLAY_CheckXWindow(extDisplay *Self, APTR Void) } #endif - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -231,16 +231,16 @@ Clear: Clears a display's image data and hardware buffers (e.g. OpenGL) -END- *********************************************************************************************************************/ -static ERROR DISPLAY_Clear(extDisplay *Self, APTR Void) +static ERR DISPLAY_Clear(extDisplay *Self, APTR Void) { #ifdef _GLES_ if (!lock_graphics_active(__func__)) { glClearColorx(Self->Bitmap->BkgdRGB.Red, Self->Bitmap->BkgdRGB.Green, Self->Bitmap->BkgdRGB.Blue, 255); glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT); unlock_graphics(); - return ERR_Okay; + return ERR::Okay; } - else return ERR_LockFailed; + else return ERR::LockFailed; #else return acClear(Self->Bitmap); #endif @@ -252,11 +252,11 @@ DataFeed: Declared for internal purposes - do not call. -END- *********************************************************************************************************************/ -static ERROR DISPLAY_DataFeed(extDisplay *Self, struct acDataFeed *Args) +static ERR DISPLAY_DataFeed(extDisplay *Self, struct acDataFeed *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); #ifdef _WIN32 if (Args->Datatype IS DATA::REQUEST) { @@ -278,7 +278,7 @@ static ERROR DISPLAY_DataFeed(extDisplay *Self, struct acDataFeed *Args) } STRING xml; - if (!AllocMemory(xmlsize, MEM::STRING|MEM::NO_CLEAR, &xml)) { + if (AllocMemory(xmlsize, MEM::STRING|MEM::NO_CLEAR, &xml) IS ERR::Okay) { LONG pos = snprintf(xml, xmlsize, "", total_items, request->Item); for (LONG i=0; i < total_items; i++) { @@ -301,14 +301,14 @@ static ERROR DISPLAY_DataFeed(extDisplay *Self, struct acDataFeed *Args) FreeResource(xml); } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } - else return log.warning(ERR_NoSupport); + else return log.warning(ERR::NoSupport); #endif } #endif - return log.warning(ERR_NoSupport); + return log.warning(ERR::NoSupport); } /********************************************************************************************************************* @@ -328,9 +328,9 @@ NoSupport: The display driver does not support DPMS. *********************************************************************************************************************/ -static ERROR DISPLAY_Disable(extDisplay *Self, APTR Void) +static ERR DISPLAY_Disable(extDisplay *Self, APTR Void) { - return ERR_NoSupport; + return ERR::NoSupport; } /********************************************************************************************************************* @@ -339,9 +339,9 @@ Enable: Restores the screen display from power saving mode. -END- *********************************************************************************************************************/ -static ERROR DISPLAY_Enable(extDisplay *Self, APTR Void) +static ERR DISPLAY_Enable(extDisplay *Self, APTR Void) { - return ERR_NoSupport; + return ERR::NoSupport; } //******************************************************************************************************************** @@ -349,9 +349,9 @@ static ERROR DISPLAY_Enable(extDisplay *Self, APTR Void) // redraw is required. It is the responsibility of the program that created the Display object to subscribe to the // Draw action and act on it. -static ERROR DISPLAY_Draw(extDisplay *Self, APTR Void) +static ERR DISPLAY_Draw(extDisplay *Self, APTR Void) { - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -360,7 +360,7 @@ Flush: Flush pending graphics operations to the display. -END- *********************************************************************************************************************/ -static ERROR DISPLAY_Flush(extDisplay *Self, APTR Void) +static ERR DISPLAY_Flush(extDisplay *Self, APTR Void) { #ifdef __xwindows__ XSync(XDisplay, False); @@ -370,12 +370,12 @@ static ERROR DISPLAY_Flush(extDisplay *Self, APTR Void) unlock_graphics(); } #endif - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR DISPLAY_Focus(extDisplay *Self, APTR Void) +static ERR DISPLAY_Focus(extDisplay *Self, APTR Void) { pf::Log log; @@ -385,12 +385,12 @@ static ERROR DISPLAY_Focus(extDisplay *Self, APTR Void) #elif __xwindows__ if ((Self->Flags & SCR::BORDERLESS) != SCR::NIL) XSetInputFocus(XDisplay, Self->XWindowHandle, RevertToNone, CurrentTime); #endif - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR DISPLAY_Free(extDisplay *Self, APTR Void) +static ERR DISPLAY_Free(extDisplay *Self, APTR Void) { pf::Log log; @@ -405,10 +405,17 @@ static ERROR DISPLAY_Free(extDisplay *Self, APTR Void) if (Self->WindowHandle IS (APTR)glDisplayWindow) glDisplayWindow = 0; + if (Self->XPixmap) { + XFreePixmap(XDisplay, Self->XPixmap); + Self->XPixmap = 0; + ((extBitmap *)Self->Bitmap)->x11.drawable = 0; + } + // Kill all expose events associated with the X Window owned by the display if (XDisplay) { - while (XCheckWindowEvent(XDisplay, Self->XWindowHandle, ExposureMask, &xevent) IS True); + while (XCheckWindowEvent(XDisplay, Self->XWindowHandle, + ExposureMask|FocusChangeMask|StructureNotifyMask, &xevent) IS True); if ((Self->Flags & SCR::CUSTOM_WINDOW) IS SCR::NIL) { if (Self->WindowHandle) { @@ -417,6 +424,8 @@ static ERROR DISPLAY_Free(extDisplay *Self, APTR Void) } } } + + XSync(XDisplay, False); #endif #ifdef _WIN32 @@ -443,7 +452,7 @@ static ERROR DISPLAY_Free(extDisplay *Self, APTR Void) if (Self->Bitmap) { FreeResource(Self->Bitmap); Self->Bitmap = NULL; } Self->~extDisplay(); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -452,18 +461,18 @@ GetVar: Retrieve formatted information from the display. -END- *********************************************************************************************************************/ -static ERROR DISPLAY_GetVar(extDisplay *Self, struct acGetVar *Args) +static ERR DISPLAY_GetVar(extDisplay *Self, struct acGetVar *Args) { pf::Log log; ULONG colours; - if (!Args) return log.warning(ERR_NullArgs); - if ((!Args->Field) or (!Args->Buffer) or (Args->Size < 1)) return log.warning(ERR_Args); + if (!Args) return log.warning(ERR::NullArgs); + if ((!Args->Field) or (!Args->Buffer) or (Args->Size < 1)) return log.warning(ERR::Args); STRING buffer = Args->Buffer; buffer[0] = 0; - if (!StrCompare("resolution(", Args->Field, 11)) { + if (StrCompare("resolution(", Args->Field, 11) IS ERR::Okay) { // Field is in the format: Resolution(Index, Format) Where 'Format' contains % symbols to indicate variable references. CSTRING str = Args->Field + 11; @@ -475,7 +484,7 @@ static ERROR DISPLAY_GetVar(extDisplay *Self, struct acGetVar *Args) if (Self->Resolutions.empty()) get_resolutions(Self); if (!Self->Resolutions.empty()) { - if (index >= LONG(Self->Resolutions.size())) return ERR_OutOfRange; + if (index >= LONG(Self->Resolutions.size())) return ERR::OutOfRange; LONG i = 0; while ((*str) and (*str != ')') and (i < Args->Size-1)) { @@ -504,11 +513,11 @@ static ERROR DISPLAY_GetVar(extDisplay *Self, struct acGetVar *Args) } buffer[i] = 0; - return ERR_Okay; + return ERR::Okay; } - else return ERR_NoData; + else return ERR::NoData; } - else return ERR_NoSupport; + else return ERR::NoSupport; } /********************************************************************************************************************* @@ -521,7 +530,7 @@ displays available then the user's viewport will be blank after calling this act -END- *********************************************************************************************************************/ -static ERROR DISPLAY_Hide(extDisplay *Self, APTR Void) +static ERR DISPLAY_Hide(extDisplay *Self, APTR Void) { pf::Log log; @@ -530,7 +539,10 @@ static ERROR DISPLAY_Hide(extDisplay *Self, APTR Void) #ifdef _WIN32 winHideWindow(Self->WindowHandle); #elif __xwindows__ - if (XDisplay) XUnmapWindow(XDisplay, Self->XWindowHandle); + if ((XDisplay) and (Self->XWindowHandle)) { + XUnmapWindow(XDisplay, Self->XWindowHandle); + XSync(XDisplay, False); + } #elif __snap__ // If the system is shutting down, don't touch the display. This makes things look tidier when the system shuts down. @@ -547,39 +559,42 @@ static ERROR DISPLAY_Hide(extDisplay *Self, APTR Void) #endif Self->Flags &= ~SCR::VISIBLE; - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR DISPLAY_Init(extDisplay *Self, APTR Void) +static ERR DISPLAY_Init(extDisplay *Self, APTR Void) { pf::Log log; - struct gfxUpdatePalette pal; - #ifdef __xwindows__ - XWindowAttributes winattrib; - XPixmapFormatValues *list; - LONG xbpp, xbytes; - LONG count; - #endif #ifdef __xwindows__ // Figure out how many bits and bytes are used per pixel on this XDisplay - xbpp = DefaultDepth(XDisplay, DefaultScreen(XDisplay)); + auto xbpp = DefaultDepth(XDisplay, DefaultScreen(XDisplay)); if (xbpp <= 8) { log.msg(VLF::CRITICAL, "Please change your X11 setup so that it runs in 15 bit mode or better."); log.msg(VLF::CRITICAL, "Currently X11 is configured to use %d bit graphics.", xbpp); - return ERR_Failed; + return ERR::Failed; + } + + if (xbpp IS 24) { + static bool bpp_warning = false; + if (!bpp_warning) { + bpp_warning = true; + log.warning("Running in 32bpp instead of 24bpp is strongly recommended."); + } } + LONG xbytes; if (xbpp <= 8) xbytes = 1; else if (xbpp <= 16) xbytes = 2; else if (xbpp <= 24) xbytes = 3; else xbytes = 4; - if ((list = XListPixmapFormats(XDisplay, &count))) { + LONG count; + if (auto list = XListPixmapFormats(XDisplay, &count)) { for (LONG i=0; i < count; i++) { if (list[i].depth IS xbpp) { xbytes = list[i].bits_per_pixel; @@ -603,7 +618,7 @@ static ERROR DISPLAY_Init(extDisplay *Self, APTR Void) auto bmp = (extBitmap *)Self->Bitmap; DISPLAYINFO info; - if (get_display_info(0, &info, sizeof(info))) return log.warning(ERR_Failed); + if (get_display_info(0, &info, sizeof(info)) != ERR::Okay) return log.warning(ERR::Failed); if (!Self->Width) { Self->Width = info.Width; @@ -695,7 +710,7 @@ static ERROR DISPLAY_Init(extDisplay *Self, APTR Void) |KeyPressMask|KeyReleaseMask|ButtonPressMask|ButtonReleaseMask|FocusChangeMask; if (!glX11.Manager) { - // If we are running inside a foreign window manager, use the following routine to create a new X11 window for us to run in. + // Window creation for running inside a foreign window manager. log.msg("Creating X11 window %dx%d,%dx%d, Override: %d, XDisplay: %p, Parent: %" PF64, Self->X, Self->Y, Self->Width, Self->Height, swa.override_redirect, XDisplay, (LARGE)Self->XWindowHandle); @@ -712,25 +727,55 @@ static ERROR DISPLAY_Init(extDisplay *Self, APTR Void) bmp->Flags |= BMF::ALPHA_CHANNEL|BMF::FIXED_DEPTH; bmp->BitsPerPixel = 32; bmp->BytesPerPixel = 4; + xbpp = 32; } if (!Self->XWindowHandle) { if (!(Self->XWindowHandle = XCreateWindow(XDisplay, DefaultRootWindow(XDisplay), Self->X, Self->Y, Self->Width, Self->Height, 0 /* Border */, depth, InputOutput, visual, cwflags, &swa))) { - log.warning("XCreateWindow() failed."); - return ERR_SystemCall; + return log.warning(ERR::SystemCall); } } else { // If the WindowHandle field is already set, use it as the parent for the new window. if (!(Self->XWindowHandle = XCreateWindow(XDisplay, Self->XWindowHandle, 0, 0, Self->Width, Self->Height, 0, depth, InputOutput, visual, cwflags, &swa))) { - log.warning("XCreateWindow() failed."); - return ERR_SystemCall; + return log.warning(ERR::SystemCall); } } - bmp->set(FID_Handle, (APTR)Self->XWindowHandle); + bmp->x11.window = Self->XWindowHandle; + + if ((bmp->Flags & BMF::ALPHA_CHANNEL) != BMF::NIL) { + // For composite windows, we can draw directly to the Window handle + bmp->x11.drawable = Self->XWindowHandle; + } + else { + // Create a pixmap buffer and associate it with the window by setting it as the background. + + // Although creating a pixmap with the same size as the display is a little excessive, it produces + // the best user experience when resizing windows + bmp->x11.pix_width = info.Width; //Self->Width; + bmp->x11.pix_height = info.Height; //Self->Height; + if (!(Self->XPixmap = XCreatePixmap(XDisplay, Self->XWindowHandle, bmp->x11.pix_width, bmp->x11.pix_height, xbpp))) { + return log.warning(ERR::SystemCall); + } + + // Blanking the pixmap reduces visible glitches caused by window resizing. + if (auto gc = XCreateGC(XDisplay, Self->XPixmap, 0, 0)) { + XSetFunction(XDisplay, gc, GXcopy); + if ((swa.override_redirect) and (glXCompositeSupported)) { + XSetForeground(XDisplay, gc, 0x000000); + } + else XSetForeground(XDisplay, gc, 0xd0d0d0); + XFillRectangle(XDisplay, Self->XPixmap, gc, 0, 0, info.Width, info.Height); + XFreeGC(XDisplay, gc); + } + + XSetWindowBackgroundPixmap(XDisplay, Self->XWindowHandle, Self->XPixmap); + + bmp->x11.drawable = Self->XPixmap; + } CSTRING name; if ((!CurrentTask()->getPtr(FID_Name, &name)) and (name)) { @@ -739,7 +784,7 @@ static ERROR DISPLAY_Init(extDisplay *Self, APTR Void) else XStoreName(XDisplay, Self->XWindowHandle, "Parasol"); Atom protocols[1] = { XWADeleteWindow }; - XSetWMProtocols(XDisplay, Self->XWindowHandle, protocols, ARRAYSIZE(protocols)); + XSetWMProtocols(XDisplay, Self->XWindowHandle, protocols, std::ssize(protocols)); Self->Flags |= SCR::HOSTED; @@ -762,7 +807,7 @@ static ERROR DISPLAY_Init(extDisplay *Self, APTR Void) XSizeHints hints = { .flags = USPosition|USSize }; XSetWMNormalHints(XDisplay, Self->XWindowHandle, &hints); - if (InitObject(bmp) != ERR_Okay) return log.warning(ERR_Init); + if (InitObject(bmp) != ERR::Okay) return log.warning(ERR::Init); } else { // If we are the window manager, set up the root window as our display. if (!Self->WindowHandle) Self->XWindowHandle = DefaultRootWindow(XDisplay); @@ -771,13 +816,14 @@ static ERROR DISPLAY_Init(extDisplay *Self, APTR Void) if (XRandRBase) xrSelectInput(Self->XWindowHandle); + XWindowAttributes winattrib; XGetWindowAttributes(XDisplay, Self->XWindowHandle, &winattrib); Self->Width = winattrib.width; Self->Height = winattrib.height; bmp->Width = Self->Width; bmp->Height = Self->Height; - if (InitObject(bmp) != ERR_Okay) return log.warning(ERR_Init); + if (InitObject(bmp) != ERR::Okay) return log.warning(ERR::Init); if (glDGAAvailable) { bmp->Flags |= BMF::X11_DGA; @@ -798,8 +844,8 @@ static ERROR DISPLAY_Init(extDisplay *Self, APTR Void) bmp->Flags |= BMF::NO_DATA; bmp->DataFlags = MEM::VIDEO; - if (InitObject(bmp) != ERR_Okay) { - return log.warning(ERR_Init); + if (InitObject(bmp) != ERR::Okay) { + return log.warning(ERR::Init); } if (!Self->WindowHandle) { @@ -809,7 +855,7 @@ static ERROR DISPLAY_Init(extDisplay *Self, APTR Void) } else { OBJECTID surface_id; - if (!FindObject("SystemSurface", ID_SURFACE, FOF::NIL, &surface_id)) { + if (FindObject("SystemSurface", ID_SURFACE, FOF::NIL, &surface_id) IS ERR::Okay) { if (surface_id IS Self->ownerID()) desktop = true; } } @@ -819,17 +865,17 @@ static ERROR DISPLAY_Init(extDisplay *Self, APTR Void) HWND popover = 0; if (Self->PopOverID) { extDisplay *other_display; - if (!AccessObject(Self->PopOverID, 3000, &other_display)) { + if (AccessObject(Self->PopOverID, 3000, &other_display) IS ERR::Okay) { popover = other_display->WindowHandle; ReleaseObject(other_display); } - else log.warning(ERR_AccessObject); + else log.warning(ERR::AccessObject); } if (!(Self->WindowHandle = (APTR)winCreateScreen(popover, &Self->X, &Self->Y, &Self->Width, &Self->Height, ((Self->Flags & SCR::MAXIMISE) != SCR::NIL) ? 1 : 0, ((Self->Flags & SCR::BORDERLESS) != SCR::NIL) ? 1 : 0, name, ((Self->Flags & SCR::COMPOSITE) != SCR::NIL) ? 1 : 0, Self->Opacity, desktop))) { - return log.warning(ERR_SystemCall); + return log.warning(ERR::SystemCall); } } else { @@ -837,7 +883,7 @@ static ERROR DISPLAY_Init(extDisplay *Self, APTR Void) // window related messages. if (!(Self->WindowHandle = (APTR)winCreateChild(Self->WindowHandle, Self->X, Self->Y, Self->Width, Self->Height))) { - return log.warning(ERR_SystemCall); + return log.warning(ERR::SystemCall); } } @@ -849,7 +895,7 @@ static ERROR DISPLAY_Init(extDisplay *Self, APTR Void) winGetMargins(Self->WindowHandle, &Self->LeftMargin, &Self->TopMargin, &Self->RightMargin, &Self->BottomMargin); #elif _GLES_ - ERROR error; + ERR error; if (Self->Bitmap->BitsPerPixel) glEGLPreferredDepth = Self->Bitmap->BitsPerPixel; else glEGLPreferredDepth = 0; @@ -867,8 +913,8 @@ static ERROR DISPLAY_Init(extDisplay *Self, APTR Void) bmp->Flags |= BMF::NO_DATA; bmp->DataFlags = MEM::VIDEO; - if (InitObject(bmp) != ERR_Okay) { - return log.warning(ERR_Init); + if (InitObject(bmp) != ERR::Okay) { + return log.warning(ERR::Init); } #else @@ -877,7 +923,7 @@ static ERROR DISPLAY_Init(extDisplay *Self, APTR Void) if ((Self->Flags & SCR::BUFFER) != SCR::NIL) alloc_display_buffer(Self); - pal.NewPalette = bmp->Palette; + struct gfxUpdatePalette pal = { .NewPalette = bmp->Palette }; Action(MT_GfxUpdatePalette, Self, &pal); // Take a record of the pixel format for GetDisplayInfo() @@ -888,7 +934,7 @@ static ERROR DISPLAY_Init(extDisplay *Self, APTR Void) update_displayinfo(Self); // Update the glDisplayInfo cache. - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -910,16 +956,19 @@ Okay *********************************************************************************************************************/ -static ERROR DISPLAY_Minimise(extDisplay *Self, APTR Void) +static ERR DISPLAY_Minimise(extDisplay *Self, APTR Void) { pf::Log log; log.branch(); #ifdef _WIN32 winMinimiseWindow(Self->WindowHandle); #elif __xwindows__ - if (XDisplay) XUnmapWindow(XDisplay, Self->XWindowHandle); + if (XDisplay) { + XUnmapWindow(XDisplay, Self->XWindowHandle); + XSync(XDisplay, False); + } #endif - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -950,11 +999,11 @@ Move: Move the display to a new display position (relative coordinates). -END- *********************************************************************************************************************/ -static ERROR DISPLAY_Move(extDisplay *Self, struct acMove *Args) +static ERR DISPLAY_Move(extDisplay *Self, struct acMove *Args) { pf::Log log; - if (!Args) return ERR_NullArgs; + if (!Args) return ERR::NullArgs; //log.branch("Moving display by %dx%d", (LONG)Args->DeltaX, (LONG)Args->DeltaY); @@ -962,28 +1011,28 @@ static ERROR DISPLAY_Move(extDisplay *Self, struct acMove *Args) if (!winMoveWindow(Self->WindowHandle, Self->X + Self->LeftMargin + Args->DeltaX, - Self->Y + Self->TopMargin + Args->DeltaY)) return ERR_Failed; + Self->Y + Self->TopMargin + Args->DeltaY)) return ERR::Failed; - return ERR_Okay; + return ERR::Okay; #elif __xwindows__ // Handling margins isn't necessary as the window manager will take that into account when it receives the move request. - if (!XDisplay) return ERR_Failed; + if (!XDisplay) return ERR::Failed; XMoveWindow(XDisplay, Self->XWindowHandle, Self->X + Args->DeltaX, Self->Y + Args->DeltaY); - return ERR_Okay; + return ERR::Okay; #elif __snap__ Self->X += Args->DeltaX; Self->Y += Args->DeltaY; - return ERR_Okay; + return ERR::Okay; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif @@ -995,7 +1044,7 @@ MoveToBack: Move the display to the back of the display list. -END- *********************************************************************************************************************/ -static ERROR DISPLAY_MoveToBack(extDisplay *Self, APTR Void) +static ERR DISPLAY_MoveToBack(extDisplay *Self, APTR Void) { pf::Log log; log.branch("%s", Self->Name); @@ -1006,7 +1055,7 @@ static ERROR DISPLAY_MoveToBack(extDisplay *Self, APTR Void) if (XDisplay) XLowerWindow(XDisplay, Self->XWindowHandle); #endif - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1015,16 +1064,19 @@ MoveToFront: Move the display to the front of the display list. -END- *********************************************************************************************************************/ -static ERROR DISPLAY_MoveToFront(extDisplay *Self, APTR Void) +static ERR DISPLAY_MoveToFront(extDisplay *Self, APTR Void) { pf::Log log; log.branch("%s", Self->Name); #ifdef _WIN32 winMoveToFront(Self->WindowHandle); #elif __xwindows__ - if (XDisplay) XRaiseWindow(XDisplay, Self->XWindowHandle); + if (XDisplay) { + XRaiseWindow(XDisplay, Self->XWindowHandle); + XSync(XDisplay, False); + } #endif - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1037,16 +1089,16 @@ In a hosted environment, the supplied coordinates are treated as being indicativ window (not the client area). For full-screen displays, MoveToPoint can alter the screen position for the hardware device managing the display -output. This is a rare feature that requires hardware support. ERR_NoSupport is returned if this feature is +output. This is a rare feature that requires hardware support. ERR::NoSupport is returned if this feature is unavailable. -END- *********************************************************************************************************************/ -static ERROR DISPLAY_MoveToPoint(extDisplay *Self, struct acMoveToPoint *Args) +static ERR DISPLAY_MoveToPoint(extDisplay *Self, struct acMoveToPoint *Args) { pf::Log log; - if (!Args) return ERR_NullArgs; + if (!Args) return ERR::NullArgs; log.traceBranch("Moving display to %dx%d", F2T(Args->X), F2T(Args->Y)); @@ -1056,11 +1108,11 @@ static ERROR DISPLAY_MoveToPoint(extDisplay *Self, struct acMoveToPoint *Args) if (!winMoveWindow(Self->WindowHandle, ((Args->Flags & MTF::X) != MTF::NIL) ? Args->X : F2T(Self->X) + Self->LeftMargin, - ((Args->Flags & MTF::Y) != MTF::NIL) ? Args->Y : F2T(Self->Y) + Self->TopMargin)) return ERR_Failed; + ((Args->Flags & MTF::Y) != MTF::NIL) ? Args->Y : F2T(Self->Y) + Self->TopMargin)) return ERR::Failed; if ((Args->Flags & MTF::X) != MTF::NIL) Self->X = F2T(Args->X) + Self->LeftMargin; if ((Args->Flags & MTF::Y) != MTF::NIL) Self->Y = F2T(Args->Y) + Self->TopMargin; - return ERR_Okay; + return ERR::Okay; #elif __xwindows__ @@ -1072,28 +1124,28 @@ static ERROR DISPLAY_MoveToPoint(extDisplay *Self, struct acMoveToPoint *Args) if ((Args->Flags & MTF::X) != MTF::NIL) Self->X = F2T(Args->X); if ((Args->Flags & MTF::Y) != MTF::NIL) Self->Y = F2T(Args->Y); - return ERR_Okay; + return ERR::Okay; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } //******************************************************************************************************************** -static ERROR DISPLAY_NewObject(extDisplay *Self, APTR Void) +static ERR DISPLAY_NewObject(extDisplay *Self, APTR Void) { new (Self) extDisplay; - if (NewObject(ID_BITMAP, NF::INTEGRAL, &Self->Bitmap)) return ERR_NewObject; + if (NewObject(ID_BITMAP, NF::INTEGRAL, &Self->Bitmap) != ERR::Okay) return ERR::NewObject; OBJECTID id; - if (FindObject("SystemVideo", 0, FOF::NIL, &id) != ERR_Okay) SetName(Self->Bitmap, "SystemVideo"); + if (FindObject("SystemVideo", 0, FOF::NIL, &id) != ERR::Okay) SetName(Self->Bitmap, "SystemVideo"); if (!Self->Name[0]) { - if (FindObject("SystemDisplay", 0, FOF::NIL, &id) != ERR_Okay) SetName(Self, "SystemDisplay"); + if (FindObject("SystemDisplay", 0, FOF::NIL, &id) != ERR::Okay) SetName(Self, "SystemDisplay"); } #ifdef __xwindows__ @@ -1148,7 +1200,7 @@ static ERROR DISPLAY_NewObject(extDisplay *Self, APTR Void) Self->DisplayType = DT::NATIVE; #endif - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1157,16 +1209,16 @@ Redimension: Moves and resizes a display object in a single action call. -END- *********************************************************************************************************************/ -static ERROR DISPLAY_Redimension(extDisplay *Self, struct acRedimension *Args) +static ERR DISPLAY_Redimension(extDisplay *Self, struct acRedimension *Args) { - if (!Args) return ERR_NullArgs; + if (!Args) return ERR::NullArgs; struct acMoveToPoint moveto = { Args->X, Args->Y, 0, MTF::X|MTF::Y }; DISPLAY_MoveToPoint(Self, &moveto); struct acResize resize = { Args->Width, Args->Height, Args->Depth }; DISPLAY_Resize(Self, &resize); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1177,18 +1229,20 @@ If the display is hosted, the Width and Height values will determine the size of -END- *********************************************************************************************************************/ -static ERROR DISPLAY_Resize(extDisplay *Self, struct acResize *Args) +static ERR DISPLAY_Resize(extDisplay *Self, struct acResize *Args) { pf::Log log; log.branch(); + if (!Self->initialised()) return log.warning(ERR::NotInitialised); + #ifdef _WIN32 - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); if (!winResizeWindow(Self->WindowHandle, 0x7fffffff, 0x7fffffff, Args->Width, Args->Height)) { - return ERR_Failed; + return ERR::Failed; } Action(AC_Resize, Self->Bitmap, Args); @@ -1197,22 +1251,19 @@ static ERROR DISPLAY_Resize(extDisplay *Self, struct acResize *Args) #elif __xwindows__ - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); - if (XDisplay) XResizeWindow(XDisplay, Self->XWindowHandle, Args->Width, Args->Height); + if (XDisplay) { + resize_pixmap(Self, Args->Width, Args->Height); + XResizeWindow(XDisplay, Self->XWindowHandle, Args->Width, Args->Height); + } + Action(AC_Resize, Self->Bitmap, Args); Self->Width = Self->Bitmap->Width; Self->Height = Self->Bitmap->Height; #elif __snap__ - UWORD gfxmode; - GA_modeInfo modeinfo; - LONG i, vx, vy, bytesperline, width, height; - LONG bestweight, weight, display; - - if (!Args) return log.warning(ERR_Args); - // Scan the available display modes and choose the one that most closely matches the requested display dimensions. if (!(width = Args->Width)) width = Self->Width; @@ -1250,9 +1301,9 @@ static ERROR DISPLAY_Resize(extDisplay *Self, struct acResize *Args) vx = -1; vy = -1; bytesperline = -1; - if (sciOpenVideoMode(gfxmode, &modeinfo, &vx, &vy, &bytesperline, &Self->VideoHandle, 0) != ERR_Okay) { + if (sciOpenVideoMode(gfxmode, &modeinfo, &vx, &vy, &bytesperline, &Self->VideoHandle, 0) != ERR::Okay) { log.warning("Failed to set the requested video mode."); - return ERR_NoSupport; + return ERR::NoSupport; } Self->GfxMode = gfxmode; @@ -1273,7 +1324,7 @@ static ERROR DISPLAY_Resize(extDisplay *Self, struct acResize *Args) Self->HDensity = 0; // DPI needs to be recalculated. Self->VDensity = 0; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1282,7 +1333,7 @@ SaveImage: Saves the image of a display to a data object. -END- *********************************************************************************************************************/ -static ERROR DISPLAY_SaveImage(extDisplay *Self, struct acSaveImage *Args) +static ERR DISPLAY_SaveImage(extDisplay *Self, struct acSaveImage *Args) { return Action(AC_SaveImage, Self->Bitmap, Args); } @@ -1293,7 +1344,7 @@ SaveSettings: Saves the current display settings as the default. -END- *********************************************************************************************************************/ -static ERROR DISPLAY_SaveSettings(extDisplay *Self, APTR Void) +static ERR DISPLAY_SaveSettings(extDisplay *Self, APTR Void) { pf::Log log; @@ -1342,12 +1393,12 @@ static ERROR DISPLAY_SaveSettings(extDisplay *Self, APTR Void) acSaveSettings(*config); } } - else return log.warning(ERR_CreateObject); + else return log.warning(ERR::CreateObject); } #endif - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1356,7 +1407,7 @@ static ERROR DISPLAY_SaveSettings(extDisplay *Self, APTR Void) SizeHints: Sets the width and height restrictions for the host window (hosted environments only). If a display is hosted in a desktop window, it may be possible to enforce size restrictions that prevent the window -from being shrunk or expanded beyond a certain size. This feature is platform dependent and `ERR_NoSupport` +from being shrunk or expanded beyond a certain size. This feature is platform dependent and `ERR::NoSupport` will be returned if it is not implemented. -INPUT- @@ -1373,7 +1424,7 @@ NoSupport: The host platform does not support this feature. *********************************************************************************************************************/ -static ERROR DISPLAY_SizeHints(extDisplay *Self, struct gfxSizeHints *Args) +static ERR DISPLAY_SizeHints(extDisplay *Self, struct gfxSizeHints *Args) { #ifdef __xwindows__ XSizeHints hints = { .flags = 0 }; @@ -1395,9 +1446,9 @@ static ERROR DISPLAY_SizeHints(extDisplay *Self, struct gfxSizeHints *Args) } XSetWMNormalHints(XDisplay, Self->XWindowHandle, &hints); - return ERR_Okay; + return ERR::Okay; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -1438,19 +1489,19 @@ Failed: Failed to switch to the requested display mode. *********************************************************************************************************************/ -static ERROR DISPLAY_SetDisplay(extDisplay *Self, struct gfxSetDisplay *Args) +static ERR DISPLAY_SetDisplay(extDisplay *Self, struct gfxSetDisplay *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); #ifdef _WIN32 // NOTE: Dimensions are measured relative to the client area, not the window including its borders. - log.msg(VLF::BRANCH|VLF::EXTAPI, "%dx%d, %dx%d", Args->X, Args->Y, Args->Width, Args->Height); + log.msg(VLF::BRANCH|VLF::DETAIL, "%dx%d, %dx%d", Args->X, Args->Y, Args->Width, Args->Height); if (!winResizeWindow(Self->WindowHandle, Args->X, Args->Y, Args->Width, Args->Height)) { - return log.warning(ERR_Failed); + return log.warning(ERR::Failed); } log.trace("Resizing the video bitmap."); @@ -1464,13 +1515,13 @@ static ERROR DISPLAY_SetDisplay(extDisplay *Self, struct gfxSetDisplay *Args) log.branch("%dx%d,%dx%d @ %.2fHz, %d bit", Args->X, Args->Y, Args->Width, Args->Height, Args->RefreshRate, Args->BitsPerPixel); - if ((Args->Width IS Self->Width) and (Args->Height IS Self->Height)) return ERR_Okay; + if ((Args->Width IS Self->Width) and (Args->Height IS Self->Height)) return ERR::Okay; LONG width = Args->Width; LONG height = Args->Height; if (glX11.Manager) { // The video mode can only be changed with the XRandR extension - if ((XRandRBase) and (xrSetDisplayMode(&width, &height) IS ERR_Okay)) { + if ((XRandRBase) and (xrSetDisplayMode(&width, &height) IS ERR::Okay)) { Self->RefreshRate = 0; Self->Width = width; Self->Height = height; @@ -1479,9 +1530,9 @@ static ERROR DISPLAY_SetDisplay(extDisplay *Self, struct gfxSetDisplay *Args) // Note: The RandR extension changes the video mode without actually changing the size of the bitmap area, so we don't resize the bitmap. - return ERR_Okay; + return ERR::Okay; } - else return ERR_Failed; + else return ERR::Failed; } else { XResizeWindow(XDisplay, Self->XWindowHandle, width, height); @@ -1505,7 +1556,7 @@ static ERROR DISPLAY_SetDisplay(extDisplay *Self, struct gfxSetDisplay *Args) if ((Self->Flags & SCR::BUFFER) != SCR::NIL) alloc_display_buffer(Self); update_displayinfo(Self); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1537,14 +1588,14 @@ NoSupport: The graphics hardware does not support gamma correction. *********************************************************************************************************************/ -static ERROR DISPLAY_SetGamma(extDisplay *Self, struct gfxSetGamma *Args) +static ERR DISPLAY_SetGamma(extDisplay *Self, struct gfxSetGamma *Args) { #ifdef __snap__ pf::Log log; GA_palette palette[256]; DOUBLE intensity, red, green, blue; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); red = Args->Red; green = Args->Green; @@ -1564,17 +1615,17 @@ static ERROR DISPLAY_SetGamma(extDisplay *Self, struct gfxSetGamma *Args) Self->Gamma[2] = blue; } - for (LONG i=0; i < ARRAYSIZE(palette); i++) { + for (LONG i=0; i < std::ssize(palette); i++) { intensity = (DOUBLE)i / 255.0; palette[i].Red = F2T(pow(intensity, 1.0 / red) * 255.0); palette[i].Green = F2T(pow(intensity, 1.0 / green) * 255.0); palette[i].Blue = F2T(pow(intensity, 1.0 / blue) * 255.0); } - SetGammaCorrectData(palette, ARRAYSIZE(palette), 0, TRUE); - return ERR_Okay; + SetGammaCorrectData(palette, std::ssize(palette), 0, TRUE); + return ERR::Okay; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -1599,13 +1650,13 @@ int(GMF) Flags: Use SAVE to store the new settings. *********************************************************************************************************************/ -static ERROR DISPLAY_SetGammaLinear(extDisplay *Self, struct gfxSetGammaLinear *Args) +static ERR DISPLAY_SetGammaLinear(extDisplay *Self, struct gfxSetGammaLinear *Args) { #ifdef __snap__ pf::Log log; GA_palette palette[256]; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); DOUBLE red = Args->Red; DOUBLE green = Args->Green; @@ -1625,7 +1676,7 @@ static ERROR DISPLAY_SetGammaLinear(extDisplay *Self, struct gfxSetGammaLinear * Self->Gamma[2] = blue; } - for (WORD i=0; i < ARRAYSIZE(palette); i++) { + for (WORD i=0; i < std::ssize(palette); i++) { DOUBLE intensity = (DOUBLE)i / 255.0; if (red > 1.0) palette[i].Red = F2T(pow(intensity, 1.0 / red) * 255.0); @@ -1638,11 +1689,11 @@ static ERROR DISPLAY_SetGammaLinear(extDisplay *Self, struct gfxSetGammaLinear * else palette[i].Blue = F2T((DOUBLE)i * blue); } - glSNAP->Driver.SetGammaCorrectData(palette, ARRAYSIZE(palette), 0, TRUE); + glSNAP->Driver.SetGammaCorrectData(palette, std::ssize(palette), 0, TRUE); - return ERR_Okay; + return ERR::Okay; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -1677,19 +1728,19 @@ NullArgs *********************************************************************************************************************/ -static ERROR DISPLAY_SetMonitor(extDisplay *Self, struct gfxSetMonitor *Args) +static ERR DISPLAY_SetMonitor(extDisplay *Self, struct gfxSetMonitor *Args) { #ifdef __snap__ pf::Log log; OBJECTPTR config; GA_monitor monitor; - ERROR priverror; + ERR priverror; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); if (CurrentTaskID() != Self->ownerTask()) { log.warning("Only the owner of the display may call this method."); - return ERR_Failed; + return ERR::Failed; } log.branch("%s", Args->Name); @@ -1755,9 +1806,9 @@ static ERROR DISPLAY_SetMonitor(extDisplay *Self, struct gfxSetMonitor *Args) } if (!priverror) SetResource(RES::PRIVILEGED_USER, 0); - return ERR_Okay; + return ERR::Okay; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -1786,7 +1837,7 @@ The `VISIBLE` flag in the #Flags field will be set if the Show operation is succ *********************************************************************************************************************/ -ERROR DISPLAY_Show(extDisplay *Self, APTR Void) +ERR DISPLAY_Show(extDisplay *Self, APTR Void) { pf::Log log; @@ -1795,7 +1846,7 @@ ERROR DISPLAY_Show(extDisplay *Self, APTR Void) #ifdef __xwindows__ if (!XDisplay) { log.error("No X11 display has been found for this machine."); - return ERR_Failed; + return ERR::Failed; } // Some window managers fool with our position when mapping, so we use XMoveWindow() before and after to be @@ -1811,10 +1862,6 @@ ERROR DISPLAY_Show(extDisplay *Self, APTR Void) XMoveWindow(XDisplay, Self->XWindowHandle, Self->X, Self->Y); } - // Mapping a window may cause the window manager to resize it without sending a notification event, so check the - // window size here. - - XFlush(XDisplay); XSync(XDisplay, False); Self->LeftMargin = 0; @@ -1822,15 +1869,16 @@ ERROR DISPLAY_Show(extDisplay *Self, APTR Void) Self->RightMargin = 0; Self->BottomMargin = 0; - // Post a delayed CheckXWindow() message so that we can respond to changes by the window manager. + // Mapping a window may cause the window manager to resize it without sending a notification event, so check the + // window size on a delay. QueueAction(MT_GfxCheckXWindow, Self->UID); - // This really shouldn't be here, but until the management of menu focussing is fixed, we need it. + // Originally introduced as a hack to manage focusing for dropdown menus, possibly no longer required as focus should remain with the instigator. - if (!StrMatch("SystemDisplay", Self->Name)) { - XSetInputFocus(XDisplay, Self->XWindowHandle, RevertToNone, CurrentTime); - } + //if (!StrMatch("SystemDisplay", Self->Name)) { + // XSetInputFocus(XDisplay, Self->XWindowHandle, RevertToNone, CurrentTime); + //} #elif _WIN32 @@ -1861,11 +1909,10 @@ ERROR DISPLAY_Show(extDisplay *Self, APTR Void) objPointer *pointer; OBJECTID pointer_id; - if (FindObject("SystemPointer", ID_POINTER, FOF::NIL, &pointer_id) != ERR_Okay) { - if (!NewObject(ID_POINTER, NF::UNTRACKED, &pointer)) { + if (FindObject("SystemPointer", ID_POINTER, FOF::NIL, &pointer_id) != ERR::Okay) { + if (NewObject(ID_POINTER, NF::UNTRACKED, &pointer) IS ERR::Okay) { SetName(pointer, "SystemPointer"); - OBJECTID owner = Self->ownerID(); - if (GetClassID(owner) IS ID_SURFACE) pointer->setSurface(owner); + if ((Self->Owner) and (Self->Owner->Class->ClassID IS ID_SURFACE)) pointer->setSurface(Self->Owner->UID); #ifdef __ANDROID__ AConfiguration *config; @@ -1877,11 +1924,11 @@ ERROR DISPLAY_Show(extDisplay *Self, APTR Void) else log.warning("Failed to get Android Config object."); #endif - if (InitObject(pointer) != ERR_Okay) FreeResource(pointer); + if (InitObject(pointer) != ERR::Okay) FreeResource(pointer); else acShow(pointer); } } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1903,11 +1950,11 @@ NullArgs *********************************************************************************************************************/ -static ERROR DISPLAY_UpdatePalette(extDisplay *Self, struct gfxUpdatePalette *Args) +static ERR DISPLAY_UpdatePalette(extDisplay *Self, struct gfxUpdatePalette *Args) { pf::Log log; - if ((!Args) or (!Args->NewPalette)) return ERR_NullArgs; + if ((!Args) or (!Args->NewPalette)) return ERR::NullArgs; log.branch("Palette: %p, Colours: %d", Args->NewPalette, Args->NewPalette->AmtColours); @@ -1918,7 +1965,7 @@ static ERROR DISPLAY_UpdatePalette(extDisplay *Self, struct gfxUpdatePalette *Ar CopyMemory(Args->NewPalette, Self->Bitmap->Palette, sizeof(*Args->NewPalette)); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1927,7 +1974,7 @@ static ERROR DISPLAY_UpdatePalette(extDisplay *Self, struct gfxUpdatePalette *Ar WaitVBL: Waits for a vertical blank. This method waits for the strobe to reach the vertical blank area at the bottom of the display. Not all graphics -hardware will support this method. If this is the case, WaitVBL() will return immediately with ERR_NoSupport. +hardware will support this method. If this is the case, WaitVBL() will return immediately with ERR::NoSupport. -ERRORS- Okay @@ -1935,9 +1982,9 @@ NoSupport *********************************************************************************************************************/ -ERROR DISPLAY_WaitVBL(extDisplay *Self, APTR Void) +ERR DISPLAY_WaitVBL(extDisplay *Self, APTR Void) { - return ERR_NoSupport; + return ERR::NoSupport; } /********************************************************************************************************************* @@ -1978,10 +2025,10 @@ not available from the driver, a NULL pointer is returned. *********************************************************************************************************************/ -static ERROR GET_CertificationDate(extDisplay *Self, STRING *Value) +static ERR GET_CertificationDate(extDisplay *Self, STRING *Value) { *Value = Self->CertificationDate; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1993,10 +2040,10 @@ is returned. *********************************************************************************************************************/ -static ERROR GET_Chipset(extDisplay *Self, STRING *Value) +static ERR GET_Chipset(extDisplay *Self, STRING *Value) { *Value = Self->Chipset; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2014,11 +2061,11 @@ Reading this field always succeeds. *********************************************************************************************************************/ -ERROR GET_HDensity(extDisplay *Self, LONG *Value) +ERR GET_HDensity(extDisplay *Self, LONG *Value) { if (Self->HDensity) { *Value = Self->HDensity; - return ERR_Okay; + return ERR::Okay; } #ifdef __ANDROID__ @@ -2030,16 +2077,16 @@ ERROR GET_HDensity(extDisplay *Self, LONG *Value) // If the user has overridden the DPI with a preferred value, we have to use it. OBJECTID style_id; - if (!FindObject("glStyle", ID_XML, FOF::NIL, &style_id)) { + if (FindObject("glStyle", ID_XML, FOF::NIL, &style_id) IS ERR::Okay) { pf::ScopedObjectLock style(style_id, 3000); if (style.granted()) { char strdpi[32]; - if (!acGetVar(style.obj, "/interface/@dpi", strdpi, sizeof(strdpi))) { + if (acGetVar(style.obj, "/interface/@dpi", strdpi, sizeof(strdpi)) IS ERR::Okay) { *Value = StrToInt(strdpi); Self->HDensity = *Value; // Store for future use. if (!Self->VDensity) Self->VDensity = Self->HDensity; } - if (*Value >= 96) return ERR_Okay; + if (*Value >= 96) return ERR::Okay; } } @@ -2059,13 +2106,13 @@ ERROR GET_HDensity(extDisplay *Self, LONG *Value) #endif *Value = Self->HDensity; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_HDensity(extDisplay *Self, LONG Value) +static ERR SET_HDensity(extDisplay *Self, LONG Value) { Self->HDensity = Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2084,11 +2131,11 @@ Reading this field always succeeds. *********************************************************************************************************************/ -ERROR GET_VDensity(extDisplay *Self, LONG *Value) +ERR GET_VDensity(extDisplay *Self, LONG *Value) { if (Self->VDensity) { *Value = Self->VDensity; - return ERR_Okay; + return ERR::Okay; } #ifdef __ANDROID__ @@ -2100,16 +2147,16 @@ ERROR GET_VDensity(extDisplay *Self, LONG *Value) // If the user has overridden the DPI with a preferred value, we have to use it. OBJECTID style_id; - if (!FindObject("glStyle", ID_XML, FOF::NIL, &style_id)) { + if (FindObject("glStyle", ID_XML, FOF::NIL, &style_id) IS ERR::Okay) { pf::ScopedObjectLock style(style_id, 3000); if (style.granted()) { char strdpi[32]; - if (!acGetVar(style.obj, "/interface/@dpi", strdpi, sizeof(strdpi))) { + if (acGetVar(style.obj, "/interface/@dpi", strdpi, sizeof(strdpi)) IS ERR::Okay) { *Value = StrToInt(strdpi); Self->VDensity = *Value; if (!Self->HDensity) Self->HDensity = Self->VDensity; } - if (*Value >= 96) return ERR_Okay; + if (*Value >= 96) return ERR::Okay; } } @@ -2129,13 +2176,13 @@ ERROR GET_VDensity(extDisplay *Self, LONG *Value) #endif *Value = Self->VDensity; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_VDensity(extDisplay *Self, LONG Value) +static ERR SET_VDensity(extDisplay *Self, LONG Value) { Self->VDensity = Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2148,11 +2195,11 @@ information is not detectable, a NULL pointer is returned. *********************************************************************************************************************/ -static ERROR GET_Display(extDisplay *Self, CSTRING *Value) +static ERR GET_Display(extDisplay *Self, CSTRING *Value) { if (Self->Display[0]) *Value = Self->Display; else *Value = NULL; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2165,11 +2212,11 @@ information is not detectable, a NULL pointer is returned. *********************************************************************************************************************/ -static ERROR GET_DisplayManufacturer(extDisplay *Self, CSTRING *Value) +static ERR GET_DisplayManufacturer(extDisplay *Self, CSTRING *Value) { if (Self->DisplayManufacturer[0]) *Value = Self->DisplayManufacturer; else *Value = NULL; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2188,11 +2235,11 @@ available, a NULL pointer is returned. *********************************************************************************************************************/ -static ERROR GET_DriverCopyright(extDisplay *Self, CSTRING *Value) +static ERR GET_DriverCopyright(extDisplay *Self, CSTRING *Value) { if (Self->DriverCopyright[0]) *Value = Self->DriverCopyright; else *Value = NULL; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2205,11 +2252,11 @@ pointer is returned. *********************************************************************************************************************/ -static ERROR GET_DriverVersion(extDisplay *Self, CSTRING *Value) +static ERR GET_DriverVersion(extDisplay *Self, CSTRING *Value) { if (Self->DriverVersion[0]) *Value = Self->DriverVersion; else *Value = NULL; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2222,10 +2269,10 @@ not available, a NULL pointer is returned. *********************************************************************************************************************/ -static ERROR GET_DriverVendor(extDisplay *Self, CSTRING *Value) +static ERR GET_DriverVendor(extDisplay *Self, CSTRING *Value) { *Value = Self->DriverVendor; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2238,7 +2285,7 @@ Optional display flags can be defined here. Post-initialisation, the only flags *********************************************************************************************************************/ -static ERROR SET_Flags(extDisplay *Self, SCR Value) +static ERR SET_Flags(extDisplay *Self, SCR Value) { pf::Log log; @@ -2292,7 +2339,7 @@ static ERROR SET_Flags(extDisplay *Self, SCR Value) #elif __xwindows__ - if (glX11.Manager) return ERR_NoSupport; + if (glX11.Manager) return ERR::NoSupport; XSetWindowAttributes swa; @@ -2334,7 +2381,7 @@ static ERROR SET_Flags(extDisplay *Self, SCR Value) Self->X, Self->Y, Self->Width, Self->Height, 0, CopyFromParent, InputOutput, CopyFromParent, cwflags, &swa))) { log.warning("Failed in call to XCreateWindow()."); - return ERR_Failed; + return ERR::Failed; } STRING name; @@ -2397,7 +2444,7 @@ static ERROR SET_Flags(extDisplay *Self, SCR Value) } else Self->Flags = (Value) & (~SCR::READ_ONLY); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2412,21 +2459,21 @@ To modify the display gamma values, please refer to the #SetGamma() and #SetGamm *********************************************************************************************************************/ -static ERROR GET_Gamma(extDisplay *Self, DOUBLE **Value, LONG *Elements) +static ERR GET_Gamma(extDisplay *Self, DOUBLE **Value, LONG *Elements) { *Elements = 3; *Value = Self->Gamma; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_Gamma(extDisplay *Self, DOUBLE *Value, LONG Elements) +static ERR SET_Gamma(extDisplay *Self, DOUBLE *Value, LONG Elements) { if (Value) { if (Elements > 3) Elements = 3; WORD i; for (i=0; i < Elements; i++) Self->Gamma[i] = Value[i]; } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2442,10 +2489,10 @@ height of the window can be calculated by reading the #TopMargin and #BottomMarg *********************************************************************************************************************/ -static ERROR SET_Height(extDisplay *Self, LONG Value) +static ERR SET_Height(extDisplay *Self, LONG Value) { if (Value > 0) Self->Height = Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2459,10 +2506,10 @@ the display #Height. *********************************************************************************************************************/ -static ERROR GET_InsideHeight(extDisplay *Self, LONG *Value) +static ERR GET_InsideHeight(extDisplay *Self, LONG *Value) { *Value = Self->Bitmap->Height; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2476,10 +2523,10 @@ display #Width. *********************************************************************************************************************/ -static ERROR GET_InsideWidth(extDisplay *Self, LONG *Value) +static ERR GET_InsideWidth(extDisplay *Self, LONG *Value) { *Value = Self->Bitmap->Width; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2498,11 +2545,11 @@ information is not detectable, a NULL pointer is returned. *********************************************************************************************************************/ -static ERROR GET_Manufacturer(extDisplay *Self, STRING *Value) +static ERR GET_Manufacturer(extDisplay *Self, STRING *Value) { if (Self->Manufacturer[0]) *Value = Self->Manufacturer; else *Value = NULL; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2540,21 +2587,21 @@ be solid. High values will retain the boldness of the display, while low values ****************************************************************************/ -static ERROR GET_Opacity(extDisplay *Self, DOUBLE *Value) +static ERR GET_Opacity(extDisplay *Self, DOUBLE *Value) { *Value = Self->Opacity * 100 / 255; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_Opacity(extDisplay *Self, DOUBLE Value) +static ERR SET_Opacity(extDisplay *Self, DOUBLE Value) { #ifdef _WIN32 if (Value < 0) Self->Opacity = 0; else if (Value > 100) Self->Opacity = 255; else Self->Opacity = Value * 255 / 100; - return ERR_Okay; + return ERR::Okay; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -2567,12 +2614,12 @@ The PopOver field can be used when a display is hosted as a window. Setting the ID of another display will ensure that the host window is always in front of the other display's window (assuming both windows are visible on the desktop). -The ERR_NoSupport error code is returned if the host does not support this functionality or if the display owns the +The ERR::NoSupport error code is returned if the host does not support this functionality or if the display owns the output device. *********************************************************************************************************************/ -static ERROR SET_PopOver(extDisplay *Self, OBJECTID Value) +static ERR SET_PopOver(extDisplay *Self, OBJECTID Value) { pf::Log log; @@ -2591,31 +2638,31 @@ static ERROR SET_PopOver(extDisplay *Self, OBJECTID Value) } ReleaseObject(popover); } - else return ERR_AccessObject; + else return ERR::AccessObject; } else if (Value) { if (GetClassID(Value) IS ID_DISPLAY) { Self->PopOverID = Value; } - else return log.warning(ERR_WrongClass); + else return log.warning(ERR::WrongClass); } else Self->PopOverID = 0; - return ERR_Okay; + return ERR::Okay; #elif _WIN32 if (Value) { if (GetClassID(Value) IS ID_DISPLAY) Self->PopOverID = Value; - else return log.warning(ERR_WrongClass); + else return log.warning(ERR::WrongClass); } else Self->PopOverID = 0; - return ERR_Okay; + return ERR::Okay; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -2636,9 +2683,9 @@ The value in this field reflects the refresh rate of the currently active displa *********************************************************************************************************************/ -static ERROR SET_RefreshRate(extDisplay *Self, DOUBLE Value) +static ERR SET_RefreshRate(extDisplay *Self, DOUBLE Value) { - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2650,27 +2697,26 @@ The value in this field reflects the refresh rate of the currently active displa *********************************************************************************************************************/ -static ERROR GET_ResizeFeedback(extDisplay *Self, FUNCTION **Value) +static ERR GET_ResizeFeedback(extDisplay *Self, FUNCTION **Value) { - if (Self->ResizeFeedback.Type != CALL_NONE) { + if (Self->ResizeFeedback.defined()) { *Value = &Self->ResizeFeedback; - return ERR_Okay; + return ERR::Okay; } - else return ERR_FieldNotSet; + else return ERR::FieldNotSet; } -static ERROR SET_ResizeFeedback(extDisplay *Self, FUNCTION *Value) +static ERR SET_ResizeFeedback(extDisplay *Self, FUNCTION *Value) { if (Value) { - if (Self->ResizeFeedback.Type IS CALL_SCRIPT) UnsubscribeAction(Self->ResizeFeedback.Script.Script, AC_Free); + if (Self->ResizeFeedback.isScript()) UnsubscribeAction(Self->ResizeFeedback.Script.Script, AC_Free); Self->ResizeFeedback = *Value; - if (Self->ResizeFeedback.Type IS CALL_SCRIPT) { - auto callback = make_function_stdc(notify_resize_free); - SubscribeAction(Self->ResizeFeedback.Script.Script, AC_Free, &callback); + if (Self->ResizeFeedback.isScript()) { + SubscribeAction(Self->ResizeFeedback.Script.Script, AC_Free, FUNCTION(notify_resize_free)); } } - else Self->ResizeFeedback.Type = CALL_NONE; - return ERR_Okay; + else Self->ResizeFeedback.clear(); + return ERR::Okay; } /********************************************************************************************************************* @@ -2689,11 +2735,11 @@ TotalResolutions: The total number of resolutions supported by the display. *********************************************************************************************************************/ -static ERROR GET_TotalResolutions(extDisplay *Self, LONG *Value) +static ERR GET_TotalResolutions(extDisplay *Self, LONG *Value) { if (Self->Resolutions.empty()) get_resolutions(Self); *Value = Self->Resolutions.size(); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2709,16 +2755,16 @@ width of the window can be calculated by reading the #LeftMargin and #RightMargi *********************************************************************************************************************/ -static ERROR SET_Width(extDisplay *Self, LONG Value) +static ERR SET_Width(extDisplay *Self, LONG Value) { if (Value > 0) { if (Self->initialised()) { acResize(Self, Value, Self->Height, 0); } else Self->Width = Value; - return ERR_Okay; + return ERR::Okay; } - else return ERR_OutOfRange; + else return ERR::OutOfRange; } /********************************************************************************************************************* @@ -2734,15 +2780,15 @@ window that already exists. *********************************************************************************************************************/ -static ERROR GET_WindowHandle(extDisplay *Self, APTR *Value) +static ERR GET_WindowHandle(extDisplay *Self, APTR *Value) { *Value = Self->WindowHandle; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_WindowHandle(extDisplay *Self, APTR Value) +static ERR SET_WindowHandle(extDisplay *Self, APTR Value) { - if (Self->initialised()) return ERR_Failed; + if (Self->initialised()) return ERR::Failed; if (Value) { Self->WindowHandle = Value; @@ -2752,7 +2798,7 @@ static ERROR SET_WindowHandle(extDisplay *Self, APTR Value) #endif } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2765,39 +2811,39 @@ Title: Sets the window title (hosted environments only). static STRING glWindowTitle = NULL; #endif -static ERROR GET_Title(extDisplay *Self, CSTRING *Value) +static ERR GET_Title(extDisplay *Self, CSTRING *Value) { #ifdef __xwindows__ - return ERR_NoSupport; + return ERR::NoSupport; #elif _WIN32 char buffer[128]; STRING str; buffer[0] = 0; winGetWindowTitle(Self->WindowHandle, buffer, sizeof(buffer)); - if (!AllocMemory(StrLength(buffer) + 1, MEM::STRING|MEM::UNTRACKED, &str)) { + if (AllocMemory(StrLength(buffer) + 1, MEM::STRING|MEM::UNTRACKED, &str) IS ERR::Okay) { StrCopy(buffer, str); if (glWindowTitle) FreeResource(glWindowTitle); glWindowTitle = str; *Value = glWindowTitle; - return ERR_Okay; + return ERR::Okay; } - else return ERR_AllocMemory; + else return ERR::AllocMemory; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } -static ERROR SET_Title(extDisplay *Self, CSTRING Value) +static ERR SET_Title(extDisplay *Self, CSTRING Value) { #ifdef __xwindows__ XStoreName(XDisplay, Self->XWindowHandle, Value); - return ERR_Okay; + return ERR::Okay; #elif _WIN32 winSetWindowTitle(Self->WindowHandle, Value); - return ERR_Okay; + return ERR::Okay; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -2816,11 +2862,11 @@ To adjust the position of the display, use the #MoveToPoint() action rather than *********************************************************************************************************************/ -static ERROR SET_X(extDisplay *Self, LONG Value) +static ERR SET_X(extDisplay *Self, LONG Value) { if (!(Self->initialised())) { Self->X = Value; - return ERR_Okay; + return ERR::Okay; } else return acMoveToPoint(Self, Value, 0, 0, MTF::X); } @@ -2840,11 +2886,11 @@ To adjust the position of the display, use the #MoveToPoint() action rather than -END- *********************************************************************************************************************/ -static ERROR SET_Y(extDisplay *Self, LONG Value) +static ERR SET_Y(extDisplay *Self, LONG Value) { if (!(Self->initialised())) { Self->Y = Value; - return ERR_Okay; + return ERR::Okay; } else return acMoveToPoint(Self, 0, Value, 0, MTF::Y); } @@ -2936,7 +2982,7 @@ CSTRING dpms_name(DPMS Index) //******************************************************************************************************************** -ERROR create_display_class(void) +ERR create_display_class(void) { clDisplay = objMetaClass::create::global( fl::ClassVersion(VER_DISPLAY), @@ -2949,5 +2995,5 @@ ERROR create_display_class(void) fl::Size(sizeof(extDisplay)), fl::Path(MOD_PATH)); - return clDisplay ? ERR_Okay : ERR_AddClass; + return clDisplay ? ERR::Okay : ERR::AddClass; } diff --git a/src/display/class_pointer.cpp b/src/display/class_pointer.cpp index f4be1995b..f28269d1f 100644 --- a/src/display/class_pointer.cpp +++ b/src/display/class_pointer.cpp @@ -20,22 +20,22 @@ used for all interactions with this service. using namespace display; #endif -static ERROR GET_ButtonOrder(extPointer *, CSTRING *); -static ERROR GET_ButtonState(extPointer *, LONG *); +static ERR GET_ButtonOrder(extPointer *, CSTRING *); +static ERR GET_ButtonState(extPointer *, LONG *); -static ERROR SET_ButtonOrder(extPointer *, CSTRING); -static ERROR SET_MaxSpeed(extPointer *, LONG); -static ERROR PTR_SET_X(extPointer *, DOUBLE); -static ERROR PTR_SET_Y(extPointer *, DOUBLE); +static ERR SET_ButtonOrder(extPointer *, CSTRING); +static ERR SET_MaxSpeed(extPointer *, LONG); +static ERR PTR_SET_X(extPointer *, DOUBLE); +static ERR PTR_SET_Y(extPointer *, DOUBLE); #ifdef _WIN32 -static ERROR PTR_SetWinCursor(extPointer *, struct ptrSetWinCursor *); +static ERR PTR_SetWinCursor(extPointer *, struct ptrSetWinCursor *); static FunctionField mthSetWinCursor[] = { { "Cursor", FD_LONG }, { NULL, 0 } }; #endif #ifdef __xwindows__ -static ERROR PTR_GrabX11Pointer(extPointer *, struct ptrGrabX11Pointer *); -static ERROR PTR_UngrabX11Pointer(extPointer *, APTR); +static ERR PTR_GrabX11Pointer(extPointer *, struct ptrGrabX11Pointer *); +static ERR PTR_UngrabX11Pointer(extPointer *, APTR); static FunctionField mthGrabX11Pointer[] = { { "Surface", FD_LONG }, { NULL, 0 } }; #endif @@ -43,7 +43,7 @@ static LONG glDefaultSpeed = 160; static DOUBLE glDefaultAcceleration = 0.8; static TIMER glRepeatTimer = 0; -static ERROR repeat_timer(extPointer *, LARGE, LARGE); +static ERR repeat_timer(extPointer *, LARGE, LARGE); static void set_pointer_defaults(extPointer *); static LONG examine_chain(extPointer *, LONG, SURFACELIST &, LONG); static bool get_over_object(extPointer *); @@ -75,11 +75,11 @@ inline void add_input(CSTRING Debug, InputEvent &input, JTYPE Flags, OBJECTID Re //******************************************************************************************************************** #ifdef _WIN32 -static ERROR PTR_SetWinCursor(extPointer *Self, struct ptrSetWinCursor *Args) +static ERR PTR_SetWinCursor(extPointer *Self, struct ptrSetWinCursor *Args) { winSetCursor(GetWinCursor(Args->Cursor)); Self->CursorID = Args->Cursor; - return ERR_Okay; + return ERR::Okay; } #endif @@ -87,7 +87,7 @@ static ERROR PTR_SetWinCursor(extPointer *Self, struct ptrSetWinCursor *Args) // Private action used to grab the window cursor under X11. Can only be executed by the task that owns the pointer. #ifdef __xwindows__ -static ERROR PTR_GrabX11Pointer(extPointer *Self, struct ptrGrabX11Pointer *Args) +static ERR PTR_GrabX11Pointer(extPointer *Self, struct ptrGrabX11Pointer *Args) { APTR xwin; OBJECTPTR surface; @@ -99,13 +99,13 @@ static ERROR PTR_GrabX11Pointer(extPointer *Self, struct ptrGrabX11Pointer *Args if (xwin) XGrabPointer(XDisplay, (Window)xwin, True, 0, GrabModeAsync, GrabModeAsync, (Window)xwin, None, CurrentTime); } - return ERR_Okay; + return ERR::Okay; } -static ERROR PTR_UngrabX11Pointer(extPointer *Self, APTR Void) +static ERR PTR_UngrabX11Pointer(extPointer *Self, APTR Void) { XUngrabPointer(XDisplay, CurrentTime); - return ERR_Okay; + return ERR::Okay; } #endif @@ -124,22 +124,22 @@ flag for that button. *********************************************************************************************************************/ -static ERROR PTR_DataFeed(extPointer *Self, struct acDataFeed *Args) +static ERR PTR_DataFeed(extPointer *Self, struct acDataFeed *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); if (Args->Datatype IS DATA::DEVICE_INPUT) { if (auto input = (struct dcDeviceInput *)Args->Buffer) { - for (LONG i=0; i < ARRAYSIZE(Self->Buttons); i++) { - if ((Self->Buttons[i].LastClicked) and (CheckObjectExists(Self->Buttons[i].LastClicked) != ERR_Okay)) Self->Buttons[i].LastClicked = 0; + for (LONG i=0; i < std::ssize(Self->Buttons); i++) { + if ((Self->Buttons[i].LastClicked) and (CheckObjectExists(Self->Buttons[i].LastClicked) != ERR::Okay)) Self->Buttons[i].LastClicked = 0; } for (LONG i=sizeof(struct dcDeviceInput); i <= Args->Size; i+=sizeof(struct dcDeviceInput), input++) { if ((LONG(input->Type) < 1) or (LONG(input->Type) >= LONG(JET::END))) continue; - input->Flags = glInputType[LONG(input->Type)].Flags; + input->Flags |= glInputType[LONG(input->Type)].Flags; //log.traceBranch("Incoming Input: %s, Value: %.2f, Flags: $%.8x, Time: %" PF64, (input->Type < JET::END) ? glInputNames[input->Type] : (STRING)"", input->Value, input->Flags, input->Timestamp); @@ -149,9 +149,9 @@ static ERROR PTR_DataFeed(extPointer *Self, struct acDataFeed *Args) } } } - else return log.warning(ERR_WrongType); + else return log.warning(ERR::WrongType); - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -164,7 +164,7 @@ static void process_ptr_button(extPointer *Self, struct dcDeviceInput *Input) LONG buttonflag, bi; ClearMemory(&userinput, sizeof(userinput)); - userinput.Value = Input->Value; + userinput.Value = Input->Values[0]; userinput.Timestamp = Input->Timestamp; userinput.Type = Input->Type; userinput.Flags = Input->Flags; @@ -172,7 +172,7 @@ static void process_ptr_button(extPointer *Self, struct dcDeviceInput *Input) if (!userinput.Timestamp) userinput.Timestamp = PreciseTime(); - auto uiflags = JTYPE::NIL; + auto uiflags = userinput.Flags; if ((userinput.Type >= JET::BUTTON_1) and (userinput.Type <= JET::BUTTON_10)) { bi = LONG(userinput.Type) - LONG(JET::BUTTON_1); @@ -200,7 +200,7 @@ static void process_ptr_button(extPointer *Self, struct dcDeviceInput *Input) if (Self->Buttons[bi].LastClicked) { LONG absx, absy; - if (!get_surface_abs(Self->Buttons[bi].LastClicked, &absx, &absy, 0, 0)) { + if (get_surface_abs(Self->Buttons[bi].LastClicked, &absx, &absy, 0, 0) IS ERR::Okay) { uiflags |= Self->DragSourceID ? JTYPE::DRAG_ITEM : JTYPE::NIL; if ((std::abs(Self->X - Self->LastReleaseX) > Self->ClickSlop) or @@ -227,16 +227,14 @@ static void process_ptr_button(extPointer *Self, struct dcDeviceInput *Input) // surface, or if no modal surface is defined. auto modal_id = gfxGetModalSurface(); - if (modal_id) { if (modal_id IS Self->OverObjectID) { + // If the pointer is interacting with the modal surface, modality is irrelevant. modal_id = 0; } - else { - // Check if the OverObject is one of the children of modal_id. - - ERROR error = gfxCheckIfChild(modal_id, Self->OverObjectID); - if ((error IS ERR_True) or (error IS ERR_LimitedSuccess)) modal_id = 0; + else { // Check if the OverObject is one of the children of modal_id. + ERR error = gfxCheckIfChild(modal_id, Self->OverObjectID); + if ((error IS ERR::True) or (error IS ERR::LimitedSuccess)) modal_id = 0; } } @@ -277,10 +275,7 @@ static void process_ptr_button(extPointer *Self, struct dcDeviceInput *Input) // If a modal surface is active for the current process, the button press is reported to the modal surface only. - if ((modal_id) and (modal_id != Self->OverObjectID)) { - target = modal_id; - } - else target = Self->OverObjectID; + target = modal_id ? modal_id : Self->OverObjectID; QueueAction(AC_Focus, target); @@ -288,8 +283,7 @@ static void process_ptr_button(extPointer *Self, struct dcDeviceInput *Input) Self->X, Self->Y, Self->OverX, Self->OverY); //} - auto call = make_function_stdc(repeat_timer); - SubscribeTimer(0.02, &call, &glRepeatTimer); // Use a timer subscription so that repeat button clicks can be supported (the interval indicates the rate of the repeat) + SubscribeTimer(0.02, FUNCTION(repeat_timer), &glRepeatTimer); // Use a timer subscription so that repeat button clicks can be supported (the interval indicates the rate of the repeat) } if ((Self->DragSourceID) and (!Self->Buttons[bi].LastClicked)) { @@ -301,7 +295,7 @@ static void process_ptr_button(extPointer *Self, struct dcDeviceInput *Input) } if (!modal_id) { - pf::ScopedObjectLock<> src(Self->DragSourceID); + pf::ScopedObjectLock src(Self->DragSourceID); if (src.granted()) { acDragDrop(Self->OverObjectID, *src, Self->DragItem, Self->DragData); } @@ -320,7 +314,7 @@ static void process_ptr_wheel(extPointer *Self, struct dcDeviceInput *Input) msg.Type = JET::WHEEL; msg.Flags = JTYPE::ANALOG|JTYPE::EXT_MOVEMENT | Input->Flags; msg.Mask = JTYPE::EXT_MOVEMENT; - msg.Value = Input->Value; + msg.Value = Input->Values[0]; msg.Timestamp = Input->Timestamp; msg.DeviceID = Input->DeviceID; msg.RecipientID = Self->OverObjectID; @@ -338,7 +332,7 @@ static void process_ptr_wheel(extPointer *Self, struct dcDeviceInput *Input) // Convert wheel mouse usage into scroll messages DOUBLE scrollrate = 0; - DOUBLE wheel = Input->Value; + DOUBLE wheel = Input->Values[0]; if (wheel > 0) { for (LONG i=1; i <= wheel; i++) scrollrate += Self->WheelSpeed * i; } @@ -349,7 +343,7 @@ static void process_ptr_wheel(extPointer *Self, struct dcDeviceInput *Input) struct acScroll scroll = { .DeltaX = 0, - .DeltaY = scrollrate / 100, //(wheel * Self->WheelSpeed) / 100 + .DeltaY = scrollrate * 0.01, //(wheel * Self->WheelSpeed) / 100 .DeltaZ = 0 }; ActionMsg(AC_Scroll, Self->OverObjectID, &scroll); @@ -363,7 +357,8 @@ static void process_ptr_movement(extPointer *Self, struct dcDeviceInput *Input) InputEvent userinput; ClearMemory(&userinput, sizeof(userinput)); - userinput.Value = Input->Value; + userinput.X = Input->Values[0]; + userinput.Y = Input->Values[1]; userinput.Timestamp = Input->Timestamp; userinput.Type = Input->Type; userinput.Flags = Input->Flags; @@ -373,21 +368,24 @@ static void process_ptr_movement(extPointer *Self, struct dcDeviceInput *Input) // All X/Y movement passed through the pointer object must be expressed in absolute coordinates. - if ((userinput.Type IS JET::DIGITAL_X) or (userinput.Type IS JET::ANALOG_X)) { - userinput.Type = JET::ABS_X; - userinput.Value += Self->X; - } - else if ((userinput.Type IS JET::DIGITAL_Y) or (userinput.Type IS JET::ANALOG_Y)) { - userinput.Type = JET::ABS_Y; - userinput.Value += Self->Y; + if ((userinput.Type IS JET::DIGITAL_XY) or (userinput.Type IS JET::ANALOG_XY)) { + userinput.Type = JET::ABS_XY; + userinput.X += Self->X; + userinput.Y += Self->Y; } bool moved = false, underlying_change = false; DOUBLE current_x = Self->X; DOUBLE current_y = Self->Y; switch (userinput.Type) { - case JET::ABS_X: current_x = userinput.Value; if (current_x != Self->X) moved = true; break; - case JET::ABS_Y: current_y = userinput.Value; if (current_y != Self->Y) moved = true; break; + case JET::ABS_XY: + current_x = userinput.X; + if (current_x != Self->X) moved = true; + + current_y = userinput.Y; + if (current_y != Self->Y) moved = true; + break; + default: break; } @@ -407,7 +405,7 @@ static void process_ptr_movement(extPointer *Self, struct dcDeviceInput *Input) // the pointer is locked. if (Self->AnchorID) { - if (CheckObjectExists(Self->AnchorID) != ERR_Okay) { + if (CheckObjectExists(Self->AnchorID) != ERR::Okay) { Self->AnchorID = 0; } } @@ -427,7 +425,7 @@ static void process_ptr_movement(extPointer *Self, struct dcDeviceInput *Input) } else { struct acMoveToPoint moveto = { Self->X, Self->Y, 0, MTF::X|MTF::Y }; - NotifySubscribers(Self, AC_MoveToPoint, &moveto, ERR_Okay); + NotifySubscribers(Self, AC_MoveToPoint, &moveto, ERR::Okay); // Recalculate the OverObject due to cursor movement @@ -446,7 +444,7 @@ static void process_ptr_movement(extPointer *Self, struct dcDeviceInput *Input) DOUBLE sy = Self->Y + DRAG_YOFFSET; if (Self->DragParent) { LONG absx, absy; - if (!gfxGetSurfaceCoords(Self->DragParent, NULL, NULL, &absx, &absy, NULL, NULL)) { + if (gfxGetSurfaceCoords(Self->DragParent, NULL, NULL, &absx, &absy, NULL, NULL) IS ERR::Okay) { sx -= absx; sy -= absy; } @@ -456,7 +454,7 @@ static void process_ptr_movement(extPointer *Self, struct dcDeviceInput *Input) } LONG absx, absy; - if (!get_surface_abs(Self->Buttons[0].LastClicked, &absx, &absy, 0, 0)) { + if (get_surface_abs(Self->Buttons[0].LastClicked, &absx, &absy, 0, 0) IS ERR::Okay) { auto uiflags = Self->DragSourceID ? JTYPE::DRAG_ITEM : JTYPE::NIL; // Send the movement message to the last clicked object @@ -502,14 +500,15 @@ static void process_ptr_movement(extPointer *Self, struct dcDeviceInput *Input) // If a release object has been specified and the cursor is not positioned over it, call the RestoreCursor method. - if ((Self->CursorReleaseID) and (Self->CursorReleaseID != Self->OverObjectID)) { + if ((userinput.Flags & JTYPE::SECONDARY) != JTYPE::NIL); // No cursor manipulation when it's in a Win32 area + else if ((Self->CursorReleaseID) and (Self->CursorReleaseID != Self->OverObjectID)) { gfxRestoreCursor(PTC::DEFAULT, 0); } } //******************************************************************************************************************** -static ERROR PTR_Free(extPointer *Self, APTR Void) +static ERR PTR_Free(extPointer *Self, APTR Void) { acHide(Self); @@ -522,7 +521,7 @@ static ERROR PTR_Free(extPointer *Self, APTR Void) ReleaseObject(object); } */ - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -531,7 +530,7 @@ Hide: Hides the pointer from the display. -END- *********************************************************************************************************************/ -static ERROR PTR_Hide(extPointer *Self, APTR Void) +static ERR PTR_Hide(extPointer *Self, APTR Void) { pf::Log log; @@ -542,7 +541,7 @@ static ERROR PTR_Hide(extPointer *Self, APTR Void) APTR xwin; OBJECTPTR surface; - if (AccessObject(Self->SurfaceID, 5000, &surface) IS ERR_Okay) { + if (AccessObject(Self->SurfaceID, 5000, &surface) IS ERR::Okay) { surface->getPtr(FID_WindowHandle, &xwin); XDefineCursor(XDisplay, (Window)xwin, GetX11Cursor(Self->CursorID)); ReleaseObject(surface); @@ -553,12 +552,12 @@ static ERROR PTR_Hide(extPointer *Self, APTR Void) #endif Self->Flags &= ~PF::VISIBLE; - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR PTR_Init(extPointer *Self, APTR Void) +static ERR PTR_Init(extPointer *Self, APTR Void) { pf::Log log; @@ -585,12 +584,12 @@ static ERROR PTR_Init(extPointer *Self, APTR Void) fl::BytesPerPixel(4), fl::Flags(BMF::ALPHA_CHANNEL)))) { } - else log.warning(ERR_NewObject); + else log.warning(ERR::NewObject); if (Self->MaxSpeed < 1) Self->MaxSpeed = 10; if (Self->Speed < 1) Self->Speed = 150; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -604,12 +603,12 @@ change). *********************************************************************************************************************/ -static ERROR PTR_Move(extPointer *Self, struct acMove *Args) +static ERR PTR_Move(extPointer *Self, struct acMove *Args) { pf::Log log; - if (!Args) return log.warning(ERR_Args); - if ((!Args->DeltaX) and (!Args->DeltaY)) return ERR_Okay; + if (!Args) return log.warning(ERR::Args); + if ((!Args->DeltaX) and (!Args->DeltaY)) return ERR::Okay; return acMoveToPoint(Self, Self->X + Args->DeltaX, Self->Y + Args->DeltaY, 0, MTF::X|MTF::Y); } @@ -627,15 +626,15 @@ The client can subscribe to this action to listen for changes to the cursor's po *********************************************************************************************************************/ -static ERROR PTR_MoveToPoint(extPointer *Self, struct acMoveToPoint *Args) +static ERR PTR_MoveToPoint(extPointer *Self, struct acMoveToPoint *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs)|ERF_Notified; + if (!Args) return log.warning(ERR::NullArgs)|ERR::Notified; /* if ((!(Args->Flags & MTF::X)) or ((Args->Flags & MTF::X) and (Self->X IS Args->X))) { if ((!(Args->Flags & MTF::Y)) or ((Args->Flags & MTF::Y) and (Self->Y IS Args->Y))) { - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } } */ @@ -660,7 +659,7 @@ static ERROR PTR_MoveToPoint(extPointer *Self, struct acMoveToPoint *Args) #elif _WIN32 OBJECTPTR surface; - if (!AccessObject(Self->SurfaceID, 3000, &surface)) { + if (AccessObject(Self->SurfaceID, 3000, &surface) IS ERR::Okay) { if ((Args->Flags & MTF::X) != MTF::NIL) Self->X = Args->X; if ((Args->Flags & MTF::Y) != MTF::NIL) Self->Y = Args->Y; if (Self->X < 0) Self->X = 0; @@ -680,19 +679,19 @@ static ERROR PTR_MoveToPoint(extPointer *Self, struct acMoveToPoint *Args) // Customised notification (ensures that both X and Y coordinates are reported). struct acMoveToPoint moveto = { Self->X, Self->Y, 0, MTF::X|MTF::Y }; - NotifySubscribers(Self, AC_MoveToPoint, &moveto, ERR_Okay); + NotifySubscribers(Self, AC_MoveToPoint, &moveto, ERR::Okay); - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR(ERR::Notified); } //******************************************************************************************************************** -static ERROR PTR_NewObject(extPointer *Self, APTR Void) +static ERR PTR_NewObject(extPointer *Self, APTR Void) { Self->CursorID = PTC::DEFAULT; Self->ClickSlop = 2; set_pointer_defaults(Self); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -701,13 +700,13 @@ Refresh: Refreshes the pointer's cursor status. -END- *********************************************************************************************************************/ -static ERROR PTR_Refresh(extPointer *Self, APTR Void) +static ERR PTR_Refresh(extPointer *Self, APTR Void) { // Calling OverObject will refresh the cursor image from the underlying surface object. Incidentally, the point of // all this is to satisfy the Surface class' need to have the pointer refreshed if a surface's cursor ID is changed. get_over_object(Self); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -716,14 +715,14 @@ Reset: Resets the pointer settings back to the default. -END- *********************************************************************************************************************/ -static ERROR PTR_Reset(extPointer *Self, APTR Void) +static ERR PTR_Reset(extPointer *Self, APTR Void) { Self->Speed = 150; Self->Acceleration = 0.50; Self->DoubleClick = 0.30; Self->MaxSpeed = 100; Self->WheelSpeed = DEFAULT_WHEELSPEED; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -732,13 +731,13 @@ SaveToObject: Saves the current pointer settings to another object. -END- *********************************************************************************************************************/ -static ERROR PTR_SaveToObject(extPointer *Self, struct acSaveToObject *Args) +static ERR PTR_SaveToObject(extPointer *Self, struct acSaveToObject *Args) { pf::Log log; - if ((!Args) or (!Args->Dest)) return log.warning(ERR_NullArgs); + if ((!Args) or (!Args->Dest)) return log.warning(ERR::NullArgs); - objConfig::create config = { }; + auto config = objConfig::create { }; if (config.ok()) { config->write("POINTER", "Speed", Self->Speed); config->write("POINTER", "Acceleration", Self->Acceleration); @@ -749,7 +748,7 @@ static ERROR PTR_SaveToObject(extPointer *Self, struct acSaveToObject *Args) config->saveToObject(Args->Dest); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -758,7 +757,7 @@ Show: Shows the pointer if it is not already on the display. -END- *********************************************************************************************************************/ -static ERROR PTR_Show(extPointer *Self, APTR Void) +static ERR PTR_Show(extPointer *Self, APTR Void) { pf::Log log; @@ -781,7 +780,7 @@ static ERROR PTR_Show(extPointer *Self, APTR Void) #endif Self->Flags |= PF::VISIBLE; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -824,19 +823,19 @@ Changes to this field will have an immediate impact on the pointing device's beh *********************************************************************************************************************/ -static ERROR GET_ButtonOrder(extPointer *Self, CSTRING *Value) +static ERR GET_ButtonOrder(extPointer *Self, CSTRING *Value) { *Value = Self->ButtonOrder; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_ButtonOrder(extPointer *Self, CSTRING Value) +static ERR SET_ButtonOrder(extPointer *Self, CSTRING Value) { pf::Log log; log.msg("%s", Value); - if (!Value) return ERR_Okay; + if (!Value) return ERR::Okay; // Assign the buttons @@ -872,7 +871,7 @@ static ERROR SET_ButtonOrder(extPointer *Self, CSTRING Value) Self->ButtonOrderFlags[i] = 1<Buttons); i++) { + for (i=0; i < std::ssize(Self->Buttons); i++) { if (Self->Buttons[i].LastClicked) state |= 1<MaxSpeed = 2; else if (Value > 200) Self->MaxSpeed = 200; else Self->MaxSpeed = Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1023,11 +1022,11 @@ X: The horizontal position of the pointer within its parent display. *********************************************************************************************************************/ -static ERROR PTR_SET_X(extPointer *Self, DOUBLE Value) +static ERR PTR_SET_X(extPointer *Self, DOUBLE Value) { if (Self->initialised()) acMoveToPoint(Self, Value, 0, 0, MTF::X); else Self->X = Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1038,11 +1037,11 @@ Y: The vertical position of the pointer within its parent display. *********************************************************************************************************************/ -static ERROR PTR_SET_Y(extPointer *Self, DOUBLE Value) +static ERR PTR_SET_Y(extPointer *Self, DOUBLE Value) { if (Self->initialised()) acMoveToPoint(Self, 0, Value, 0, MTF::Y); else Self->Y = Value; - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -1051,22 +1050,22 @@ static void set_pointer_defaults(extPointer *Self) { DOUBLE speed = glDefaultSpeed; DOUBLE acceleration = glDefaultAcceleration; - LONG maxspeed = 100; + LONG maxspeed = 100; DOUBLE wheelspeed = DEFAULT_WHEELSPEED; DOUBLE doubleclick = 0.36; CSTRING buttonorder = "123456789ABCDEF"; - objConfig::create config = { fl::Path("user:config/pointer.cfg") }; + auto config = objConfig::create { fl::Path("user:config/pointer.cfg") }; if (config.ok()) { DOUBLE dbl; CSTRING str; - if (!cfgRead(*config, "POINTER", "Speed", &dbl)) speed = dbl; - if (!cfgRead(*config, "POINTER", "Acceleration", &dbl)) acceleration = dbl; - if (!cfgRead(*config, "POINTER", "MaxSpeed", &dbl)) maxspeed = dbl; - if (!cfgRead(*config, "POINTER", "WheelSpeed", &dbl)) wheelspeed = dbl; - if (!cfgRead(*config, "POINTER", "DoubleClick", &dbl)) doubleclick = dbl; - if (!cfgReadValue(*config, "POINTER", "ButtonOrder", &str)) buttonorder = str; + if (cfgRead(*config, "POINTER", "Speed", &dbl) IS ERR::Okay) speed = dbl; + if (cfgRead(*config, "POINTER", "Acceleration", &dbl) IS ERR::Okay) acceleration = dbl; + if (cfgRead(*config, "POINTER", "MaxSpeed", &dbl) IS ERR::Okay) maxspeed = dbl; + if (cfgRead(*config, "POINTER", "WheelSpeed", &dbl) IS ERR::Okay) wheelspeed = dbl; + if (cfgRead(*config, "POINTER", "DoubleClick", &dbl) IS ERR::Okay) doubleclick = dbl; + if (cfgReadValue(*config, "POINTER", "ButtonOrder", &str) IS ERR::Okay) buttonorder = str; } if (doubleclick < 0.2) doubleclick = 0.2; @@ -1086,7 +1085,7 @@ static bool get_over_object(extPointer *Self) { pf::Log log(__FUNCTION__); - if ((Self->SurfaceID) and (CheckObjectExists(Self->SurfaceID) != ERR_Okay)) Self->SurfaceID = 0; + if ((Self->SurfaceID) and (CheckObjectExists(Self->SurfaceID) != ERR::Okay)) Self->SurfaceID = 0; bool changed = false; @@ -1094,12 +1093,14 @@ static bool get_over_object(extPointer *Self) const std::lock_guard lock(glSurfaceLock); - LONG index; + if (glSurfaces.empty()) return false; + + size_t index; if (!Self->SurfaceID) { Self->SurfaceID = glSurfaces[0].SurfaceID; index = 0; } - else for (index=0; (index < LONG(glSurfaces.size())) and (glSurfaces[index].SurfaceID != Self->SurfaceID); index++); + else for (index=0; (index < glSurfaces.size()) and (glSurfaces[index].SurfaceID != Self->SurfaceID); index++); auto i = examine_chain(Self, index, glSurfaces, glSurfaces.size()); @@ -1126,15 +1127,15 @@ static bool get_over_object(extPointer *Self) .X = Self->X - li_left, .Y = Self->Y - li_top, .DeviceID = Self->UID, - .Type = JET::LEFT_SURFACE, - .Flags = JTYPE::FEEDBACK, - .Mask = JTYPE::FEEDBACK + .Type = JET::CROSSED_OUT, + .Flags = JTYPE::CROSSING, + .Mask = JTYPE::CROSSING }; const std::lock_guard lock(glInputLock); glInputEvents.push_back(input); - input.Type = JET::ENTERED_SURFACE; + input.Type = JET::CROSSED_IN; input.Value = li_objectid; input.RecipientID = li_objectid; // Recipient is the surface we are entering glInputEvents.push_back(input); @@ -1181,14 +1182,14 @@ static LONG examine_chain(extPointer *Self, LONG Index, SURFACELIST &List, LONG //******************************************************************************************************************** // This timer is used for handling repeat-clicks. -static ERROR repeat_timer(extPointer *Self, LARGE Elapsed, LARGE Unused) +static ERR repeat_timer(extPointer *Self, LARGE Elapsed, LARGE Unused) { pf::Log log(__FUNCTION__); // The subscription is automatically removed if no buttons are held down bool unsub = true; - for (LONG i=0; i < ARRAYSIZE(Self->Buttons); i++) { + for (LONG i=0; i < std::ssize(Self->Buttons); i++) { if (Self->Buttons[i].LastClicked) { LARGE time = PreciseTime(); if (Self->Buttons[i].LastClickTime + 300000LL <= time) { @@ -1200,7 +1201,7 @@ static ERROR repeat_timer(extPointer *Self, LARGE Elapsed, LARGE Unused) input.X = Self->OverX; input.Y = Self->OverY; } - else if (!get_surface_abs(Self->Buttons[i].LastClicked, &surface_x, &surface_y, 0, 0)) { + else if (get_surface_abs(Self->Buttons[i].LastClicked, &surface_x, &surface_y, 0, 0) IS ERR::Okay) { input.X = Self->X - surface_x; input.Y = Self->Y - surface_y; } @@ -1228,8 +1229,8 @@ static ERROR repeat_timer(extPointer *Self, LARGE Elapsed, LARGE Unused) } } - if (unsub) return ERR_Terminate; - else return ERR_Okay; + if (unsub) return ERR::Terminate; + else return ERR::Okay; } //******************************************************************************************************************** @@ -1331,7 +1332,7 @@ static const FieldArray clPointerFields[] = { //******************************************************************************************************************** -ERROR create_pointer_class(void) +ERR create_pointer_class(void) { clPointer = objMetaClass::create::global( fl::BaseClassID(ID_POINTER), @@ -1344,5 +1345,5 @@ ERROR create_pointer_class(void) fl::Size(sizeof(extPointer)), fl::Path(MOD_PATH)); - return clPointer ? ERR_Okay : ERR_AddClass; + return clPointer ? ERR::Okay : ERR::AddClass; } diff --git a/src/display/class_surface/class_surface.cpp b/src/display/class_surface/class_surface.cpp index 9c75da060..574fa6dd9 100644 --- a/src/display/class_surface/class_surface.cpp +++ b/src/display/class_surface/class_surface.cpp @@ -36,16 +36,16 @@ areas. using namespace display; #endif -static ERROR SET_Opacity(extSurface *, DOUBLE); -static ERROR SET_XOffset(extSurface *, Variable *); -static ERROR SET_YOffset(extSurface *, Variable *); +static ERR SET_Opacity(extSurface *, DOUBLE); +static ERR SET_XOffset(extSurface *, Variable *); +static ERR SET_YOffset(extSurface *, Variable *); #define MOVE_VERTICAL 0x0001 #define MOVE_HORIZONTAL 0x0002 -static ERROR consume_input_events(const InputEvent *, LONG); +static ERR consume_input_events(const InputEvent *, LONG); static void draw_region(extSurface *, extSurface *, extBitmap *); -static ERROR redraw_timer(extSurface *, LARGE, LARGE); +static ERR redraw_timer(extSurface *, LARGE, LARGE); /********************************************************************************************************************* ** This call is used to refresh the pointer image when at least one layer has been rearranged. The timer is used to @@ -53,7 +53,7 @@ static ERROR redraw_timer(extSurface *, LARGE, LARGE); ** The delay also prevents clashes with read/write access to the surface list. */ -static ERROR refresh_pointer_timer(OBJECTPTR Task, LARGE Elapsed, LARGE CurrentTime) +static ERR refresh_pointer_timer(OBJECTPTR Task, LARGE Elapsed, LARGE CurrentTime) { objPointer *pointer; if ((pointer = gfxAccessPointer())) { @@ -61,37 +61,33 @@ static ERROR refresh_pointer_timer(OBJECTPTR Task, LARGE Elapsed, LARGE CurrentT ReleaseObject(pointer); } glRefreshPointerTimer = 0; - return ERR_Terminate; // Timer is only called once + return ERR::Terminate; // Timer is only called once } void refresh_pointer(extSurface *Self) { if (!glRefreshPointerTimer) { pf::SwitchContext context(glModule); - auto call = make_function_stdc(refresh_pointer_timer); - SubscribeTimer(0.02, &call, &glRefreshPointerTimer); + SubscribeTimer(0.02, FUNCTION(refresh_pointer_timer), &glRefreshPointerTimer); } } //******************************************************************************************************************** -static ERROR access_video(OBJECTID DisplayID, objDisplay **Display, objBitmap **Bitmap) +static ERR access_video(OBJECTID DisplayID, objDisplay **Display, objBitmap **Bitmap) { - if (!AccessObject(DisplayID, 5000, Display)) { + if (AccessObject(DisplayID, 5000, Display) IS ERR::Okay) { + #ifdef _WIN32 APTR winhandle; - - if (!Display[0]->getPtr(FID_WindowHandle, &winhandle)) { - #ifdef _WIN32 - Display[0]->Bitmap->setHandle(winGetDC(winhandle)); - #else - Display[0]->Bitmap->setHandle(winhandle); - #endif + if (Display[0]->getPtr(FID_WindowHandle, &winhandle) IS ERR::Okay) { + Display[0]->Bitmap->setHandle(winGetDC(winhandle)); } + #endif if (Bitmap) *Bitmap = Display[0]->Bitmap; - return ERR_Okay; + return ERR::Okay; } - else return ERR_AccessObject; + else return ERR::AccessObject; } //******************************************************************************************************************** @@ -103,7 +99,7 @@ static void release_video(objDisplay *Display) Display->Bitmap->getPtr(FID_Handle, &surface); APTR winhandle; - if (!Display->getPtr(FID_WindowHandle, &winhandle)) { + if (Display->getPtr(FID_WindowHandle, &winhandle) IS ERR::Okay) { winReleaseDC(winhandle, surface); } @@ -298,7 +294,7 @@ static void expose_buffer(const SURFACELIST &list, LONG Limit, LONG Index, LONG objDisplay *display; objBitmap *video_bmp; - if (!access_video(DisplayID, &display, &video_bmp)) { + if (access_video(DisplayID, &display, &video_bmp) IS ERR::Okay) { video_bmp->XOffset = 0; video_bmp->YOffset = 0; @@ -397,7 +393,7 @@ static void display_resized(OBJECTID DisplayID, LONG X, LONG Y, LONG Width, LONG { OBJECTID surface_id = GetOwnerID(DisplayID); extSurface *surface; - if (!AccessObject(surface_id, 4000, &surface)) { + if (AccessObject(surface_id, 4000, &surface) IS ERR::Okay) { if (surface->Class->ClassID IS ID_SURFACE) { if ((X != surface->X) or (Y != surface->Y)) { surface->X = X; @@ -415,7 +411,7 @@ static void display_resized(OBJECTID DisplayID, LONG X, LONG Y, LONG Width, LONG //******************************************************************************************************************** -static void notify_free_parent(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, APTR Void) +static void notify_free_parent(OBJECTPTR Object, ACTIONID ActionID, ERR Result, APTR Void) { pf::Log log(__FUNCTION__); auto Self = (extSurface *)CurrentContext(); @@ -429,15 +425,15 @@ static void notify_free_parent(OBJECTPTR Object, ACTIONID ActionID, ERROR Result else FreeResource(Self); } -static void notify_free_callback(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, APTR Void) +static void notify_free_callback(OBJECTPTR Object, ACTIONID ActionID, ERR Result, APTR Void) { pf::Log log(__FUNCTION__); auto Self = (extSurface *)CurrentContext(); for (LONG i=0; i < Self->CallbackCount; i++) { - if (Self->Callback[i].Function.Type IS CALL_SCRIPT) { + if (Self->Callback[i].Function.isScript()) { if (Self->Callback[i].Function.Script.Script->UID IS Object->UID) { - Self->Callback[i].Function.Type = CALL_NONE; + Self->Callback[i].Function.clear(); LONG j; for (j=i; j < Self->CallbackCount-1; j++) { // Shorten the array @@ -450,7 +446,7 @@ static void notify_free_callback(OBJECTPTR Object, ACTIONID ActionID, ERROR Resu } } -static void notify_draw_display(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, struct acDraw *Args) +static void notify_draw_display(OBJECTPTR Object, ACTIONID ActionID, ERR Result, struct acDraw *Args) { pf::Log log(__FUNCTION__); auto Self = (extSurface *)CurrentContext(); @@ -471,7 +467,7 @@ static void notify_draw_display(OBJECTPTR Object, ACTIONID ActionID, ERROR Resul } } -static void notify_redimension_parent(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, struct acRedimension *Args) +static void notify_redimension_parent(OBJECTPTR Object, ACTIONID ActionID, ERR Result, struct acRedimension *Args) { pf::Log log(__FUNCTION__); auto Self = (extSurface *)CurrentContext(); @@ -491,7 +487,7 @@ static void notify_redimension_parent(OBJECTPTR Object, ACTIONID ActionID, ERROR LONG i; for (i=0; (i < LONG(glSurfaces.size())) and (glSurfaces[i].SurfaceID != Self->ParentID); i++); if (i >= LONG(glSurfaces.size())) { - log.warning(ERR_Search); + log.warning(ERR::Search); return; } parentwidth = glSurfaces[i].Width; @@ -499,7 +495,7 @@ static void notify_redimension_parent(OBJECTPTR Object, ACTIONID ActionID, ERROR } else { DISPLAYINFO *display; - if (!gfxGetDisplayInfo(0, &display)) { + if (gfxGetDisplayInfo(0, &display) IS ERR::Okay) { parentwidth = display->Width; parentheight = display->Height; } @@ -508,31 +504,31 @@ static void notify_redimension_parent(OBJECTPTR Object, ACTIONID ActionID, ERROR // Convert relative offsets to their fixed equivalent - if (Self->Dimensions & DMF_RELATIVE_X_OFFSET) Self->XOffset = parentwidth * Self->XOffsetPercent; - if (Self->Dimensions & DMF_RELATIVE_Y_OFFSET) Self->YOffset = parentheight * Self->YOffsetPercent; + if (Self->Dimensions & DMF_SCALED_X_OFFSET) Self->XOffset = parentwidth * Self->XOffsetPercent; + if (Self->Dimensions & DMF_SCALED_Y_OFFSET) Self->YOffset = parentheight * Self->YOffsetPercent; // Calculate absolute width and height values - if (Self->Dimensions & DMF_RELATIVE_WIDTH) width = parentwidth * Self->WidthPercent; + if (Self->Dimensions & DMF_SCALED_WIDTH) width = parentwidth * Self->WidthPercent; else if (Self->Dimensions & DMF_FIXED_WIDTH) width = Self->Width; else if (Self->Dimensions & DMF_X_OFFSET) { if (Self->Dimensions & DMF_FIXED_X) { width = parentwidth - Self->X - Self->XOffset; } - else if (Self->Dimensions & DMF_RELATIVE_X) { + else if (Self->Dimensions & DMF_SCALED_X) { width = parentwidth - (parentwidth * Self->XPercent) - Self->XOffset; } else width = parentwidth - Self->XOffset; } else width = Self->Width; - if (Self->Dimensions & DMF_RELATIVE_HEIGHT) height = parentheight * Self->HeightPercent; + if (Self->Dimensions & DMF_SCALED_HEIGHT) height = parentheight * Self->HeightPercent; else if (Self->Dimensions & DMF_FIXED_HEIGHT) height = Self->Height; else if (Self->Dimensions & DMF_Y_OFFSET) { if (Self->Dimensions & DMF_FIXED_Y) { height = parentheight - Self->Y - Self->YOffset; } - else if (Self->Dimensions & DMF_RELATIVE_Y) { + else if (Self->Dimensions & DMF_SCALED_Y) { height = parentheight - (parentheight * Self->YPercent) - Self->YOffset; } else height = parentheight - Self->YOffset; @@ -541,11 +537,11 @@ static void notify_redimension_parent(OBJECTPTR Object, ACTIONID ActionID, ERROR // Calculate new coordinates - if (Self->Dimensions & DMF_RELATIVE_X) x = parentwidth * Self->XPercent; + if (Self->Dimensions & DMF_SCALED_X) x = parentwidth * Self->XPercent; else if (Self->Dimensions & DMF_X_OFFSET) x = parentwidth - Self->XOffset - width; else x = Self->X; - if (Self->Dimensions & DMF_RELATIVE_Y) y = parentheight * Self->YPercent; + if (Self->Dimensions & DMF_SCALED_Y) y = parentheight * Self->YPercent; else if (Self->Dimensions & DMF_Y_OFFSET) y = parentheight - Self->YOffset - height; else y = Self->Y; @@ -582,10 +578,10 @@ Activate: Shows a surface object on the display. -END- *********************************************************************************************************************/ -static ERROR SURFACE_Activate(extSurface *Self, APTR Void) +static ERR SURFACE_Activate(extSurface *Self, APTR Void) { if (!Self->ParentID) acShow(Self); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -593,10 +589,10 @@ static ERROR SURFACE_Activate(extSurface *Self, APTR Void) -METHOD- AddCallback: Inserts a function hook into the drawing process of a surface object. -The AddCallback() method provides a gateway for custom functions to draw directly to a surface. Whenever a surface +The AddCallback() method provides a hook for custom functions to draw directly to a surface. Whenever a surface object performs a redraw event, all functions inserted by this method will be called in their original subscription order with a direct reference to the Surface's target bitmap. The C/C++ prototype is -`Function(APTR Context, *Surface, *Bitmap)`. +`Function(APTR Context, *Surface, *Bitmap, APTR Meta)`. The Fluid prototype is `function draw(Surface, Bitmap)` @@ -617,20 +613,20 @@ AllocMemory *********************************************************************************************************************/ -static ERROR SURFACE_AddCallback(extSurface *Self, struct drwAddCallback *Args) +static ERR SURFACE_AddCallback(extSurface *Self, struct drwAddCallback *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); OBJECTPTR context = GetParentContext(); OBJECTPTR call_context = NULL; - if (Args->Callback->Type IS CALL_STDC) call_context = (OBJECTPTR)Args->Callback->StdC.Context; - else if (Args->Callback->Type IS CALL_SCRIPT) call_context = context; // Scripts use runtime ID resolution... + if (Args->Callback->isC()) call_context = (OBJECTPTR)Args->Callback->StdC.Context; + else if (Args->Callback->isScript()) call_context = context; // Scripts use runtime ID resolution... if (context->UID < 0) { log.warning("Public objects may not draw directly to surfaces."); - return ERR_Failed; + return ERR::Failed; } log.msg("Context: %d, Callback Context: %d, Routine: %p (Count: %d)", context->UID, call_context ? call_context->UID : 0, Args->Callback->StdC.Routine, Self->CallbackCount); @@ -643,10 +639,10 @@ static ERROR SURFACE_AddCallback(extSurface *Self, struct drwAddCallback *Args) LONG i; for (i=0; i < Self->CallbackCount; i++) { if (Self->Callback[i].Object IS context) { - if ((Self->Callback[i].Function.Type IS CALL_STDC) and (Args->Callback->Type IS CALL_STDC)) { + if ((Self->Callback[i].Function.isC()) and (Args->Callback->isC())) { if (Self->Callback[i].Function.StdC.Routine IS Args->Callback->StdC.Routine) break; } - else if ((Self->Callback[i].Function.Type IS CALL_SCRIPT) and (Args->Callback->Type IS CALL_SCRIPT)) { + else if ((Self->Callback[i].Function.isScript()) and (Args->Callback->isScript())) { if (Self->Callback[i].Function.Script.ProcedureID IS Args->Callback->Script.ProcedureID) break; } } @@ -661,7 +657,7 @@ static ERROR SURFACE_AddCallback(extSurface *Self, struct drwAddCallback *Args) } Self->Callback[i].Object = context; Self->Callback[i].Function = *Args->Callback; - return ERR_Okay; + return ERR::Okay; } else if (Self->CallbackCount < Self->CallbackSize) { // Add the callback routine to the cache @@ -671,12 +667,12 @@ static ERROR SURFACE_AddCallback(extSurface *Self, struct drwAddCallback *Args) Self->CallbackCount++; } else if (Self->CallbackCount < 255) { - log.extmsg("Expanding draw subscription array."); + log.detail("Expanding draw subscription array."); LONG new_size = Self->CallbackSize + 10; if (new_size > 255) new_size = 255; SurfaceCallback *scb; - if (!AllocMemory(sizeof(SurfaceCallback) * new_size, MEM::DATA|MEM::NO_CLEAR, &scb)) { + if (AllocMemory(sizeof(SurfaceCallback) * new_size, MEM::DATA|MEM::NO_CLEAR, &scb) IS ERR::Okay) { CopyMemory(Self->Callback, scb, sizeof(SurfaceCallback) * Self->CallbackCount); scb[Self->CallbackCount].Object = context; @@ -687,9 +683,9 @@ static ERROR SURFACE_AddCallback(extSurface *Self, struct drwAddCallback *Args) if (Self->Callback != Self->CallbackCache) FreeResource(Self->Callback); Self->Callback = scb; } - else return ERR_AllocMemory; + else return ERR::AllocMemory; } - else return ERR_ArrayFull; + else return ERR::ArrayFull; } else { Self->Callback = Self->CallbackCache; @@ -700,11 +696,10 @@ static ERROR SURFACE_AddCallback(extSurface *Self, struct drwAddCallback *Args) } if (Args->Callback->Type IS CALL_SCRIPT) { - auto callback = make_function_stdc(notify_free_callback); - SubscribeAction(Args->Callback->Script.Script, AC_Free, &callback); + SubscribeAction(Args->Callback->Script.Script, AC_Free, FUNCTION(notify_free_callback)); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -713,11 +708,11 @@ Disable: Disables a surface object. -END- *********************************************************************************************************************/ -static ERROR SURFACE_Disable(extSurface *Self, APTR Void) +static ERR SURFACE_Disable(extSurface *Self, APTR Void) { Self->Flags |= RNF::DISABLED; UpdateSurfaceField(Self, &SurfaceRecord::Flags, Self->Flags); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -726,11 +721,11 @@ Enable: Enables a disabled surface object. -END- *********************************************************************************************************************/ -static ERROR SURFACE_Enable(extSurface *Self, APTR Void) +static ERR SURFACE_Enable(extSurface *Self, APTR Void) { Self->Flags &= ~RNF::DISABLED; UpdateSurfaceField(Self, &SurfaceRecord::Flags, Self->Flags); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -741,18 +736,18 @@ Focus: Changes the primary user focus to the surface object. static LARGE glLastFocusTime = 0; -static ERROR SURFACE_Focus(extSurface *Self, APTR Void) +static ERR SURFACE_Focus(extSurface *Self, APTR Void) { pf::Log log; - if (Self->disabled()) return ERR_Okay|ERF_Notified; + if (Self->disabled()) return ERR::Okay|ERR::Notified; if (auto msg = GetActionMsg()) { // This is a message - in which case it could have been delayed and thus superseded by a more recent message. if (msg->Time < glLastFocusTime) { FOCUSMSG("Ignoring superseded focus message."); - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } } @@ -760,39 +755,39 @@ static ERROR SURFACE_Focus(extSurface *Self, APTR Void) FOCUSMSG("Focus propagated to parent (IGNORE_FOCUS flag set)."); acFocus(Self->ParentID); glLastFocusTime = PreciseTime(); - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } if ((Self->Flags & RNF::NO_FOCUS) != RNF::NIL) { FOCUSMSG("Focus cancelled (NO_FOCUS flag set)."); glLastFocusTime = PreciseTime(); - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } FOCUSMSG("Focussing... HasFocus: %c", (Self->hasFocus()) ? 'Y' : 'N'); if (auto modal = gfxGetModalSurface()) { if (modal != Self->UID) { - ERROR error; + ERR error; error = gfxCheckIfChild(modal, Self->UID); - if ((error != ERR_True) and (error != ERR_LimitedSuccess)) { + if ((error != ERR::True) and (error != ERR::LimitedSuccess)) { // Focussing is not OK - surface is out of the modal's scope log.warning("Surface #%d is not within modal #%d's scope.", Self->UID, modal); glLastFocusTime = PreciseTime(); - return ERR_Failed|ERF_Notified; + return ERR::Failed|ERR::Notified; } } } - const std::lock_guard lock(glFocusLock); + const std::lock_guard lock(glFocusLock); // Return immediately if this surface object already has the -primary- focus if (Self->hasFocus() and (glFocusList[0] IS Self->UID)) { FOCUSMSG("Surface already has the primary focus."); glLastFocusTime = PreciseTime(); - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } LONG j; @@ -808,7 +803,7 @@ static ERROR SURFACE_Focus(extSurface *Self, APTR Void) // during the free process. glLastFocusTime = PreciseTime(); - return ERR_Failed|ERF_Notified; + return ERR::Failed|ERR::Notified; } // Build the new focus chain in a local focus list. Also also reset the HAS_FOCUS flag. Surfaces that have @@ -894,7 +889,7 @@ static ERROR SURFACE_Focus(extSurface *Self, APTR Void) } glLastFocusTime = PreciseTime(); - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } else { Self->Flags |= RNF::HAS_FOCUS; @@ -910,13 +905,13 @@ static ERROR SURFACE_Focus(extSurface *Self, APTR Void) } glLastFocusTime = PreciseTime(); - return ERR_Okay; + return ERR::Okay; } } //******************************************************************************************************************** -static ERROR SURFACE_Free(extSurface *Self, APTR Void) +static ERR SURFACE_Free(extSurface *Self, APTR Void) { if (Self->ScrollTimer) { UpdateTimer(Self->ScrollTimer, 0); Self->ScrollTimer = 0; } if (Self->RedrawTimer) { UpdateTimer(Self->RedrawTimer, 0); Self->RedrawTimer = 0; } @@ -930,8 +925,7 @@ static ERROR SURFACE_Free(extSurface *Self, APTR Void) if (Self->ParentID) { extSurface *parent; - ERROR error; - if (!(error = AccessObject(Self->ParentID, 5000, &parent))) { + if (auto error = AccessObject(Self->ParentID, 5000, &parent); error IS ERR::Okay) { UnsubscribeAction(parent, 0); if (Self->transparent()) { drwRemoveCallback(parent, NULL); @@ -960,7 +954,7 @@ static ERROR SURFACE_Free(extSurface *Self, APTR Void) // Give the focus to the parent if our object has the primary focus. Do not apply this technique to surface objects // acting as windows, as the window class has its own focus management code. - if (Self->hasFocus() and (GetClassID(Self->ownerID()) != ID_WINDOW)) { + if (Self->hasFocus() and (Self->Owner) and (Self->Owner->Class->ClassID != ID_WINDOW)) { if (Self->ParentID) acFocus(Self->ParentID); } @@ -979,7 +973,7 @@ static ERROR SURFACE_Free(extSurface *Self, APTR Void) else it++; } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -988,19 +982,19 @@ Hide: Hides a surface object from the display. -END- *********************************************************************************************************************/ -static ERROR SURFACE_Hide(extSurface *Self, APTR Void) +static ERR SURFACE_Hide(extSurface *Self, APTR Void) { pf::Log log; log.traceBranch(""); - if (Self->invisible()) return ERR_Okay|ERF_Notified; + if (Self->invisible()) return ERR::Okay|ERR::Notified; if (!Self->ParentID) { Self->Flags &= ~RNF::VISIBLE; // Important to switch off visibliity before Hide(), otherwise a false redraw will occur. UpdateSurfaceField(Self, &SurfaceRecord::Flags, Self->Flags); - if (acHide(Self->DisplayID) != ERR_Okay) return ERR_Failed; + if (acHide(Self->DisplayID) != ERR::Okay) return ERR::Failed; } else { // Mark this surface object as invisible, then invalidate the region it was covering in order to have the background redrawn. @@ -1026,7 +1020,7 @@ static ERROR SURFACE_Hide(extSurface *Self, APTR Void) } refresh_pointer(Self); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1046,14 +1040,14 @@ Okay *********************************************************************************************************************/ -static ERROR SURFACE_InheritedFocus(extSurface *Self, struct gfxInheritedFocus *Args) +static ERR SURFACE_InheritedFocus(extSurface *Self, struct gfxInheritedFocus *Args) { if (auto msg = GetActionMsg()) { // This is a message - in which case it could have been delayed and thus superseded by a more recent message. if (msg->Time < glLastFocusTime) { FOCUSMSG("Ignoring superseded focus message."); - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } } @@ -1061,7 +1055,7 @@ static ERROR SURFACE_InheritedFocus(extSurface *Self, struct gfxInheritedFocus * if (Self->hasFocus()) { FOCUSMSG("This surface already has focus."); - return ERR_Okay; + return ERR::Okay; } else { FOCUSMSG("Object has received the focus through inheritance."); @@ -1070,14 +1064,14 @@ static ERROR SURFACE_InheritedFocus(extSurface *Self, struct gfxInheritedFocus * //UpdateSurfaceField(Self, Flags); // Not necessary because SURFACE_Focus sets the surfacelist - NotifySubscribers(Self, AC_Focus, NULL, ERR_Okay); - return ERR_Okay; + NotifySubscribers(Self, AC_Focus, NULL, ERR::Okay); + return ERR::Okay; } } //******************************************************************************************************************** -static ERROR SURFACE_Init(extSurface *Self, APTR Void) +static ERR SURFACE_Init(extSurface *Self, APTR Void) { pf::Log log; objBitmap *bitmap; @@ -1095,16 +1089,16 @@ static ERROR SURFACE_Init(extSurface *Self, APTR Void) if ((!Self->ParentID) and (gfxGetDisplayType() IS DT::NATIVE)) { if ((Self->Flags & RNF::FULL_SCREEN) IS RNF::NIL) { - if (FindObject("desktop", ID_SURFACE, FOF::NIL, &Self->ParentID) != ERR_Okay) { + if (FindObject("desktop", ID_SURFACE, FOF::NIL, &Self->ParentID) != ERR::Okay) { if (!glSurfaces.empty()) Self->ParentID = glSurfaces[0].SurfaceID; } } } - ERROR error = ERR_Okay; + ERR error = ERR::Okay; if (Self->ParentID) { pf::ScopedObjectLock parent(Self->ParentID, 3000); - if (!parent.granted()) return ERR_AccessObject; + if (!parent.granted()) return ERR::AccessObject; log.trace("Initialising surface to parent #%d.", Self->ParentID); @@ -1121,16 +1115,13 @@ static ERROR SURFACE_Init(extSurface *Self, APTR Void) // Subscribe to the surface parent's Resize and Redimension actions - auto callback = make_function_stdc(notify_free_parent); - SubscribeAction(*parent, AC_Free, &callback); - - callback = make_function_stdc(notify_redimension_parent); - SubscribeAction(*parent, AC_Redimension, &callback); + SubscribeAction(*parent, AC_Free, FUNCTION(notify_free_parent)); + SubscribeAction(*parent, AC_Redimension, FUNCTION(notify_redimension_parent)); // If the surface object is transparent, subscribe to the Draw action of the parent object. if (Self->transparent()) { - auto func = make_function_stdc(draw_region); + auto func = FUNCTION(draw_region); struct drwAddCallback args = { &func }; Action(MT_DrwAddCallback, *parent, &args); @@ -1142,17 +1133,17 @@ static ERROR SURFACE_Init(extSurface *Self, APTR Void) // Set FixedX/FixedY accordingly - this is used to assist in the layout process when a surface is used in a document. if (Self->Dimensions & 0xffff) { - if ((Self->Dimensions & DMF_X) and (Self->Dimensions & (DMF_FIXED_WIDTH|DMF_RELATIVE_WIDTH|DMF_FIXED_X_OFFSET|DMF_RELATIVE_X_OFFSET))) { + if ((Self->Dimensions & DMF_X) and (Self->Dimensions & (DMF_FIXED_WIDTH|DMF_SCALED_WIDTH|DMF_FIXED_X_OFFSET|DMF_SCALED_X_OFFSET))) { Self->FixedX = TRUE; } - else if ((Self->Dimensions & DMF_X_OFFSET) and (Self->Dimensions & (DMF_FIXED_WIDTH|DMF_RELATIVE_WIDTH|DMF_FIXED_X|DMF_RELATIVE_X))) { + else if ((Self->Dimensions & DMF_X_OFFSET) and (Self->Dimensions & (DMF_FIXED_WIDTH|DMF_SCALED_WIDTH|DMF_FIXED_X|DMF_SCALED_X))) { Self->FixedX = TRUE; } - if ((Self->Dimensions & DMF_Y) and (Self->Dimensions & (DMF_FIXED_HEIGHT|DMF_RELATIVE_HEIGHT|DMF_FIXED_Y_OFFSET|DMF_RELATIVE_Y_OFFSET))) { + if ((Self->Dimensions & DMF_Y) and (Self->Dimensions & (DMF_FIXED_HEIGHT|DMF_SCALED_HEIGHT|DMF_FIXED_Y_OFFSET|DMF_SCALED_Y_OFFSET))) { Self->FixedY = TRUE; } - else if ((Self->Dimensions & DMF_Y_OFFSET) and (Self->Dimensions & (DMF_FIXED_HEIGHT|DMF_RELATIVE_HEIGHT|DMF_FIXED_Y|DMF_RELATIVE_Y))) { + else if ((Self->Dimensions & DMF_Y_OFFSET) and (Self->Dimensions & (DMF_FIXED_HEIGHT|DMF_SCALED_HEIGHT|DMF_FIXED_Y|DMF_SCALED_Y))) { Self->FixedY = TRUE; } } @@ -1160,18 +1151,18 @@ static ERROR SURFACE_Init(extSurface *Self, APTR Void) // Recalculate coordinates if offsets are used if (Self->Dimensions & DMF_FIXED_X_OFFSET) Self->setXOffset(Self->XOffset); - else if (Self->Dimensions & DMF_RELATIVE_X_OFFSET) Self->setPercentage(FID_XOffset, Self->XOffsetPercent); + else if (Self->Dimensions & DMF_SCALED_X_OFFSET) Self->setScale(FID_XOffset, Self->XOffsetPercent); if (Self->Dimensions & DMF_FIXED_Y_OFFSET) Self->setYOffset(Self->YOffset); - else if (Self->Dimensions & DMF_RELATIVE_Y_OFFSET) Self->setPercentage(FID_YOffset, Self->YOffsetPercent); + else if (Self->Dimensions & DMF_SCALED_Y_OFFSET) Self->setScale(FID_YOffset, Self->YOffsetPercent); - if (Self->Dimensions & DMF_RELATIVE_X) Self->setPercentage(FID_X, Self->XPercent); - if (Self->Dimensions & DMF_RELATIVE_Y) Self->setPercentage(FID_Y, Self->YPercent); - if (Self->Dimensions & DMF_RELATIVE_WIDTH) Self->setPercentage(FID_Width, Self->WidthPercent); - if (Self->Dimensions & DMF_RELATIVE_HEIGHT) Self->setPercentage(FID_Height, Self->HeightPercent); + if (Self->Dimensions & DMF_SCALED_X) Self->setScale(FID_X, Self->XPercent); + if (Self->Dimensions & DMF_SCALED_Y) Self->setScale(FID_Y, Self->YPercent); + if (Self->Dimensions & DMF_SCALED_WIDTH) Self->setScale(FID_Width, Self->WidthPercent); + if (Self->Dimensions & DMF_SCALED_HEIGHT) Self->setScale(FID_Height, Self->HeightPercent); if (!(Self->Dimensions & DMF_WIDTH)) { - if (Self->Dimensions & (DMF_RELATIVE_X_OFFSET|DMF_FIXED_X_OFFSET)) { + if (Self->Dimensions & (DMF_SCALED_X_OFFSET|DMF_FIXED_X_OFFSET)) { Self->Width = parent->Width - Self->X - Self->XOffset; } else { @@ -1181,7 +1172,7 @@ static ERROR SURFACE_Init(extSurface *Self, APTR Void) } if (!(Self->Dimensions & DMF_HEIGHT)) { - if (Self->Dimensions & (DMF_RELATIVE_Y_OFFSET|DMF_FIXED_Y_OFFSET)) { + if (Self->Dimensions & (DMF_SCALED_Y_OFFSET|DMF_FIXED_Y_OFFSET)) { Self->Height = parent->Height - Self->Y - Self->YOffset; } else { @@ -1295,7 +1286,7 @@ static ERROR SURFACE_Init(extSurface *Self, APTR Void) // Alignment adjustments DISPLAYINFO *display; - if (!gfxGetDisplayInfo(0, &display)) { + if (gfxGetDisplayInfo(0, &display) IS ERR::Okay) { if ((Self->Align & ALIGN::LEFT) != ALIGN::NIL) { Self->X = 0; Self->setX(Self->X); } else if ((Self->Align & ALIGN::RIGHT) != ALIGN::NIL) { Self->X = display->Width - Self->Width; Self->setX(Self->X); } else if ((Self->Align & ALIGN::HORIZONTAL) != ALIGN::NIL) { Self->X = (display->Width - Self->Width) / 2; Self->setX(Self->X); } @@ -1317,11 +1308,11 @@ static ERROR SURFACE_Init(extSurface *Self, APTR Void) if ((Self->Flags & RNF::COMPOSITE) != RNF::NIL) scrflags |= SCR::COMPOSITE; OBJECTID id, pop_display = 0; - CSTRING name = FindObject("SystemDisplay", 0, FOF::NIL, &id) ? "SystemDisplay" : (CSTRING)NULL; + CSTRING name = FindObject("SystemDisplay", 0, FOF::NIL, &id) != ERR::Okay ? "SystemDisplay" : (CSTRING)NULL; if (Self->PopOverID) { extSurface *popsurface; - if (!AccessObject(Self->PopOverID, 2000, &popsurface)) { + if (AccessObject(Self->PopOverID, 2000, &popsurface) IS ERR::Okay) { pop_display = popsurface->DisplayID; ReleaseObject(popsurface); @@ -1380,16 +1371,15 @@ static ERROR SURFACE_Init(extSurface *Self, APTR Void) // can be used by the host to notify of window exposures. if (Self->DisplayWindow) { - display->setResizeFeedback(make_function_stdc(display_resized)); + display->setResizeFeedback(FUNCTION(display_resized)); - auto callback = make_function_stdc(notify_draw_display); - SubscribeAction(display, AC_Draw, &callback); + SubscribeAction(display, AC_Draw, FUNCTION(notify_draw_display)); } Self->DisplayID = display->UID; - error = ERR_Okay; + error = ERR::Okay; } - else return log.warning(ERR_CreateObject); + else return log.warning(ERR::CreateObject); } // Allocate a backing store if this is a host object, or the parent is foreign, or we are the child of a host object @@ -1400,7 +1390,7 @@ static ERROR SURFACE_Init(extSurface *Self, APTR Void) else { if (Self->BitsPerPixel >= 8) { DISPLAYINFO *info; - if (!gfxGetDisplayInfo(Self->DisplayID, &info)) { + if (gfxGetDisplayInfo(Self->DisplayID, &info) IS ERR::Okay) { if (info->BitsPerPixel != Self->BitsPerPixel) require_store = true; } } @@ -1445,13 +1435,13 @@ static ERROR SURFACE_Init(extSurface *Self, APTR Void) Self->LineWidth = bitmap->LineWidth; Self->Data = bitmap->Data; Self->BufferID = bitmap->UID; - error = ERR_Okay; + error = ERR::Okay; } - else error = ERR_CreateObject; + else error = ERR::CreateObject; } - else error = ERR_AccessObject; + else error = ERR::AccessObject; - if (error) return log.warning(error); + if (error != ERR::Okay) return log.warning(error); } else { Self->BufferID = parent_bitmap; @@ -1461,7 +1451,7 @@ static ERROR SURFACE_Init(extSurface *Self, APTR Void) // If the FIXED_BUFFER option is set, pass the NEVER_SHRINK option to the bitmap if ((Self->Flags & RNF::FIXED_BUFFER) != RNF::NIL) { - if (!AccessObject(Self->BufferID, 5000, &bitmap)) { + if (AccessObject(Self->BufferID, 5000, &bitmap) IS ERR::Okay) { bitmap->Flags |= BMF::NEVER_SHRINK; ReleaseObject(bitmap); } @@ -1469,7 +1459,7 @@ static ERROR SURFACE_Init(extSurface *Self, APTR Void) // Track the surface object - if (track_layer(Self) != ERR_Okay) return ERR_Failed; + if (track_layer(Self) != ERR::Okay) return ERR::Failed; // The PopOver reference can only be managed once track_layer() has been called if this is a surface with a parent. @@ -1503,7 +1493,7 @@ static ERROR SURFACE_Init(extSurface *Self, APTR Void) if ((Self->Flags & RNF::STICK_TO_BACK) != RNF::NIL) acMoveToBack(Self); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1512,7 +1502,7 @@ LostFocus: Informs a surface object that it has lost the user focus. -END- *********************************************************************************************************************/ -static ERROR SURFACE_LostFocus(extSurface *Self, APTR Void) +static ERR SURFACE_LostFocus(extSurface *Self, APTR Void) { #if 0 if (auto msg = GetActionMsg()) { @@ -1520,7 +1510,7 @@ static ERROR SURFACE_LostFocus(extSurface *Self, APTR Void) if (msg->Time < glLastFocusTime) { FOCUSMSG("Ignoring superseded focus message."); - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } } @@ -1530,9 +1520,9 @@ static ERROR SURFACE_LostFocus(extSurface *Self, APTR Void) if (Self->hasFocus()) { Self->Flags &= ~RNF::HAS_FOCUS; UpdateSurfaceField(Self, &SurfaceRecord::Flags, Self->Flags); - return ERR_Okay; + return ERR::Okay; } - else return ERR_Okay | ERF_Notified; + else return ERR::Okay | ERR::Notified; } /********************************************************************************************************************* @@ -1551,10 +1541,10 @@ host platform. *********************************************************************************************************************/ -static ERROR SURFACE_Minimise(extSurface *Self, APTR Void) +static ERR SURFACE_Minimise(extSurface *Self, APTR Void) { if (Self->DisplayID) ActionMsg(MT_GfxMinimise, Self->DisplayID, NULL); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1563,13 +1553,13 @@ Move: Moves a surface object to a new display position. -END- *********************************************************************************************************************/ -static ERROR SURFACE_Move(extSurface *Self, struct acMove *Args) +static ERR SURFACE_Move(extSurface *Self, struct acMove *Args) { pf::Log log; struct acMove move; LONG i; - if (!Args) return log.warning(ERR_NullArgs)|ERF_Notified; + if (!Args) return log.warning(ERR::NullArgs)|ERR::Notified; // Check if other move messages are queued for this object - if so, do not do anything until the final message is // reached. @@ -1580,11 +1570,11 @@ static ERROR SURFACE_Move(extSurface *Self, struct acMove *Args) LONG index = 0; UBYTE msgbuffer[sizeof(Message) + sizeof(ActionMessage) + sizeof(struct acMove)]; - while (!ScanMessages(&index, MSGID_ACTION, msgbuffer, sizeof(msgbuffer))) { + while (ScanMessages(&index, MSGID_ACTION, msgbuffer, sizeof(msgbuffer)) IS ERR::Okay) { auto action = (ActionMessage *)(msgbuffer + sizeof(Message)); if ((action->ActionID IS AC_MoveToPoint) and (action->ObjectID IS Self->UID)) { - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } else if ((action->ActionID IS AC_Move) and (action->SendArgs IS TRUE) and (action->ObjectID IS Self->UID)) { @@ -1595,11 +1585,11 @@ static ERROR SURFACE_Move(extSurface *Self, struct acMove *Args) UpdateMessage(((Message *)msgbuffer)->UID, 0, action, sizeof(ActionMessage) + sizeof(struct acMove)); - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } } - if ((Self->Flags & RNF::STICKY) != RNF::NIL) return ERR_Failed|ERF_Notified; + if ((Self->Flags & RNF::STICKY) != RNF::NIL) return ERR::Failed|ERR::Notified; LONG xchange = Args->DeltaX; LONG ychange = Args->DeltaY; @@ -1615,7 +1605,7 @@ static ERROR SURFACE_Move(extSurface *Self, struct acMove *Args) // If there isn't any movement, return immediately if ((move.DeltaX < 1) and (move.DeltaX > -1) and (move.DeltaY < 1) and (move.DeltaY > -1)) { - return ERR_Failed|ERF_Notified; + return ERR::Failed|ERR::Notified; } log.traceBranch("X,Y: %d,%d", xchange, ychange); @@ -1661,7 +1651,7 @@ static ERROR SURFACE_Move(extSurface *Self, struct acMove *Args) // Second check: If there isn't any movement, return immediately if ((!move.DeltaX) and (!move.DeltaY)) { - return ERR_Failed|ERF_Notified; + return ERR::Failed|ERR::Notified; } } @@ -1677,8 +1667,8 @@ static ERROR SURFACE_Move(extSurface *Self, struct acMove *Args) log.traceBranch("Sending redimension notifications"); struct acRedimension redimension = { (DOUBLE)Self->X, (DOUBLE)Self->Y, 0, (DOUBLE)Self->Width, (DOUBLE)Self->Height, 0 }; - NotifySubscribers(Self, AC_Redimension, &redimension, ERR_Okay); - return ERR_Okay|ERF_Notified; + NotifySubscribers(Self, AC_Redimension, &redimension, ERR::Okay); + return ERR::Okay|ERR::Notified; } /********************************************************************************************************************* @@ -1687,13 +1677,13 @@ MoveToBack: Moves a surface object to the back of its container. -END- *********************************************************************************************************************/ -static ERROR SURFACE_MoveToBack(extSurface *Self, APTR Void) +static ERR SURFACE_MoveToBack(extSurface *Self, APTR Void) { pf::Log log; if (!Self->ParentID) { acMoveToBack(Self->DisplayID); - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } log.branch("%s", Self->Name); @@ -1702,7 +1692,7 @@ static ERROR SURFACE_MoveToBack(extSurface *Self, APTR Void) auto &list = glSurfaces; LONG index; // Get our position within the chain - if ((index = find_surface_list(Self)) IS -1) return log.warning(ERR_Search)|ERF_Notified; + if ((index = find_surface_list(Self)) IS -1) return log.warning(ERR::Search)|ERR::Notified; OBJECTID parent_bitmap; if (auto i = find_parent_list(list, Self); i != -1) parent_bitmap = list[i].BitmapID; @@ -1723,7 +1713,7 @@ static ERROR SURFACE_MoveToBack(extSurface *Self, APTR Void) } } - if (pos >= index) return ERR_Okay|ERF_Notified; // If the position is unchanged, return immediately + if (pos >= index) return ERR::Okay|ERR::Notified; // If the position is unchanged, return immediately move_layer_pos(list, index, pos); // Reorder the list so that our surface object is inserted at the new position @@ -1737,7 +1727,7 @@ static ERROR SURFACE_MoveToBack(extSurface *Self, APTR Void) refresh_pointer(Self); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1746,7 +1736,7 @@ MoveToFront: Moves a surface object to the front of its container. -END- *********************************************************************************************************************/ -static ERROR SURFACE_MoveToFront(extSurface *Self, APTR Void) +static ERR SURFACE_MoveToFront(extSurface *Self, APTR Void) { pf::Log log; @@ -1754,14 +1744,14 @@ static ERROR SURFACE_MoveToFront(extSurface *Self, APTR Void) if (!Self->ParentID) { acMoveToFront(Self->DisplayID); - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } const std::lock_guard lock(glSurfaceLock); LONG currentindex; if ((currentindex = find_surface_list(Self)) IS -1) { - return log.warning(ERR_Search)|ERF_Notified; + return log.warning(ERR::Search)|ERR::Notified; } // Find the object in the list that our surface object will displace @@ -1794,14 +1784,14 @@ static ERROR SURFACE_MoveToFront(extSurface *Self, APTR Void) if (glSurfaces[i].Level IS level) { if (glSurfaces[i].SurfaceID != Self->PopOverID) { acMoveToFront(Self->PopOverID); - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } break; } } } - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } // Skip past the children that belong to the target object @@ -1831,7 +1821,7 @@ static ERROR SURFACE_MoveToFront(extSurface *Self, APTR Void) // Areas of our surface that were obscured by surfaces that also shared our bitmap space. objBitmap *bitmap; - if (!AccessObject(Self->BufferID, 5000, &bitmap)) { + if (AccessObject(Self->BufferID, 5000, &bitmap) IS ERR::Okay) { auto area = ClipRectangle(cplist[i].Left, cplist[i].Top, cplist[i].Right, cplist[i].Bottom); invalidate_overlap(Self, cplist, currentindex, i, area, bitmap); ReleaseObject(bitmap); @@ -1848,7 +1838,7 @@ static ERROR SURFACE_MoveToFront(extSurface *Self, APTR Void) if (cplist[i].Level IS level) { if (cplist[i].SurfaceID != Self->PopOverID) { acMoveToFront(Self->PopOverID); - return ERR_Okay; + return ERR::Okay; } break; } @@ -1856,7 +1846,7 @@ static ERROR SURFACE_MoveToFront(extSurface *Self, APTR Void) } refresh_pointer(Self); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1865,7 +1855,7 @@ MoveToPoint: Moves a surface object to an absolute coordinate. -END- *********************************************************************************************************************/ -static ERROR SURFACE_MoveToPoint(extSurface *Self, struct acMoveToPoint *Args) +static ERR SURFACE_MoveToPoint(extSurface *Self, struct acMoveToPoint *Args) { struct acMove move; @@ -1877,12 +1867,12 @@ static ERROR SURFACE_MoveToPoint(extSurface *Self, struct acMoveToPoint *Args) move.DeltaZ = 0; - return Action(AC_Move, Self, &move)|ERF_Notified; + return Action(AC_Move, Self, &move)|ERR::Notified; } //******************************************************************************************************************** -static ERROR SURFACE_NewOwner(extSurface *Self, struct acNewOwner *Args) +static ERR SURFACE_NewOwner(extSurface *Self, struct acNewOwner *Args) { if ((!Self->ParentDefined) and (!Self->initialised())) { OBJECTID owner_id = Args->NewOwner->UID; @@ -1893,12 +1883,12 @@ static ERROR SURFACE_NewOwner(extSurface *Self, struct acNewOwner *Args) else Self->ParentID = 0; } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR SURFACE_NewObject(extSurface *Self, APTR Void) +static ERR SURFACE_NewObject(extSurface *Self, APTR Void) { Self->LeftLimit = -1000000000; Self->RightLimit = -1000000000; @@ -1911,7 +1901,7 @@ static ERROR SURFACE_NewObject(extSurface *Self, APTR Void) Self->Opacity = 255; Self->RootID = Self->UID; Self->WindowType = glpWindowType; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1934,13 +1924,13 @@ Search *********************************************************************************************************************/ -static ERROR SURFACE_RemoveCallback(extSurface *Self, struct drwRemoveCallback *Args) +static ERR SURFACE_RemoveCallback(extSurface *Self, struct drwRemoveCallback *Args) { pf::Log log; OBJECTPTR context = NULL; if (Args) { - if ((Args->Callback) and (Args->Callback->Type IS CALL_STDC)) { + if ((Args->Callback) and (Args->Callback->isC())) { context = (OBJECTPTR)Args->Callback->StdC.Context; log.trace("Context: %d, Routine %p, Current Total: %d", context->UID, Args->Callback->StdC.Routine, Self->CallbackCount); } @@ -1950,9 +1940,9 @@ static ERROR SURFACE_RemoveCallback(extSurface *Self, struct drwRemoveCallback * if (!context) context = GetParentContext(); - if (!Self->Callback) return ERR_Okay; + if (!Self->Callback) return ERR::Okay; - if ((!Args) or (!Args->Callback) or (Args->Callback->Type IS CALL_NONE)) { + if ((!Args) or (!Args->Callback) or (!Args->Callback->defined())) { // Remove everything relating to this context if no callback was specified. LONG i; @@ -1965,10 +1955,10 @@ static ERROR SURFACE_RemoveCallback(extSurface *Self, struct drwRemoveCallback * if (shrink) Self->Callback[i+shrink] = Self->Callback[i]; } Self->CallbackCount += shrink; - return ERR_Okay; + return ERR::Okay; } - if (Args->Callback->Type IS CALL_SCRIPT) { + if (Args->Callback->isScript()) { UnsubscribeAction(Args->Callback->Script.Script, AC_Free); } @@ -1978,11 +1968,11 @@ static ERROR SURFACE_RemoveCallback(extSurface *Self, struct drwRemoveCallback * for (i=0; i < Self->CallbackCount; i++) { //log.msg(" %d: #%d, Routine %p", i, Self->Callback[i].Object->UID, Self->Callback[i].Function.StdC.Routine); - if ((Self->Callback[i].Function.Type IS CALL_STDC) and + if ((Self->Callback[i].Function.isC()) and (Self->Callback[i].Function.StdC.Context IS context) and (Self->Callback[i].Function.StdC.Routine IS Args->Callback->StdC.Routine)) break; - if ((Self->Callback[i].Function.Type IS CALL_SCRIPT) and + if ((Self->Callback[i].Function.isScript()) and (Self->Callback[i].Function.Script.Script IS context) and (Self->Callback[i].Function.Script.ProcedureID IS Args->Callback->Script.ProcedureID)) break; } @@ -1993,12 +1983,12 @@ static ERROR SURFACE_RemoveCallback(extSurface *Self, struct drwRemoveCallback * i++; } Self->CallbackCount--; - return ERR_Okay; + return ERR::Okay; } else { if (Args->Callback->Type IS CALL_STDC) log.warning("Unable to find callback for #%d, routine %p", context->UID, Args->Callback->StdC.Routine); else log.warning("Unable to find callback for #%d", context->UID); - return ERR_Search; + return ERR::Search; } } @@ -2034,15 +2024,15 @@ AccessMemory: Unable to access internal surface list. *********************************************************************************************************************/ -static ERROR SURFACE_ResetDimensions(extSurface *Self, struct drwResetDimensions *Args) +static ERR SURFACE_ResetDimensions(extSurface *Self, struct drwResetDimensions *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); log.branch("%.0f,%.0f %.0fx%.0f %.0fx%.0f, Flags: $%.8x", Args->X, Args->Y, Args->XOffset, Args->YOffset, Args->Width, Args->Height, Args->Dimensions); - if (!Args->Dimensions) return log.warning(ERR_NullArgs); + if (!Args->Dimensions) return log.warning(ERR::NullArgs); LONG dimensions = Args->Dimensions; @@ -2057,22 +2047,22 @@ static ERROR SURFACE_ResetDimensions(extSurface *Self, struct drwResetDimensions //gfxForbidDrawing(); - if (dimensions & DMF_RELATIVE_X) SetField(Self, FID_X|TDOUBLE|TREL, Args->X); + if (dimensions & DMF_SCALED_X) SetField(Self, FID_X|TDOUBLE|TSCALE, Args->X); else if (dimensions & DMF_FIXED_X) SetField(Self, FID_X|TDOUBLE, Args->X); - if (dimensions & DMF_RELATIVE_Y) SetField(Self, FID_Y|TDOUBLE|TREL, Args->Y); + if (dimensions & DMF_SCALED_Y) SetField(Self, FID_Y|TDOUBLE|TSCALE, Args->Y); else if (dimensions & DMF_FIXED_Y) SetField(Self, FID_Y|TDOUBLE, Args->Y); - if (dimensions & DMF_RELATIVE_X_OFFSET) SetField(Self, FID_XOffset|TDOUBLE|TREL, Args->XOffset); + if (dimensions & DMF_SCALED_X_OFFSET) SetField(Self, FID_XOffset|TDOUBLE|TSCALE, Args->XOffset); else if (dimensions & DMF_FIXED_X_OFFSET) SetField(Self, FID_XOffset|TDOUBLE, Args->XOffset); - if (dimensions & DMF_RELATIVE_Y_OFFSET) SetField(Self, FID_YOffset|TDOUBLE|TREL, Args->YOffset); + if (dimensions & DMF_SCALED_Y_OFFSET) SetField(Self, FID_YOffset|TDOUBLE|TSCALE, Args->YOffset); else if (dimensions & DMF_FIXED_Y_OFFSET) SetField(Self, FID_YOffset|TDOUBLE, Args->YOffset); - if (dimensions & DMF_RELATIVE_HEIGHT) SetField(Self, FID_Height|TDOUBLE|TREL, Args->Height); + if (dimensions & DMF_SCALED_HEIGHT) SetField(Self, FID_Height|TDOUBLE|TSCALE, Args->Height); else if (dimensions & DMF_FIXED_HEIGHT) SetField(Self, FID_Height|TDOUBLE, Args->Height); - if (dimensions & DMF_RELATIVE_WIDTH) SetField(Self, FID_Width|TDOUBLE|TREL, Args->Width); + if (dimensions & DMF_SCALED_WIDTH) SetField(Self, FID_Width|TDOUBLE|TSCALE, Args->Width); else if (dimensions & DMF_FIXED_WIDTH) SetField(Self, FID_Width|TDOUBLE, Args->Width); //gfxPermitDrawing(); @@ -2095,7 +2085,7 @@ static ERROR SURFACE_ResetDimensions(extSurface *Self, struct drwResetDimensions _expose_surface(Self->ParentID, glSurfaces, index, nx, ny, nx2-nx, ny2-ny, EXF::NIL); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2120,25 +2110,24 @@ Okay *********************************************************************************************************************/ -static ERROR SURFACE_ScheduleRedraw(extSurface *Self, APTR Void) +static ERR SURFACE_ScheduleRedraw(extSurface *Self, APTR Void) { // TODO Currently defaults to 60FPS, we should get the correct FPS from the Display object. - #define FPS 60.0 + const DOUBLE FPS = 60.0; - if (Self->RedrawScheduled) return ERR_Okay; + if (Self->RedrawScheduled) return ERR::Okay; if (Self->RedrawTimer) { - Self->RedrawScheduled = TRUE; - return ERR_Okay; + Self->RedrawScheduled = true; + return ERR::Okay; } - auto call = make_function_stdc(redraw_timer); - if (!SubscribeTimer(1.0/FPS, &call, &Self->RedrawTimer)) { - Self->RedrawCountdown = FPS * 30; + if (SubscribeTimer(1.0 / FPS, FUNCTION(redraw_timer), &Self->RedrawTimer) IS ERR::Okay) { + Self->RedrawCountdown = FPS * 30.0; Self->RedrawScheduled = TRUE; - return ERR_Okay; + return ERR::Okay; } - else return ERR_Failed; + else return ERR::Failed; } /********************************************************************************************************************* @@ -2157,12 +2146,12 @@ the user's preferred default file format is used. *********************************************************************************************************************/ -static ERROR SURFACE_SaveImage(extSurface *Self, struct acSaveImage *Args) +static ERR SURFACE_SaveImage(extSurface *Self, struct acSaveImage *Args) { pf::Log log; LONG j, level; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); log.branch(); @@ -2171,21 +2160,21 @@ static ERROR SURFACE_SaveImage(extSurface *Self, struct acSaveImage *Args) CLASSID class_id = (!Args->ClassID) ? ID_PICTURE: Args->ClassID; objPicture *picture; - if (!NewObject(class_id, &picture)) { + if (NewObject(class_id, &picture) IS ERR::Okay) { picture->setFlags(PCF::NEW); picture->Bitmap->setWidth(Self->Width); picture->Bitmap->setHeight(Self->Height); objDisplay *display; objBitmap *video_bmp; - if (!access_video(Self->DisplayID, &display, &video_bmp)) { + if (access_video(Self->DisplayID, &display, &video_bmp) IS ERR::Okay) { picture->Bitmap->setBitsPerPixel(video_bmp->BitsPerPixel); picture->Bitmap->setBytesPerPixel(video_bmp->BytesPerPixel); picture->Bitmap->setType(video_bmp->Type); release_video(display); } - if (!InitObject(picture)) { + if (InitObject(picture) IS ERR::Okay) { // Scan through the surface list and copy each buffer to our picture const std::lock_guard lock(glSurfaceLock); @@ -2214,16 +2203,16 @@ static ERROR SURFACE_SaveImage(extSurface *Self, struct acSaveImage *Args) } } - if (!Action(AC_SaveImage, picture, Args)) { // Save the picture to disk + if (Action(AC_SaveImage, picture, Args) IS ERR::Okay) { // Save the picture to disk FreeResource(picture); - return ERR_Okay; + return ERR::Okay; } } FreeResource(picture); - return log.warning(ERR_Failed); + return log.warning(ERR::Failed); } - else return log.warning(ERR_NewObject); + else return log.warning(ERR::NewObject); } /********************************************************************************************************************* @@ -2245,9 +2234,9 @@ listening for the Scroll action on the surface. *********************************************************************************************************************/ -static ERROR SURFACE_Scroll(extSurface *Self, struct acScroll *Args) +static ERR SURFACE_Scroll(extSurface *Self, struct acScroll *Args) { - if (!Args) return ERR_NullArgs; + if (!Args) return ERR::NullArgs; if ((Self->Flags & RNF::SCROLL_CONTENT) != RNF::NIL) { if ((Args->DeltaX >= 1) or (Args->DeltaX <= -1) or (Args->DeltaY >= 1) or (Args->DeltaY <= -1)) { @@ -2266,7 +2255,7 @@ static ERROR SURFACE_Scroll(extSurface *Self, struct acScroll *Args) } } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2275,9 +2264,9 @@ ScrollToPoint: Moves the content of a surface object to a specific point. -END- *********************************************************************************************************************/ -static ERROR SURFACE_ScrollToPoint(extSurface *Self, struct acScrollToPoint *Args) +static ERR SURFACE_ScrollToPoint(extSurface *Self, struct acScrollToPoint *Args) { - if (!Args) return ERR_NullArgs; + if (!Args) return ERR::NullArgs; if ((Self->Flags & RNF::SCROLL_CONTENT) != RNF::NIL) { const std::lock_guard lock(glSurfaceLock); @@ -2298,7 +2287,7 @@ static ERROR SURFACE_ScrollToPoint(extSurface *Self, struct acScrollToPoint *Arg for (auto &id : surfaces) QueueAction(AC_MoveToPoint, id, &move); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2318,15 +2307,15 @@ NullArgs *********************************************************************************************************************/ -static ERROR SURFACE_SetOpacity(extSurface *Self, struct drwSetOpacity *Args) +static ERR SURFACE_SetOpacity(extSurface *Self, struct drwSetOpacity *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); if (Self->BitmapOwnerID != Self->UID) { log.warning("Opacity cannot be set on a surface that does not own its bitmap."); - return ERR_NoSupport; + return ERR::NoSupport; } DOUBLE value; @@ -2343,7 +2332,7 @@ static ERROR SURFACE_SetOpacity(extSurface *Self, struct drwSetOpacity *Args) if (Self->visible()) QueueAction(MT_DrwInvalidateRegion, Self->UID); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -2352,31 +2341,31 @@ Show: Shows a surface object on the display. -END- *********************************************************************************************************************/ -static ERROR SURFACE_Show(extSurface *Self, APTR Void) +static ERR SURFACE_Show(extSurface *Self, APTR Void) { pf::Log log; log.traceBranch("%dx%d, %dx%d, Parent: %d, Modal: %d", Self->X, Self->Y, Self->Width, Self->Height, Self->ParentID, Self->Modal); - LONG notified; + ERR notified; if (Self->visible()) { - notified = ERF_Notified; - return ERR_Okay|ERF_Notified; + notified = ERR::Notified; + return ERR::Okay|ERR::Notified; } - else notified = 0; + else notified = ERR::NIL; if (!Self->ParentID) { - if (!acShow(Self->DisplayID)) { + if (acShow(Self->DisplayID) IS ERR::Okay) { Self->Flags |= RNF::VISIBLE; if (Self->hasFocus()) acFocus(Self->DisplayID); } - else return log.warning(ERR_Failed); + else return log.warning(ERR::Failed); } else Self->Flags |= RNF::VISIBLE; if (Self->Modal) Self->PrevModalID = gfxSetModalSurface(Self->UID); - if (!notified) { + if (notified IS ERR::NIL) { UpdateSurfaceField(Self, &SurfaceRecord::Flags, Self->Flags); gfxRedrawSurface(Self->UID, 0, 0, Self->Width, Self->Height, IRF::RELATIVE); @@ -2385,12 +2374,12 @@ static ERROR SURFACE_Show(extSurface *Self, APTR Void) refresh_pointer(Self); - return ERR_Okay|notified; + return ERR::Okay|notified; } //******************************************************************************************************************** -static ERROR redraw_timer(extSurface *Self, LARGE Elapsed, LARGE CurrentTime) +static ERR redraw_timer(extSurface *Self, LARGE Elapsed, LARGE CurrentTime) { if (Self->RedrawScheduled) { Self->RedrawScheduled = false; // Done before Draw() because it tests this field. @@ -2403,11 +2392,11 @@ static ERROR redraw_timer(extSurface *Self, LARGE Elapsed, LARGE CurrentTime) if (Self->RedrawCountdown > 0) Self->RedrawCountdown--; if (!Self->RedrawCountdown) { Self->RedrawTimer = NULL; - return ERR_Terminate; + return ERR::Terminate; } } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -2470,7 +2459,7 @@ static void draw_region(extSurface *Self, extSurface *Parent, extBitmap *Bitmap) //******************************************************************************************************************** -static ERROR consume_input_events(const InputEvent *Events, LONG Handle) +static ERR consume_input_events(const InputEvent *Events, LONG Handle) { pf::Log log(__FUNCTION__); @@ -2558,7 +2547,7 @@ static ERROR consume_input_events(const InputEvent *Events, LONG Handle) glAnchorX = event->X; glAnchorY = event->Y; - if (!gfxLockCursor(Self->UID)) Self->DragStatus = DRAG::ANCHOR; + if (gfxLockCursor(Self->UID) IS ERR::Okay) Self->DragStatus = DRAG::ANCHOR; else Self->DragStatus = DRAG::NORMAL; } } @@ -2571,7 +2560,7 @@ static ERROR consume_input_events(const InputEvent *Events, LONG Handle) } } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -2625,10 +2614,10 @@ static const FieldArray clSurfaceFields[] = { { "BottomLimit", FDF_LONG|FDF_RW, NULL, SET_BottomLimit }, { "Display", FDF_OBJECTID|FDF_R, NULL, NULL, ID_DISPLAY }, { "Flags", FDF_LONGFLAGS|FDF_RW, NULL, SET_Flags, &clSurfaceFlags }, - { "X", FD_VARIABLE|FDF_LONG|FDF_PERCENTAGE|FDF_RW, GET_XCoord, SET_XCoord }, - { "Y", FD_VARIABLE|FDF_LONG|FDF_PERCENTAGE|FDF_RW, GET_YCoord, SET_YCoord }, - { "Width", FD_VARIABLE|FDF_LONG|FDF_PERCENTAGE|FDF_RW, GET_Width, SET_Width }, - { "Height", FD_VARIABLE|FDF_LONG|FDF_PERCENTAGE|FDF_RW, GET_Height, SET_Height }, + { "X", FD_VARIABLE|FDF_LONG|FDF_SCALED|FDF_RW, GET_XCoord, SET_XCoord }, + { "Y", FD_VARIABLE|FDF_LONG|FDF_SCALED|FDF_RW, GET_YCoord, SET_YCoord }, + { "Width", FD_VARIABLE|FDF_LONG|FDF_SCALED|FDF_RW, GET_Width, SET_Width }, + { "Height", FD_VARIABLE|FDF_LONG|FDF_SCALED|FDF_RW, GET_Height, SET_Height }, { "RootLayer", FDF_OBJECTID|FDF_RW, NULL, SET_RootLayer }, { "Align", FDF_LONGFLAGS|FDF_RW, NULL, NULL, &clSurfaceAlign }, { "Dimensions", FDF_LONG|FDF_RW, NULL, SET_Dimensions, &clSurfaceDimensions }, @@ -2657,14 +2646,14 @@ static const FieldArray clSurfaceFields[] = { { "WindowType", FDF_VIRTUAL|FDF_LONG|FDF_LOOKUP|FDF_RW, GET_WindowType, SET_WindowType, &clWindowType }, { "WindowHandle", FDF_VIRTUAL|FDF_POINTER|FDF_RW, GET_WindowHandle, SET_WindowHandle }, // Variable fields - { "XOffset", FDF_VIRTUAL|FDF_VARIABLE|FDF_LONG|FDF_PERCENTAGE|FDF_RW, GET_XOffset, SET_XOffset }, - { "YOffset", FDF_VIRTUAL|FDF_VARIABLE|FDF_LONG|FDF_PERCENTAGE|FDF_RW, GET_YOffset, SET_YOffset }, + { "XOffset", FDF_VIRTUAL|FDF_VARIABLE|FDF_LONG|FDF_SCALED|FDF_RW, GET_XOffset, SET_XOffset }, + { "YOffset", FDF_VIRTUAL|FDF_VARIABLE|FDF_LONG|FDF_SCALED|FDF_RW, GET_YOffset, SET_YOffset }, END_FIELD }; //******************************************************************************************************************** -ERROR create_surface_class(void) +ERR create_surface_class(void) { clSurface = objMetaClass::create::global( fl::ClassVersion(VER_SURFACE), @@ -2676,5 +2665,5 @@ ERROR create_surface_class(void) fl::Size(sizeof(extSurface)), fl::Path(MOD_PATH)); - return clSurface ? ERR_Okay : ERR_AddClass; + return clSurface ? ERR::Okay : ERR::AddClass; } diff --git a/src/display/class_surface/surface_def.c b/src/display/class_surface/surface_def.c index d56637c58..89abed743 100644 --- a/src/display/class_surface/surface_def.c +++ b/src/display/class_surface/surface_def.c @@ -50,43 +50,43 @@ static const struct FieldDef clSurfaceAlign[] = { }; static const struct FieldDef clSurfaceDimensions[] = { - { "RelativeX", 0x00000001 }, - { "RelativeY", 0x00000002 }, + { "ScaledX", 0x00000001 }, + { "ScaledY", 0x00000002 }, { "FixedX", 0x00000004 }, { "X", 0x00000005 }, { "FixedY", 0x00000008 }, { "Y", 0x0000000a }, - { "RelativeXOffset", 0x00000010 }, - { "RelativeYOffset", 0x00000020 }, + { "ScaledXOffset", 0x00000010 }, + { "ScaledYOffset", 0x00000020 }, { "FixedXOffset", 0x00000040 }, { "XOffset", 0x00000050 }, { "FixedYOffset", 0x00000080 }, { "YOffset", 0x000000a0 }, { "FixedHeight", 0x00000100 }, { "FixedWidth", 0x00000200 }, - { "RelativeHeight", 0x00000400 }, + { "ScaledHeight", 0x00000400 }, { "Height", 0x00000500 }, { "HeightFlags", 0x000005a0 }, { "VerticalFlags", 0x000005aa }, - { "RelativeWidth", 0x00000800 }, + { "ScaledWidth", 0x00000800 }, { "Width", 0x00000a00 }, { "WidthFlags", 0x00000a50 }, { "HorizontalFlags", 0x00000a55 }, { "FixedDepth", 0x00001000 }, - { "RelativeDepth", 0x00002000 }, + { "ScaledDepth", 0x00002000 }, { "FixedZ", 0x00004000 }, - { "RelativeZ", 0x00008000 }, - { "RelativeRadiusX", 0x00010000 }, + { "ScaledZ", 0x00008000 }, + { "ScaledRadiusX", 0x00010000 }, { "FixedRadiusX", 0x00020000 }, - { "RelativeCenterX", 0x00040000 }, - { "RelativeCenterY", 0x00080000 }, + { "ScaledCenterX", 0x00040000 }, + { "ScaledCenterY", 0x00080000 }, { "FixedCenterX", 0x00100000 }, { "FixedCenterY", 0x00200000 }, { "StatusChangeH", 0x00400000 }, { "StatusChangeV", 0x00800000 }, { "StatusChange", 0x00c00000 }, - { "RelativeRadiusY", 0x01000000 }, - { "RelativeRadius", 0x01010000 }, + { "ScaledRadiusY", 0x01000000 }, + { "ScaledRadius", 0x01010000 }, { "FixedRadiusY", 0x02000000 }, { "FixedRadius", 0x02020000 }, { NULL, 0 } diff --git a/src/display/class_surface/surface_dimensions.cpp b/src/display/class_surface/surface_dimensions.cpp index 8a7d2ac9c..e14882155 100644 --- a/src/display/class_surface/surface_dimensions.cpp +++ b/src/display/class_surface/surface_dimensions.cpp @@ -11,19 +11,19 @@ It is possible to set this field, but only after initialisation of the surface o *********************************************************************************************************************/ -static ERROR GET_AbsX(extSurface *Self, LONG *Value) +static ERR GET_AbsX(extSurface *Self, LONG *Value) { const std::lock_guard lock(glSurfaceLock); LONG i; if ((i = find_surface_list(Self)) != -1) { *Value = glSurfaces[i].Left; - return ERR_Okay; + return ERR::Okay; } - else return ERR_Search; + else return ERR::Search; } -static ERROR SET_AbsX(extSurface *Self, LONG Value) +static ERR SET_AbsX(extSurface *Self, LONG Value) { pf::Log log; @@ -34,11 +34,11 @@ static ERROR SET_AbsX(extSurface *Self, LONG Value) if ((parent = find_parent_list(glSurfaces, Self)) != -1) { x = Value - glSurfaces[parent].Left; move_layer(Self, x, Self->Y); - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_Search); + else return log.warning(ERR::Search); } - else return log.warning(ERR_NotInitialised); + else return log.warning(ERR::NotInitialised); } /********************************************************************************************************************* @@ -53,19 +53,19 @@ It is possible to set this field, but only after initialisation of the surface o *********************************************************************************************************************/ -static ERROR GET_AbsY(extSurface *Self, LONG *Value) +static ERR GET_AbsY(extSurface *Self, LONG *Value) { const std::lock_guard lock(glSurfaceLock); LONG i; if ((i = find_surface_list(Self)) != -1) { *Value = glSurfaces[i].Top; - return ERR_Okay; + return ERR::Okay; } - else return ERR_Search; + else return ERR::Search; } -static ERROR SET_AbsY(extSurface *Self, LONG Value) +static ERR SET_AbsY(extSurface *Self, LONG Value) { pf::Log log; @@ -76,12 +76,12 @@ static ERROR SET_AbsY(extSurface *Self, LONG Value) if ((parent = find_parent_list(glSurfaces, Self)) != -1) { y = Value - glSurfaces[parent].Top; move_layer(Self, Self->X, y); - return ERR_Okay; + return ERR::Okay; } - return log.warning(ERR_Search); + return log.warning(ERR::Search); } - else return log.warning(ERR_NotInitialised); + else return log.warning(ERR::NotInitialised); } /********************************************************************************************************************* @@ -99,10 +99,10 @@ Bottom: Returns the bottom-most coordinate of a surface object (Y + Height). *********************************************************************************************************************/ -static ERROR GET_Bottom(extSurface *Self, LONG *Bottom) +static ERR GET_Bottom(extSurface *Self, LONG *Bottom) { *Bottom = Self->Y + Self->Height; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -119,10 +119,10 @@ setting the coordinate fields directly (which can be useful in certain cases). *********************************************************************************************************************/ -static ERROR SET_BottomLimit(extSurface *Self, LONG Value) +static ERR SET_BottomLimit(extSurface *Self, LONG Value) { Self->BottomLimit = Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -139,11 +139,11 @@ By default, all margins are set to zero when a new surface object is created. *********************************************************************************************************************/ -static ERROR SET_BottomMargin(extSurface *Self, LONG Value) +static ERR SET_BottomMargin(extSurface *Self, LONG Value) { if (Value < 0) Self->BottomMargin = -Value; else Self->BottomMargin = Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -157,16 +157,16 @@ are in use, and whether the values are fixed or relative. It is strongly recommended that this field is never set manually, because the flags are automatically managed for the client when setting fields such as #X and #Width. If circumstances require manual configuration, take care to ensure -that the flags do not conflict. For instance, `FIXED_X` and `RELATIVE_X` cannot be paired, nor could `FIXED_X`, +that the flags do not conflict. For instance, `FIXED_X` and `SCALED_X` cannot be paired, nor could `FIXED_X`, `FIXED_XOFFSET` and `FIXED_WIDTH` simultaneously. *********************************************************************************************************************/ -static ERROR SET_Dimensions(extSurface *Self, LONG Value) +static ERR SET_Dimensions(extSurface *Self, LONG Value) { SURFACEINFO *parent; - if (!gfxGetSurfaceInfo(Self->ParentID, &parent)) { + if (gfxGetSurfaceInfo(Self->ParentID, &parent) IS ERR::Okay) { if (Value & DMF_Y) { if ((Value & DMF_HEIGHT) or (Value & DMF_Y_OFFSET)) { Self->Dimensions &= ~DMF_VERTICAL_FLAGS; @@ -191,34 +191,34 @@ static ERROR SET_Dimensions(extSurface *Self, LONG Value) struct acRedimension resize; if (Self->Dimensions & DMF_FIXED_X) resize.X = Self->X; - else if (Self->Dimensions & DMF_RELATIVE_X) resize.X = (parent->Width * F2I(Self->XPercent)); + else if (Self->Dimensions & DMF_SCALED_X) resize.X = (parent->Width * F2I(Self->XPercent)); else if (Self->Dimensions & DMF_FIXED_X_OFFSET) resize.X = parent->Width - Self->XOffset; - else if (Self->Dimensions & DMF_RELATIVE_X_OFFSET) resize.X = parent->Width - ((parent->Width * F2I(Self->XOffsetPercent))); + else if (Self->Dimensions & DMF_SCALED_X_OFFSET) resize.X = parent->Width - ((parent->Width * F2I(Self->XOffsetPercent))); else resize.X = 0; if (Self->Dimensions & DMF_FIXED_Y) resize.Y = Self->Y; - else if (Self->Dimensions & DMF_RELATIVE_Y) resize.Y = (parent->Height * F2I(Self->YPercent)); + else if (Self->Dimensions & DMF_SCALED_Y) resize.Y = (parent->Height * F2I(Self->YPercent)); else if (Self->Dimensions & DMF_FIXED_Y_OFFSET) resize.Y = parent->Height - Self->YOffset; - else if (Self->Dimensions & DMF_RELATIVE_Y_OFFSET) resize.Y = parent->Height - ((parent->Height * F2I(Self->YOffsetPercent))); + else if (Self->Dimensions & DMF_SCALED_Y_OFFSET) resize.Y = parent->Height - ((parent->Height * F2I(Self->YOffsetPercent))); else resize.Y = 0; if (Self->Dimensions & DMF_FIXED_WIDTH) resize.Width = Self->Width; - else if (Self->Dimensions & DMF_RELATIVE_WIDTH) resize.Width = (parent->Width * F2I(Self->WidthPercent)); + else if (Self->Dimensions & DMF_SCALED_WIDTH) resize.Width = (parent->Width * F2I(Self->WidthPercent)); else { - if (Self->Dimensions & DMF_RELATIVE_X_OFFSET) resize.Width = parent->Width - (parent->Width * F2I(Self->XOffsetPercent)); + if (Self->Dimensions & DMF_SCALED_X_OFFSET) resize.Width = parent->Width - (parent->Width * F2I(Self->XOffsetPercent)); else resize.Width = parent->Width - Self->XOffset; - if (Self->Dimensions & DMF_RELATIVE_X) resize.Width = resize.Width - ((parent->Width * F2I(Self->XPercent))); + if (Self->Dimensions & DMF_SCALED_X) resize.Width = resize.Width - ((parent->Width * F2I(Self->XPercent))); else resize.Width = resize.Width - Self->X; } if (Self->Dimensions & DMF_FIXED_HEIGHT) resize.Height = Self->Height; - else if (Self->Dimensions & DMF_RELATIVE_HEIGHT) resize.Height = (parent->Height * F2I(Self->HeightPercent)); + else if (Self->Dimensions & DMF_SCALED_HEIGHT) resize.Height = (parent->Height * F2I(Self->HeightPercent)); else { - if (Self->Dimensions & DMF_RELATIVE_Y_OFFSET) resize.Height = parent->Height - (parent->Height * F2I(Self->YOffsetPercent)); + if (Self->Dimensions & DMF_SCALED_Y_OFFSET) resize.Height = parent->Height - (parent->Height * F2I(Self->YOffsetPercent)); else resize.Height = parent->Height - Self->YOffset; - if (Self->Dimensions & DMF_RELATIVE_Y) resize.Height = resize.Height - ((parent->Height * F2I(Self->YPercent))); + if (Self->Dimensions & DMF_SCALED_Y) resize.Height = resize.Height - ((parent->Height * F2I(Self->YPercent))); else resize.Height = resize.Height - Self->Y; } @@ -226,9 +226,9 @@ static ERROR SET_Dimensions(extSurface *Self, LONG Value) resize.Depth = 0; Action(AC_Redimension, Self, &resize); - return ERR_Okay; + return ERR::Okay; } - else return ERR_Search; + else return ERR::Search; } /********************************************************************************************************************* @@ -236,11 +236,9 @@ static ERROR SET_Dimensions(extSurface *Self, LONG Value) -FIELD- Height: Defines the height of a surface object. -The height of a surface object is manipulated through this field, although you can also use the Resize() action, which -is faster if you need to set both the Width and the Height. A client can set the Height as a fixed value by default, or as -a relative value if you set the `FD_PERCENT` marker. Relative heights are always calculated in relationship to a surface -object's container, e.g. if the container is 200 pixels high and surface Height is 80%, then your surface object will -be 160 pixels high. +The height of a surface object is manipulated through this field. Alternatively, use the Resize() action to adjust the +Width and Height at the same time. A client can set the Height as a fixed value by default, or as a scaled value in +conjunction with the `FD_SCALED` flag. Scaled values are multiplied by the height of their parent container. Setting the Height while a surface object is on display causes an immediate graphical update to reflect the change. Any objects that are within the surface area will be re-drawn and resized as necessary. @@ -250,24 +248,24 @@ for pairing the Y and YOffset fields together for dynamic height adjustment. *********************************************************************************************************************/ -static ERROR GET_Height(extSurface *Self, Variable *Value) +static ERR GET_Height(extSurface *Self, Variable *Value) { - if (Value->Type & FD_PERCENTAGE) { - if (Self->Dimensions & DMF_RELATIVE_HEIGHT) { + if (Value->Type & FD_SCALED) { + if (Self->Dimensions & DMF_SCALED_HEIGHT) { Value->Double = Self->HeightPercent; Value->Large = F2I(Self->HeightPercent); - return ERR_Okay; + return ERR::Okay; } - else return ERR_Failed; + else return ERR::Failed; } else { Value->Double = Self->Height; Value->Large = Self->Height; - return ERR_Okay; + return ERR::Okay; } } -static ERROR SET_Height(extSurface *Self, Variable *Value) +static ERR SET_Height(extSurface *Self, Variable *Value) { pf::Log log; DOUBLE value; @@ -275,43 +273,43 @@ static ERROR SET_Height(extSurface *Self, Variable *Value) if (Value->Type & FD_DOUBLE) value = Value->Double; else if (Value->Type & FD_LARGE) value = Value->Large; else if (Value->Type & FD_STRING) value = StrToFloat((CSTRING)Value->Pointer); - else return log.warning(ERR_SetValueNotNumeric); + else return log.warning(ERR::SetValueNotNumeric); if (value <= 0) { - if (Self->initialised()) return ERR_InvalidDimension; + if (Self->initialised()) return ERR::InvalidDimension; else { Self->Dimensions &= ~(DMF_HEIGHT); - return ERR_Okay; + return ERR::Okay; } } if (value > 0x7fffffff) value = 0x7fffffff; - if (Value->Type & FD_PERCENTAGE) { + if (Value->Type & FD_SCALED) { if (Self->ParentID) { extSurface *parent; - if (!AccessObject(Self->ParentID, 500, &parent)) { + if (AccessObject(Self->ParentID, 500, &parent) IS ERR::Okay) { Self->HeightPercent = value; - Self->Dimensions = (Self->Dimensions & ~DMF_FIXED_HEIGHT) | DMF_RELATIVE_HEIGHT; + Self->Dimensions = (Self->Dimensions & ~DMF_FIXED_HEIGHT) | DMF_SCALED_HEIGHT; resize_layer(Self, Self->X, Self->Y, 0, parent->Height * value, 0, 0, 0, 0, 0); ReleaseObject(parent); } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } else { Self->HeightPercent = value; - Self->Dimensions = (Self->Dimensions & ~DMF_FIXED_HEIGHT) | DMF_RELATIVE_HEIGHT; + Self->Dimensions = (Self->Dimensions & ~DMF_FIXED_HEIGHT) | DMF_SCALED_HEIGHT; } } else { if (value != Self->Height) resize_layer(Self, Self->X, Self->Y, 0, value, 0, 0, 0, 0, 0); - Self->Dimensions = (Self->Dimensions & ~DMF_RELATIVE_HEIGHT) | DMF_FIXED_HEIGHT; + Self->Dimensions = (Self->Dimensions & ~DMF_SCALED_HEIGHT) | DMF_FIXED_HEIGHT; // If the offset flags are used, adjust the vertical position - if (Self->Dimensions & DMF_RELATIVE_Y_OFFSET) { + if (Self->Dimensions & DMF_SCALED_Y_OFFSET) { Variable var; - var.Type = FD_DOUBLE|FD_PERCENTAGE; + var.Type = FD_DOUBLE|FD_SCALED; var.Double = Self->YOffsetPercent; SET_YOffset(Self, &var); } @@ -321,7 +319,7 @@ static ERROR SET_Height(extSurface *Self, Variable *Value) } } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -337,18 +335,18 @@ height. *********************************************************************************************************************/ -static ERROR GET_InsideHeight(extSurface *Self, LONG *Value) +static ERR GET_InsideHeight(extSurface *Self, LONG *Value) { *Value = Self->Height - Self->TopMargin - Self->BottomMargin; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_InsideHeight(extSurface *Self, LONG Value) +static ERR SET_InsideHeight(extSurface *Self, LONG Value) { LONG height = Value + Self->TopMargin + Self->BottomMargin; if (height < Self->MinHeight) height = Self->MinHeight; Self->setHeight(height); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -363,18 +361,18 @@ If the LeftMargin and RightMargin fields are not set, the returned value will be *********************************************************************************************************************/ -static ERROR GET_InsideWidth(extSurface *Self, LONG *Value) +static ERR GET_InsideWidth(extSurface *Self, LONG *Value) { *Value = Self->Width - Self->LeftMargin - Self->RightMargin; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_InsideWidth(extSurface *Self, LONG Value) +static ERR SET_InsideWidth(extSurface *Self, LONG Value) { LONG width = Value + Self->LeftMargin + Self->RightMargin; if (width < Self->MinWidth) width = Self->MinWidth; Self->setWidth(width); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -391,10 +389,10 @@ setting the coordinate fields directly. *********************************************************************************************************************/ -static ERROR SET_LeftLimit(extSurface *Self, LONG Value) +static ERR SET_LeftLimit(extSurface *Self, LONG Value) { Self->LeftLimit = Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -421,7 +419,7 @@ to the inside-height of the surface area, thus the overall maximum height will i *********************************************************************************************************************/ -static ERROR SET_MaxHeight(extSurface *Self, LONG Value) +static ERR SET_MaxHeight(extSurface *Self, LONG Value) { Self->MaxHeight = Value; @@ -436,7 +434,7 @@ static ERROR SET_MaxHeight(extSurface *Self, LONG Value) ActionMsg(MT_GfxSizeHints, Self->DisplayID, &hints); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -453,7 +451,7 @@ values. *********************************************************************************************************************/ -static ERROR SET_MaxWidth(extSurface *Self, LONG Value) +static ERR SET_MaxWidth(extSurface *Self, LONG Value) { Self->MaxWidth = Value; @@ -468,7 +466,7 @@ static ERROR SET_MaxWidth(extSurface *Self, LONG Value) ActionMsg(MT_GfxSizeHints, Self->DisplayID, &hints); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -484,7 +482,7 @@ It is possible to circumvent the MinHeight by setting the #Height field directly *********************************************************************************************************************/ -static ERROR SET_MinHeight(extSurface *Self, LONG Value) +static ERR SET_MinHeight(extSurface *Self, LONG Value) { Self->MinHeight = Value; if (Self->MinHeight < 1) Self->MinHeight = 1; @@ -500,7 +498,7 @@ static ERROR SET_MinHeight(extSurface *Self, LONG Value) ActionMsg(MT_GfxSizeHints, Self->DisplayID, &hints); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -516,7 +514,7 @@ It is possible to circumvent the MinWidth by setting the Width field directly. *********************************************************************************************************************/ -static ERROR SET_MinWidth(extSurface *Self, LONG Value) +static ERR SET_MinWidth(extSurface *Self, LONG Value) { Self->MinWidth = Value; if (Self->MinWidth < 1) Self->MinWidth = 1; @@ -532,7 +530,7 @@ static ERROR SET_MinWidth(extSurface *Self, LONG Value) ActionMsg(MT_GfxSizeHints, Self->DisplayID, &hints); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -542,10 +540,10 @@ Right: Returns the right-most coordinate of a surface object (X + Width). *********************************************************************************************************************/ -static ERROR GET_Right(extSurface *Self, LONG *Value) +static ERR GET_Right(extSurface *Self, LONG *Value) { *Value = Self->X + Self->Width; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -562,10 +560,10 @@ setting the coordinate fields directly (which can be useful in certain cases). *********************************************************************************************************************/ -static ERROR SET_RightLimit(extSurface *Self, LONG Value) +static ERR SET_RightLimit(extSurface *Self, LONG Value) { Self->RightLimit = Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -582,11 +580,11 @@ By default, all margins are set to zero when a new surface object is created. *********************************************************************************************************************/ -static ERROR SET_RightMargin(extSurface *Self, LONG Value) +static ERR SET_RightMargin(extSurface *Self, LONG Value) { if (Value < 0) Self->RightMargin = -Value; else Self->RightMargin = Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -603,10 +601,10 @@ setting the coordinate fields directly (which can be useful in certain cases). *********************************************************************************************************************/ -static ERROR SET_TopLimit(extSurface *Self, LONG Value) +static ERR SET_TopLimit(extSurface *Self, LONG Value) { Self->TopLimit = Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -634,22 +632,22 @@ If none of the surface area is visible then zero is returned. The result is nev *********************************************************************************************************************/ -static ERROR GET_VisibleHeight(extSurface *Self, LONG *Value) +static ERR GET_VisibleHeight(extSurface *Self, LONG *Value) { if (!Self->ParentID) { *Value = Self->Height; - return ERR_Okay; + return ERR::Okay; } else { const std::lock_guard lock(glSurfaceLock); WORD i; - if ((i = find_surface_list(Self)) IS -1) return ERR_Search; + if ((i = find_surface_list(Self)) IS -1) return ERR::Search; auto clip = glSurfaces[i].area(); restrict_region_to_parents(glSurfaces, i, clip, false); *Value = clip.height(); - return ERR_Okay; + return ERR::Okay; } } @@ -668,22 +666,22 @@ If none of the surface area is visible then zero is returned. The result is nev *********************************************************************************************************************/ -static ERROR GET_VisibleWidth(extSurface *Self, LONG *Value) +static ERR GET_VisibleWidth(extSurface *Self, LONG *Value) { if (!Self->ParentID) { *Value = Self->Height; - return ERR_Okay; + return ERR::Okay; } else { const std::lock_guard lock(glSurfaceLock); WORD i; - if ((i = find_surface_list(Self)) IS -1) return ERR_Search; + if ((i = find_surface_list(Self)) IS -1) return ERR::Search; auto clip = glSurfaces[i].area(); restrict_region_to_parents(glSurfaces, i, clip, false); *Value = clip.width(); - return ERR_Okay; + return ERR::Okay; } } @@ -702,23 +700,23 @@ If none of the surface area is visible then zero is returned. The result is nev *********************************************************************************************************************/ -static ERROR GET_VisibleX(extSurface *Self, LONG *Value) +static ERR GET_VisibleX(extSurface *Self, LONG *Value) { if (!Self->ParentID) { *Value = Self->Height; - return ERR_Okay; + return ERR::Okay; } else { const std::lock_guard lock(glSurfaceLock); WORD i; - if ((i = find_surface_list(Self)) IS -1) return ERR_Search; + if ((i = find_surface_list(Self)) IS -1) return ERR::Search; auto clip = glSurfaces[i].area(); restrict_region_to_parents(glSurfaces, i, clip, false); *Value = clip.Left - glSurfaces[i].Left; - return ERR_Okay; + return ERR::Okay; } } @@ -737,22 +735,22 @@ If none of the surface area is visible then zero is returned. The result is nev *********************************************************************************************************************/ -static ERROR GET_VisibleY(extSurface *Self, LONG *Value) +static ERR GET_VisibleY(extSurface *Self, LONG *Value) { if (!Self->ParentID) { *Value = Self->Height; - return ERR_Okay; + return ERR::Okay; } else { const std::lock_guard lock(glSurfaceLock); WORD i; - if ((i = find_surface_list(Self)) IS -1) return ERR_Search; + if ((i = find_surface_list(Self)) IS -1) return ERR::Search; auto clip = glSurfaces[i].area(); restrict_region_to_parents(glSurfaces, i, clip, false); *Value = clip.Top - glSurfaces[i].Top; - return ERR_Okay; + return ERR::Okay; } } @@ -761,35 +759,33 @@ static ERROR GET_VisibleY(extSurface *Self, LONG *Value) -FIELD- Width: Defines the width of a surface object. -The width of a surface object is manipulated through this field, although you can also use the Resize() action, which -is faster if you need to set both the Width and the Height. A client can set the Width as a fixed value by default, or as a -relative value if you set the `FD_PERCENT` field. Relative widths are always calculated in relationship to a surface -object's container, e.g. if the container is 200 pixels wide and surface Width is 80%, then your surface object will be -160 pixels wide. +The width of a surface object is manipulated through this field. Alternatively, use the Resize() action to adjust the +Width and Height at the same time. A client can set the Width as a fixed value by default, or as a scaled value in +conjunction with the `FD_SCALED` flag. Scaled values are multiplied by the width of their parent container. Setting the Width while a surface object is on display causes an immediate graphical update to reflect the change. Any objects that are within the surface area will be re-drawn and resized as necessary. -Width values of 0 or less are illegal, and will result in an `ERR_OutOfRange` error-code. +Width values of 0 or less are illegal, and will result in an `ERR::OutOfRange` error-code. *********************************************************************************************************************/ -static ERROR GET_Width(extSurface *Self, Variable *Value) +static ERR GET_Width(extSurface *Self, Variable *Value) { if (Value->Type & FD_DOUBLE) { - if (Value->Type & FD_PERCENTAGE) { - if (Self->Dimensions & DMF_RELATIVE_WIDTH) { + if (Value->Type & FD_SCALED) { + if (Self->Dimensions & DMF_SCALED_WIDTH) { Value->Double = Self->WidthPercent; } - else return ERR_Failed; + else return ERR::Failed; } else Value->Double = Self->Width; } else Value->Large = Self->Width; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_Width(extSurface *Self, Variable *Value) +static ERR SET_Width(extSurface *Self, Variable *Value) { pf::Log log; Variable var; @@ -799,40 +795,40 @@ static ERROR SET_Width(extSurface *Self, Variable *Value) if (Value->Type & FD_DOUBLE) value = Value->Double; else if (Value->Type & FD_LARGE) value = Value->Large; else if (Value->Type & FD_STRING) value = StrToFloat((CSTRING)Value->Pointer); - else return log.warning(ERR_SetValueNotNumeric); + else return log.warning(ERR::SetValueNotNumeric); if (value <= 0) { - if (Self->initialised()) return ERR_InvalidDimension; + if (Self->initialised()) return ERR::InvalidDimension; else { Self->Dimensions &= ~(DMF_WIDTH); - return ERR_Okay; + return ERR::Okay; } } if (value > 0x7fffffff) value = 0x7fffffff; - if (Value->Type & FD_PERCENTAGE) { + if (Value->Type & FD_SCALED) { if (Self->ParentID) { - if (!AccessObject(Self->ParentID, 500, &parent)) { + if (AccessObject(Self->ParentID, 500, &parent) IS ERR::Okay) { Self->WidthPercent = value; - Self->Dimensions = (Self->Dimensions & ~DMF_FIXED_WIDTH) | DMF_RELATIVE_WIDTH; + Self->Dimensions = (Self->Dimensions & ~DMF_FIXED_WIDTH) | DMF_SCALED_WIDTH; resize_layer(Self, Self->X, Self->Y, parent->Width * value, 0, 0, 0, 0, 0, 0); ReleaseObject(parent); } - else return ERR_AccessObject; + else return ERR::AccessObject; } else { Self->WidthPercent = value; - Self->Dimensions = (Self->Dimensions & ~DMF_FIXED_WIDTH) | DMF_RELATIVE_WIDTH; + Self->Dimensions = (Self->Dimensions & ~DMF_FIXED_WIDTH) | DMF_SCALED_WIDTH; } } else { if (value != Self->Width) resize_layer(Self, Self->X, Self->Y, value, 0, 0, 0, 0, 0, 0); - Self->Dimensions = (Self->Dimensions & ~DMF_RELATIVE_WIDTH) | DMF_FIXED_WIDTH; + Self->Dimensions = (Self->Dimensions & ~DMF_SCALED_WIDTH) | DMF_FIXED_WIDTH; // If the offset flags are used, adjust the horizontal position - if (Self->Dimensions & DMF_RELATIVE_X_OFFSET) { - var.Type = FD_DOUBLE|FD_PERCENTAGE; + if (Self->Dimensions & DMF_SCALED_X_OFFSET) { + var.Type = FD_DOUBLE|FD_SCALED; var.Double = Self->XOffsetPercent; SET_XOffset(Self, &var); } @@ -842,7 +838,7 @@ static ERROR SET_Width(extSurface *Self, Variable *Value) SET_XOffset(Self, &var); } } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -851,31 +847,31 @@ static ERROR SET_Width(extSurface *Self, Variable *Value) X: Determines the horizontal position of a surface object. The horizontal position of a surface object can be set through this field. You have the choice of setting a fixed -coordinate (the default) or a relative coordinate if you use the `FD_PERCENT` flag. +coordinate (the default) or a scaled coordinate if you use the `FD_SCALED` flag. If you set the X while the surface object is on display, the position of the surface area will be updated immediately. *********************************************************************************************************************/ -static ERROR GET_XCoord(extSurface *Self, Variable *Value) +static ERR GET_XCoord(extSurface *Self, Variable *Value) { if (Value->Type & FD_DOUBLE) { - if (Value->Type & FD_PERCENTAGE) Value->Double = Self->XPercent; + if (Value->Type & FD_SCALED) Value->Double = Self->XPercent; else Value->Double = Self->X; } else if (Value->Type & FD_LARGE) { - if (Value->Type & FD_PERCENTAGE) Value->Large = F2I(Self->XPercent); + if (Value->Type & FD_SCALED) Value->Large = F2I(Self->XPercent); else Value->Large = Self->X; } else { pf::Log log; - return log.warning(ERR_FieldTypeMismatch); + return log.warning(ERR::FieldTypeMismatch); } - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_XCoord(extSurface *Self, Variable *Value) +static ERR SET_XCoord(extSurface *Self, Variable *Value) { pf::Log log; extSurface *parent; @@ -884,35 +880,35 @@ static ERROR SET_XCoord(extSurface *Self, Variable *Value) if (Value->Type & FD_DOUBLE) value = Value->Double; else if (Value->Type & FD_LARGE) value = Value->Large; else if (Value->Type & FD_STRING) value = StrToFloat((CSTRING)Value->Pointer); - else return log.warning(ERR_SetValueNotNumeric); + else return log.warning(ERR::SetValueNotNumeric); - if (Value->Type & FD_PERCENTAGE) { - Self->Dimensions = (Self->Dimensions & ~DMF_FIXED_X) | DMF_RELATIVE_X; + if (Value->Type & FD_SCALED) { + Self->Dimensions = (Self->Dimensions & ~DMF_FIXED_X) | DMF_SCALED_X; Self->XPercent = value; if (Self->ParentID) { - if (AccessObject(Self->ParentID, 500, &parent) IS ERR_Okay) { + if (AccessObject(Self->ParentID, 500, &parent) IS ERR::Okay) { move_layer(Self, parent->Width * value, Self->Y); ReleaseObject(parent); } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } } else { - Self->Dimensions = (Self->Dimensions & ~DMF_RELATIVE_X) | DMF_FIXED_X; + Self->Dimensions = (Self->Dimensions & ~DMF_SCALED_X) | DMF_FIXED_X; move_layer(Self, value, Self->Y); // If our right-hand side is relative, we need to resize our surface to counteract the movement. - if ((Self->ParentID) and (Self->Dimensions & (DMF_RELATIVE_X_OFFSET|DMF_FIXED_X_OFFSET))) { - if (!AccessObject(Self->ParentID, 1000, &parent)) { + if ((Self->ParentID) and (Self->Dimensions & (DMF_SCALED_X_OFFSET|DMF_FIXED_X_OFFSET))) { + if (AccessObject(Self->ParentID, 1000, &parent) IS ERR::Okay) { resize_layer(Self, Self->X, Self->Y, parent->Width - Self->X - Self->XOffset, 0, 0, 0, 0, 0, 0); ReleaseObject(parent); } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -926,23 +922,23 @@ If set in conjunction with the X field, the width of the surface object will be of the container, minus the value given in the XOffset. This means that the width of the surface object is dynamically calculated in relation to the width of its container. -If the XOffset field is set in conjunction with a fixed or relative width then the surface object will be positioned at +If the XOffset field is set in conjunction with a fixed or scaled width then the surface object will be positioned at an X coordinate calculated from the formula `X = ContainerWidth - SurfaceWidth - XOffset`. -END- *********************************************************************************************************************/ -static ERROR GET_XOffset(extSurface *Self, Variable *Value) +static ERR GET_XOffset(extSurface *Self, Variable *Value) { pf::Log log; Variable xoffset; extSurface *parent; DOUBLE value; - if (Value->Type & FD_PERCENTAGE) { + if (Value->Type & FD_SCALED) { xoffset.Type = FD_DOUBLE; xoffset.Double = 0; - if (GET_XOffset(Self, &xoffset) IS ERR_Okay) { + if (GET_XOffset(Self, &xoffset) IS ERR::Okay) { value = xoffset.Double / Self->Width; } else value = 0; @@ -954,23 +950,23 @@ static ERROR GET_XOffset(extSurface *Self, Variable *Value) else if ((Self->Dimensions & DMF_WIDTH) and (Self->Dimensions & DMF_X) and (Self->ParentID)) { - if (!AccessObject(Self->ParentID, 1000, &parent)) { + if (AccessObject(Self->ParentID, 1000, &parent) IS ERR::Okay) { value = parent->Width - Self->X - Self->Width; ReleaseObject(parent); } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } else value = 0; } if (Value->Type & FD_DOUBLE) Value->Double = value; else if (Value->Type & FD_LARGE) Value->Large = value; - else return log.warning(ERR_FieldTypeMismatch); + else return log.warning(ERR::FieldTypeMismatch); - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_XOffset(extSurface *Self, Variable *Value) +static ERR SET_XOffset(extSurface *Self, Variable *Value) { pf::Log log; extSurface *parent; @@ -979,16 +975,16 @@ static ERROR SET_XOffset(extSurface *Self, Variable *Value) if (Value->Type & FD_DOUBLE) value = Value->Double; else if (Value->Type & FD_LARGE) value = Value->Large; else if (Value->Type & FD_STRING) value = StrToFloat((CSTRING)Value->Pointer); - else return log.warning(ERR_SetValueNotNumeric); + else return log.warning(ERR::SetValueNotNumeric); if (value < 0) value = -value; - if (Value->Type & FD_PERCENTAGE) { - Self->Dimensions = (Self->Dimensions & ~DMF_FIXED_X_OFFSET) | DMF_RELATIVE_X_OFFSET; + if (Value->Type & FD_SCALED) { + Self->Dimensions = (Self->Dimensions & ~DMF_FIXED_X_OFFSET) | DMF_SCALED_X_OFFSET; Self->XOffsetPercent = value; if (Self->ParentID) { - if (!AccessObject(Self->ParentID, 500, &parent)) { + if (AccessObject(Self->ParentID, 500, &parent) IS ERR::Okay) { Self->XOffset = parent->Width * F2I(Self->XOffsetPercent); if (!(Self->Dimensions & DMF_X)) Self->X = parent->Width - Self->XOffset - Self->Width; if (!(Self->Dimensions & DMF_WIDTH)) { @@ -996,30 +992,30 @@ static ERROR SET_XOffset(extSurface *Self, Variable *Value) } ReleaseObject(parent); } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } } else { - Self->Dimensions = (Self->Dimensions & ~DMF_RELATIVE_X_OFFSET) | DMF_FIXED_X_OFFSET; + Self->Dimensions = (Self->Dimensions & ~DMF_SCALED_X_OFFSET) | DMF_FIXED_X_OFFSET; Self->XOffset = value; if ((Self->Dimensions & DMF_WIDTH) and (Self->ParentID)) { - if (!AccessObject(Self->ParentID, 1000, &parent)) { + if (AccessObject(Self->ParentID, 1000, &parent) IS ERR::Okay) { move_layer(Self, parent->Width - Self->XOffset - Self->Width, Self->Y); ReleaseObject(parent); } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } else if ((Self->Dimensions & DMF_X) and (Self->ParentID)) { - if (!AccessObject(Self->ParentID, 1000, &parent)) { + if (AccessObject(Self->ParentID, 1000, &parent) IS ERR::Okay) { resize_layer(Self, Self->X, Self->Y, parent->Width - Self->X - Self->XOffset, 0, 0, 0, 0, 0, 0); ReleaseObject(parent); } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1028,30 +1024,30 @@ static ERROR SET_XOffset(extSurface *Self, Variable *Value) Y: Determines the vertical position of a surface object. The vertical position of a surface object can be set through this field. You have the choice of setting a fixed -coordinate (the default) or a relative coordinate if you use the FD_PERCENT flag. +coordinate (the default) or a scaled coordinate if you use the `FD_SCALED` flag. If the value is changed while the surface is on display, its position will be updated immediately. *********************************************************************************************************************/ -static ERROR GET_YCoord(extSurface *Self, Variable *Value) +static ERR GET_YCoord(extSurface *Self, Variable *Value) { if (Value->Type & FD_DOUBLE) { - if (Value->Type & FD_PERCENTAGE) Value->Double = Self->YPercent; + if (Value->Type & FD_SCALED) Value->Double = Self->YPercent; else Value->Double = Self->Y; } else if (Value->Type & FD_LARGE) { - if (Value->Type & FD_PERCENTAGE) Value->Large = F2I(Self->YPercent); + if (Value->Type & FD_SCALED) Value->Large = F2I(Self->YPercent); else Value->Large = Self->Y; } else { pf::Log log; - return log.warning(ERR_FieldTypeMismatch); + return log.warning(ERR::FieldTypeMismatch); } - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_YCoord(extSurface *Self, Variable *Value) +static ERR SET_YCoord(extSurface *Self, Variable *Value) { pf::Log log; extSurface *parent; @@ -1060,25 +1056,25 @@ static ERROR SET_YCoord(extSurface *Self, Variable *Value) if (Value->Type & FD_DOUBLE) value = Value->Double; else if (Value->Type & FD_LARGE) value = Value->Large; else if (Value->Type & FD_STRING) value = StrToFloat((CSTRING)Value->Pointer); - else return log.warning(ERR_SetValueNotNumeric); + else return log.warning(ERR::SetValueNotNumeric); - if (Value->Type & FD_PERCENTAGE) { - Self->Dimensions = (Self->Dimensions & ~DMF_FIXED_Y) | DMF_RELATIVE_Y; + if (Value->Type & FD_SCALED) { + Self->Dimensions = (Self->Dimensions & ~DMF_FIXED_Y) | DMF_SCALED_Y; Self->YPercent = value; if (Self->ParentID) { - if (!AccessObject(Self->ParentID, 500, &parent)) { + if (AccessObject(Self->ParentID, 500, &parent) IS ERR::Okay) { move_layer(Self, Self->X, parent->Height * value); ReleaseObject(parent); } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } } else { - Self->Dimensions = (Self->Dimensions & ~DMF_RELATIVE_Y) | DMF_FIXED_Y; + Self->Dimensions = (Self->Dimensions & ~DMF_SCALED_Y) | DMF_FIXED_Y; move_layer(Self, Self->X, value); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1092,23 +1088,23 @@ If set in conjunction with the Y field, the height of the surface object will be height of the container, minus the value given in the YOffset. This means that the height of the surface object is dynamically calculated in relation to the height of its container. -If the YOffset field is set in conjunction with a fixed or relative height then the surface object will be positioned +If the YOffset field is set in conjunction with a fixed or scaled height then the surface object will be positioned at a Y coordinate calculated from the formula "Y = ContainerHeight - SurfaceHeight - YOffset". -END- *********************************************************************************************************************/ -static ERROR GET_YOffset(extSurface *Self, Variable *Value) +static ERR GET_YOffset(extSurface *Self, Variable *Value) { pf::Log log; Variable yoffset; extSurface *parent; DOUBLE value; - if (Value->Type & FD_PERCENTAGE) { + if (Value->Type & FD_SCALED) { yoffset.Type = FD_DOUBLE; yoffset.Double = 0; - if (!GET_YOffset(Self, &yoffset)) { + if (GET_YOffset(Self, &yoffset) IS ERR::Okay) { value = yoffset.Double / Self->Height; } else value = 0; @@ -1118,23 +1114,23 @@ static ERROR GET_YOffset(extSurface *Self, Variable *Value) value = Self->YOffset; } else if ((Self->Dimensions & DMF_HEIGHT) and (Self->Dimensions & DMF_Y) and (Self->ParentID)) { - if (!AccessObject(Self->ParentID, 1000, &parent)) { + if (AccessObject(Self->ParentID, 1000, &parent) IS ERR::Okay) { value = parent->Height - Self->Y - Self->Height; ReleaseObject(parent); } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } else value = 0; } if (Value->Type & FD_DOUBLE) Value->Double = value; else if (Value->Type & FD_LARGE) Value->Large = value; - else return log.warning(ERR_FieldTypeMismatch); + else return log.warning(ERR::FieldTypeMismatch); - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_YOffset(extSurface *Self, Variable *Value) +static ERR SET_YOffset(extSurface *Self, Variable *Value) { pf::Log log; extSurface *parent; @@ -1143,16 +1139,16 @@ static ERROR SET_YOffset(extSurface *Self, Variable *Value) if (Value->Type & FD_DOUBLE) value = Value->Double; else if (Value->Type & FD_LARGE) value = Value->Large; else if (Value->Type & FD_STRING) value = StrToInt((CSTRING)Value->Pointer); - else return log.warning(ERR_SetValueNotNumeric); + else return log.warning(ERR::SetValueNotNumeric); if (value < 0) value = -value; - if (Value->Type & FD_PERCENTAGE) { - Self->Dimensions = (Self->Dimensions & ~DMF_FIXED_Y_OFFSET) | DMF_RELATIVE_Y_OFFSET; + if (Value->Type & FD_SCALED) { + Self->Dimensions = (Self->Dimensions & ~DMF_FIXED_Y_OFFSET) | DMF_SCALED_Y_OFFSET; Self->YOffsetPercent = value; if (Self->ParentID) { - if (!AccessObject(Self->ParentID, 500, &parent)) { + if (AccessObject(Self->ParentID, 500, &parent) IS ERR::Okay) { Self->YOffset = parent->Height * F2I(Self->YOffsetPercent); if (!(Self->Dimensions & DMF_Y))Self->Y = parent->Height - Self->YOffset - Self->Height; if (!(Self->Dimensions & DMF_HEIGHT)) { @@ -1161,31 +1157,31 @@ static ERROR SET_YOffset(extSurface *Self, Variable *Value) else move_layer(Self, Self->X, parent->Height - Self->YOffset - Self->Height); ReleaseObject(parent); } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } } else { - Self->Dimensions = (Self->Dimensions & ~DMF_RELATIVE_Y_OFFSET) | DMF_FIXED_Y_OFFSET; + Self->Dimensions = (Self->Dimensions & ~DMF_SCALED_Y_OFFSET) | DMF_FIXED_Y_OFFSET; Self->YOffset = value; if ((Self->Dimensions & DMF_HEIGHT) and (Self->ParentID)) { - if (!AccessObject(Self->ParentID, 1000, &parent)) { + if (AccessObject(Self->ParentID, 1000, &parent) IS ERR::Okay) { if (!(Self->Dimensions & DMF_HEIGHT)) { resize_layer(Self, Self->X, Self->Y, 0, parent->Height - Self->Y - Self->YOffset, 0, 0, 0, 0, 0); } else move_layer(Self, Self->X, parent->Height - Self->YOffset - Self->Height); ReleaseObject(parent); } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } else if ((Self->Dimensions & DMF_Y) and (Self->ParentID)) { - if (!AccessObject(Self->ParentID, 1000, &parent)) { + if (AccessObject(Self->ParentID, 1000, &parent) IS ERR::Okay) { resize_layer(Self, Self->X, Self->Y, 0, parent->Height - Self->Y - Self->YOffset, 0, 0, 0, 0, 0); ReleaseObject(parent); } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } } - return ERR_Okay; + return ERR::Okay; } diff --git a/src/display/class_surface/surface_drawing.cpp b/src/display/class_surface/surface_drawing.cpp index 367a137bd..3f8cdc78b 100644 --- a/src/display/class_surface/surface_drawing.cpp +++ b/src/display/class_surface/surface_drawing.cpp @@ -1,7 +1,7 @@ void copy_bkgd(const SURFACELIST &, LONG, LONG, LONG, ClipRectangle &, extBitmap *, extBitmap *, WORD, bool); -ERROR _expose_surface(OBJECTID SurfaceID, const SURFACELIST &List, LONG index, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags) +ERR _expose_surface(OBJECTID SurfaceID, const SURFACELIST &List, LONG index, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags) { pf::Log log("expose_surface"); extBitmap *bitmap; @@ -9,13 +9,13 @@ ERROR _expose_surface(OBJECTID SurfaceID, const SURFACELIST &List, LONG index, L bool skip; OBJECTID parent_id; - if ((Width < 1) or (Height < 1)) return ERR_Okay; - if (!SurfaceID) return log.warning(ERR_NullArgs); - if (index >= LONG(List.size())) return log.warning(ERR_OutOfRange); + if ((Width < 1) or (Height < 1)) return ERR::Okay; + if (!SurfaceID) return log.warning(ERR::NullArgs); + if (index >= LONG(List.size())) return log.warning(ERR::OutOfRange); if (List[index].invisible() or (List[index].Width < 1) or (List[index].Height < 1)) { log.trace("Surface %d invisible or too small to draw.", SurfaceID); - return ERR_Okay; + return ERR::Okay; } // Calculate the absolute coordinates of the exposed area @@ -58,7 +58,7 @@ ERROR _expose_surface(OBJECTID SurfaceID, const SURFACELIST &List, LONG index, L // restrict the exposed dimensions. NOTE: This loop looks strange but is both correct & fast. Don't alter it! for (i=index, parent_id = SurfaceID; ;) { - if (List[i].invisible()) return ERR_Okay; + if (List[i].invisible()) return ERR::Okay; auto area = List[i].area(); clip_rectangle(abs, area); if (!(parent_id = List[i].ParentID)) break; @@ -66,14 +66,14 @@ ERROR _expose_surface(OBJECTID SurfaceID, const SURFACELIST &List, LONG index, L while (List[i].SurfaceID != parent_id) i--; } - if ((abs.Left >= abs.Right) or (abs.Top >= abs.Bottom)) return ERR_Okay; + if ((abs.Left >= abs.Right) or (abs.Top >= abs.Bottom)) return ERR::Okay; // Check that the expose area actually overlaps the target surface - if (abs.Left >= List[index].Right) return ERR_Okay; - if (abs.Top >= List[index].Bottom) return ERR_Okay; - if (abs.Right <= List[index].Left) return ERR_Okay; - if (abs.Bottom <= List[index].Top) return ERR_Okay; + if (abs.Left >= List[index].Right) return ERR::Okay; + if (abs.Top >= List[index].Bottom) return ERR::Okay; + if (abs.Right <= List[index].Left) return ERR::Okay; + if (abs.Bottom <= List[index].Top) return ERR::Okay; // Cursor split routine. The purpose of this is to eliminate as much flicker as possible from the cursor when // exposing large areas. @@ -92,7 +92,7 @@ ERROR _expose_surface(OBJECTID SurfaceID, const SURFACELIST &List, LONG index, L log.traceBranch("Splitting cursor."); _expose_surface(SurfaceID, List, index, abs.Left, abs.Top, abs.Right, List[cursor].Bottom, EXF::CURSOR_SPLIT|EXF::ABSOLUTE|Flags); _expose_surface(SurfaceID, List, index, abs.Left, List[cursor].Bottom, abs.Right, abs.Bottom, EXF::CURSOR_SPLIT|EXF::ABSOLUTE|Flags); - return ERR_Okay; + return ERR::Okay; } } } @@ -154,8 +154,7 @@ ERROR _expose_surface(OBJECTID SurfaceID, const SURFACELIST &List, LONG index, L // Do the expose - ERROR error; - if (!(error = AccessObject(List[i].BitmapID, 2000, &bitmap))) { + if (auto error = AccessObject(List[i].BitmapID, 2000, &bitmap); error IS ERR::Okay) { expose_buffer(List, List.size(), i, i, childexpose.Left, childexpose.Top, childexpose.Right, childexpose.Bottom, List[index].DisplayID, bitmap); ReleaseObject(bitmap); } @@ -259,7 +258,7 @@ ERROR _expose_surface(OBJECTID SurfaceID, const SURFACELIST &List, LONG index, L } } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -292,7 +291,7 @@ the surface area first). *********************************************************************************************************************/ -ERROR SURFACE_Draw(extSurface *Self, struct acDraw *Args) +ERR SURFACE_Draw(extSurface *Self, struct acDraw *Args) { pf::Log log; @@ -300,12 +299,12 @@ ERROR SURFACE_Draw(extSurface *Self, struct acDraw *Args) if (Self->invisible() or (tlNoDrawing) or (Self->Width < 1) or (Self->Height < 1)) { log.trace("Not drawing (invisible or tlNoDrawing set)."); - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } // Do not perform manual redraws when a redraw is scheduled. - if (Self->RedrawScheduled) return ERR_Okay|ERF_Notified; + if (Self->RedrawScheduled) return ERR::Okay|ERR::Notified; LONG x, y, width, height; if (!Args) { @@ -327,12 +326,12 @@ ERROR SURFACE_Draw(extSurface *Self, struct acDraw *Args) UBYTE msgbuffer[sizeof(Message) + sizeof(ActionMessage) + sizeof(struct acDraw)]; LONG msgindex = 0; - while (!ScanMessages(&msgindex, MSGID_ACTION, msgbuffer, sizeof(msgbuffer))) { + while (ScanMessages(&msgindex, MSGID_ACTION, msgbuffer, sizeof(msgbuffer)) IS ERR::Okay) { auto action = (ActionMessage *)(msgbuffer + sizeof(Message)); if ((action->ActionID IS MT_DrwInvalidateRegion) and (action->ObjectID IS Self->UID)) { if (!action->SendArgs) { - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } } else if ((action->ActionID IS AC_Draw) and (action->ObjectID IS Self->UID)) { @@ -361,7 +360,7 @@ ERROR SURFACE_Draw(extSurface *Self, struct acDraw *Args) // We do nothing here because the next draw message will draw everything. } - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } } @@ -369,7 +368,7 @@ ERROR SURFACE_Draw(extSurface *Self, struct acDraw *Args) log.traceBranch("%dx%d,%dx%d", x, y, width, height); gfxRedrawSurface(Self->UID, x, y, width, height, IRF::RELATIVE|IRF::IGNORE_CHILDREN); gfxExposeSurface(Self->UID, x, y, width, height, EXF::REDRAW_VOLATILE); - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } /********************************************************************************************************************* @@ -393,15 +392,15 @@ Okay *********************************************************************************************************************/ -static ERROR SURFACE_Expose(extSurface *Self, struct drwExpose *Args) +static ERR SURFACE_Expose(extSurface *Self, struct drwExpose *Args) { - if (tlNoExpose) return ERR_Okay; + if (tlNoExpose) return ERR::Okay; // Check if other draw messages are queued for this object - if so, do not do anything until the final message is reached. UBYTE msgbuffer[sizeof(Message) + sizeof(ActionMessage) + sizeof(struct drwExpose)]; LONG msgindex = 0; - while (!ScanMessages(&msgindex, MSGID_ACTION, msgbuffer, sizeof(msgbuffer))) { + while (ScanMessages(&msgindex, MSGID_ACTION, msgbuffer, sizeof(msgbuffer)) IS ERR::Okay) { auto action = (ActionMessage *)(msgbuffer + sizeof(Message)); if ((action->ActionID IS MT_DrwExpose) and (action->ObjectID IS Self->UID)) { @@ -441,12 +440,12 @@ static ERROR SURFACE_Expose(extSurface *Self, struct drwExpose *Args) // We do nothing here because the next expose message will draw everything. } - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } } - ERROR error; + ERR error; if (Args) error = gfxExposeSurface(Self->UID, Args->X, Args->Y, Args->Width, Args->Height, Args->Flags); else error = gfxExposeSurface(Self->UID, 0, 0, Self->Width, Self->Height, EXF::NIL); @@ -482,21 +481,21 @@ AccessMemory: Failed to access the internal surface list. *********************************************************************************************************************/ -static ERROR SURFACE_InvalidateRegion(extSurface *Self, struct drwInvalidateRegion *Args) +static ERR SURFACE_InvalidateRegion(extSurface *Self, struct drwInvalidateRegion *Args) { if (Self->invisible() or (tlNoDrawing) or (Self->Width < 1) or (Self->Height < 1)) { - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } // Do not perform manual redraws when a redraw is scheduled. - if (Self->RedrawTimer) return ERR_Okay|ERF_Notified; + if (Self->RedrawTimer) return ERR::Okay|ERR::Notified; // Check if other draw messages are queued for this object - if so, do not do anything until the final message is reached. LONG msgindex = 0; UBYTE msgbuffer[sizeof(Message) + sizeof(ActionMessage) + sizeof(struct drwInvalidateRegion)]; - while (!ScanMessages(&msgindex, MSGID_ACTION, msgbuffer, sizeof(msgbuffer))) { + while (ScanMessages(&msgindex, MSGID_ACTION, msgbuffer, sizeof(msgbuffer)) IS ERR::Okay) { auto action = (ActionMessage *)(msgbuffer + sizeof(Message)); if ((action->ActionID IS MT_DrwInvalidateRegion) and (action->ObjectID IS Self->UID)) { if (action->SendArgs IS TRUE) { @@ -522,7 +521,7 @@ static ERROR SURFACE_InvalidateRegion(extSurface *Self, struct drwInvalidateRegi } else { } // We do nothing here because the next invalidation message will draw everything. - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } } @@ -536,7 +535,7 @@ static ERROR SURFACE_InvalidateRegion(extSurface *Self, struct drwInvalidateRegi gfxExposeSurface(Self->UID, 0, 0, Self->Width, Self->Height, EXF::CHILDREN|EXF::REDRAW_VOLATILE_OVERLAP); } - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } //******************************************************************************************************************** @@ -559,20 +558,20 @@ void move_layer(extSurface *Self, LONG X, LONG Y) if (!Self->ParentID) { objDisplay *display; - if (!AccessObject(Self->DisplayID, 2000, &display)) { + if (AccessObject(Self->DisplayID, 2000, &display) IS ERR::Okay) { // Subtract the host window's LeftMargin and TopMargin as MoveToPoint() is based on the coordinates of the window frame. LONG left_margin = display->LeftMargin; LONG top_margin = display->TopMargin; ReleaseObject(display); - if (!acMoveToPoint(display, X - left_margin, Y - top_margin, 0, MTF::X|MTF::Y)) { + if (acMoveToPoint(display, X - left_margin, Y - top_margin, 0, MTF::X|MTF::Y) IS ERR::Okay) { Self->X = X; Self->Y = Y; UpdateSurfaceRecord(Self); } } - else log.warning(ERR_AccessObject); + else log.warning(ERR::AccessObject); return; } @@ -718,13 +717,12 @@ void prepare_background(extSurface *Self, const SURFACELIST &List, LONG Index, e bool pervasive = ((List[Index].Flags & RNF::PERVASIVE_COPY) != RNF::NIL) and (Stage IS STAGE_AFTERCOPY); extBitmap *bitmap; - ERROR error; - if (!(error = AccessObject(List[i].BitmapID, 2000, &bitmap))) { + if (auto error = AccessObject(List[i].BitmapID, 2000, &bitmap); error IS ERR::Okay) { copy_bkgd(List, i, end, master, expose, DestBitmap, bitmap, opaque, pervasive); ReleaseObject(bitmap); } else { - log.warning("prepare_bkgd: %d failed to access bitmap #%d of surface #%d (error %d).", List[Index].SurfaceID, List[i].BitmapID, List[i].SurfaceID, error); + log.warning("prepare_bkgd: %d failed to access bitmap #%d of surface #%d (error %d).", List[Index].SurfaceID, List[i].BitmapID, List[i].SurfaceID, LONG(error)); break; } } diff --git a/src/display/class_surface/surface_fields.cpp b/src/display/class_surface/surface_fields.cpp index 009c07004..36fc9b252 100644 --- a/src/display/class_surface/surface_fields.cpp +++ b/src/display/class_surface/surface_fields.cpp @@ -9,20 +9,20 @@ the display and as such is not recommended. *********************************************************************************************************************/ -static ERROR GET_BitsPerPixel(extSurface *Self, LONG *Value) +static ERR GET_BitsPerPixel(extSurface *Self, LONG *Value) { SURFACEINFO *info; - if (!gfxGetSurfaceInfo(Self->UID, &info)) { + if (gfxGetSurfaceInfo(Self->UID, &info) IS ERR::Okay) { *Value = info->BitsPerPixel; } else *Value = 0; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_BitsPerPixel(extSurface *Self, LONG Value) +static ERR SET_BitsPerPixel(extSurface *Self, LONG Value) { Self->BitsPerPixel = Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -63,17 +63,17 @@ The Cursor field may be written with valid cursor names or their ID's, as you pr *********************************************************************************************************************/ -static ERROR SET_Cursor(extSurface *Self, PTC Value) +static ERR SET_Cursor(extSurface *Self, PTC Value) { Self->Cursor = Value; if (Self->initialised()) { UpdateSurfaceField(Self, &SurfaceRecord::Cursor, (BYTE)Self->Cursor); OBJECTID pointer_id; - if (!FindObject("SystemPointer", ID_POINTER, FOF::NIL, &pointer_id)) { + if (FindObject("SystemPointer", ID_POINTER, FOF::NIL, &pointer_id) IS ERR::Okay) { acRefresh(pointer_id); } } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -98,20 +98,20 @@ To turn off dragging, set the field to zero. *********************************************************************************************************************/ -static ERROR SET_Drag(extSurface *Self, OBJECTID Value) +static ERR SET_Drag(extSurface *Self, OBJECTID Value) { if (Value) { - auto callback = make_function_stdc(consume_input_events); - if (!gfxSubscribeInput(&callback, Self->UID, JTYPE::MOVEMENT|JTYPE::BUTTON, 0, &Self->InputHandle)) { + auto callback = FUNCTION(consume_input_events); + if (gfxSubscribeInput(&callback, Self->UID, JTYPE::MOVEMENT|JTYPE::BUTTON, 0, &Self->InputHandle) IS ERR::Okay) { Self->DragID = Value; - return ERR_Okay; + return ERR::Okay; } - else return ERR_Failed; + else return ERR::Failed; } else { if (Self->InputHandle) { gfxUnsubscribeInput(Self->InputHandle); Self->InputHandle = 0; } Self->DragID = 0; - return ERR_Okay; + return ERR::Okay; } } @@ -131,7 +131,7 @@ field so that existing flags are not overwritten. To not do so can produce unex *********************************************************************************************************************/ -static ERROR SET_Flags(extSurface *Self, RNF Value) +static ERR SET_Flags(extSurface *Self, RNF Value) { auto flags = (Self->Flags & RNF::READ_ONLY) | (Value & (~RNF::READ_ONLY)); @@ -142,7 +142,7 @@ static ERROR SET_Flags(extSurface *Self, RNF Value) UpdateSurfaceField(Self, &SurfaceRecord::Flags, flags); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -155,7 +155,7 @@ with normally. *********************************************************************************************************************/ -static ERROR SET_Modal(extSurface *Self, LONG Value) +static ERR SET_Modal(extSurface *Self, LONG Value) { if ((!Value) and (Self->Modal)) { if (Self->PrevModalID) { @@ -166,7 +166,7 @@ static ERROR SET_Modal(extSurface *Self, LONG Value) } Self->Modal = Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -182,7 +182,7 @@ setting the coordinate fields directly. *********************************************************************************************************************/ -static ERROR SET_Movement(extSurface *Self, LONG Flags) +static ERR SET_Movement(extSurface *Self, LONG Flags) { if (Flags IS MOVE_HORIZONTAL) Self->Flags = (Self->Flags & RNF::NO_HORIZONTAL) | RNF::NO_VERTICAL; else if (Flags IS MOVE_VERTICAL) Self->Flags = (Self->Flags & RNF::NO_VERTICAL) | RNF::NO_HORIZONTAL; @@ -190,7 +190,7 @@ static ERROR SET_Movement(extSurface *Self, LONG Flags) else Self->Flags |= RNF::NO_HORIZONTAL|RNF::NO_VERTICAL; UpdateSurfaceField(Self, &SurfaceRecord::Flags, Self->Flags); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -209,13 +209,13 @@ Please note that the use of translucency is realised at a significant cost to CP *********************************************************************************************************************/ -static ERROR GET_Opacity(extSurface *Self, DOUBLE *Value) +static ERR GET_Opacity(extSurface *Self, DOUBLE *Value) { *Value = Self->Opacity * 100 / 255; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_Opacity(extSurface *Self, DOUBLE Value) +static ERR SET_Opacity(extSurface *Self, DOUBLE Value) { LONG opacity; @@ -224,13 +224,13 @@ static ERROR SET_Opacity(extSurface *Self, DOUBLE Value) if (Value >= 100) { opacity = 255; - if (opacity IS Self->Opacity) return ERR_Okay; + if (opacity IS Self->Opacity) return ERR::Okay; Self->Flags &= ~RNF::AFTER_COPY; } else { if (Value < 0) opacity = 0; else opacity = (Value * 255) / 100; - if (opacity IS Self->Opacity) return ERR_Okay; + if (opacity IS Self->Opacity) return ERR::Okay; Self->Flags |= RNF::AFTER_COPY; // See PrepareBackground() to see what these flags are for // NB: Currently the combination of PRECOPY and AFTERCOPY at the same time is permissible, @@ -240,7 +240,7 @@ static ERROR SET_Opacity(extSurface *Self, DOUBLE Value) Self->Opacity = opacity; UpdateSurfaceRecord(Self); // Update Opacity, Flags - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -253,14 +253,14 @@ a surface object. This behaviour can be switched off by setting a Parent of zer *********************************************************************************************************************/ -static ERROR SET_Parent(extSurface *Self, LONG Value) +static ERR SET_Parent(extSurface *Self, LONG Value) { // To change the parent post-initialisation, we have to re-track the surface so that it is correctly repositioned // within the surface lists. if (Self->initialised()) { - if (!Self->ParentID) return ERR_Failed; // Top level surfaces cannot be re-parented - if (Self->ParentID IS Value) return ERR_Okay; + if (!Self->ParentID) return ERR::Failed; // Top level surfaces cannot be re-parented + if (Self->ParentID IS Value) return ERR::Okay; acHide(Self); @@ -288,7 +288,7 @@ static ERROR SET_Parent(extSurface *Self, LONG Value) Self->ParentDefined = true; } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -302,40 +302,40 @@ other surfaces created by the current program. Setting the PopOver field to zero will return the surface to its normal state. If an object that does not belong to the Surface class is detected, an attempt will be made to read that object's -Surface field, if available. If this does not yield a valid surface then ERR_InvalidObject is returned. +Surface field, if available. If this does not yield a valid surface then ERR::InvalidObject is returned. *********************************************************************************************************************/ -static ERROR SET_PopOver(extSurface *Self, OBJECTID Value) +static ERR SET_PopOver(extSurface *Self, OBJECTID Value) { pf::Log log; - if (Value IS Self->UID) return ERR_Okay; + if (Value IS Self->UID) return ERR::Okay; - if (Self->initialised()) return log.warning(ERR_Immutable); + if (Self->initialised()) return log.warning(ERR::Immutable); if (Value) { CLASSID class_id = GetClassID(Value); if (class_id != ID_SURFACE) { OBJECTPTR obj; - if (!AccessObject(Value, 3000, &obj)) { - obj->get(FID_Surface, &Value); + if (AccessObject(Value, 3000, &obj) IS ERR::Okay) { + Value = obj->get(FID_Surface); ReleaseObject(obj); } - else return ERR_AccessObject; + else return ERR::AccessObject; - if (class_id != ID_SURFACE) return log.warning(ERR_InvalidObject); + if (class_id != ID_SURFACE) return log.warning(ERR::InvalidObject); } } Self->PopOverID = Value; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_RevertFocus(extSurface *Self, OBJECTID Value) +static ERR SET_RevertFocus(extSurface *Self, OBJECTID Value) { Self->RevertFocusID = Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -345,11 +345,11 @@ RootLayer: Private *********************************************************************************************************************/ -static ERROR SET_RootLayer(extSurface *Self, OBJECTID Value) +static ERR SET_RootLayer(extSurface *Self, OBJECTID Value) { Self->RootID = Value; UpdateSurfaceField(Self, &SurfaceRecord::RootID, Value); // Update RootLayer - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -361,11 +361,11 @@ Returns the surface object that has the primary user focus. Returns NULL if no *********************************************************************************************************************/ -static ERROR GET_UserFocus(extSurface *Self, OBJECTID *Value) +static ERR GET_UserFocus(extSurface *Self, OBJECTID *Value) { - const std::lock_guard lock(glFocusLock); + const std::lock_guard lock(glFocusLock); *Value = glFocusList[0]; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -383,18 +383,18 @@ Visibility is directly affected by the Hide and Show actions if you wish to chan *********************************************************************************************************************/ -static ERROR GET_Visible(extSurface *Self, LONG *Value) +static ERR GET_Visible(extSurface *Self, LONG *Value) { if (Self->visible()) *Value = TRUE; else *Value = FALSE; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_Visible(extSurface *Self, LONG Value) +static ERR SET_Visible(extSurface *Self, LONG Value) { if (Value) acShow(Self); else acHide(Self); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -412,25 +412,25 @@ custom surfaces. *********************************************************************************************************************/ -static ERROR GET_WindowType(extSurface *Self, SWIN *Value) +static ERR GET_WindowType(extSurface *Self, SWIN *Value) { *Value = Self->WindowType; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_WindowType(extSurface *Self, SWIN Value) +static ERR SET_WindowType(extSurface *Self, SWIN Value) { if (Self->initialised()) { pf::Log log; if (Self->WindowType IS Value) { log.trace("WindowType == %d", Value); - return ERR_Okay; + return ERR::Okay; } if (Self->DisplayID) { objDisplay *display; - if (!AccessObject(Self->DisplayID, 2000, &display)) { + if (AccessObject(Self->DisplayID, 2000, &display) IS ERR::Okay) { log.trace("Changing window type to %d.", Value); bool border; @@ -460,13 +460,13 @@ static ERROR SET_WindowType(extSurface *Self, SWIN Value) Self->WindowType = Value; ReleaseObject(display); } - else return ERR_AccessObject; + else return ERR::AccessObject; } - else return log.warning(ERR_NoSupport); + else return log.warning(ERR::NoSupport); } else Self->WindowType = Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -484,16 +484,16 @@ window that already exists. *********************************************************************************************************************/ -static ERROR GET_WindowHandle(extSurface *Self, APTR *Value) +static ERR GET_WindowHandle(extSurface *Self, APTR *Value) { *Value = (APTR)Self->DisplayWindow; - return ERR_Okay; + return ERR::Okay; } -static ERROR SET_WindowHandle(extSurface *Self, APTR Value) +static ERR SET_WindowHandle(extSurface *Self, APTR Value) { - if (Self->initialised()) return ERR_Failed; + if (Self->initialised()) return ERR::Failed; if (Value) Self->DisplayWindow = Value; - return ERR_Okay; + return ERR::Okay; } diff --git a/src/display/class_surface/surface_resize.cpp b/src/display/class_surface/surface_resize.cpp index 1bf1a2fcc..22a557629 100644 --- a/src/display/class_surface/surface_resize.cpp +++ b/src/display/class_surface/surface_resize.cpp @@ -5,21 +5,21 @@ Redimension: Moves and resizes a surface object in a single action call. -END- *********************************************************************************************************************/ -static ERROR SURFACE_Redimension(extSurface *Self, struct acRedimension *Args) +static ERR SURFACE_Redimension(extSurface *Self, struct acRedimension *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs)|ERF_Notified; + if (!Args) return log.warning(ERR::NullArgs)|ERR::Notified; if ((Args->Width < 0) or (Args->Height < 0)) { log.trace("Bad width/height: %.0fx%.0f", Args->Width, Args->Height); - return ERR_Args|ERF_Notified; + return ERR::Args|ERR::Notified; } if (auto msg = GetActionMsg()) { // If this action was called as a message, then it could have been delayed and thus superseded by a more recent call. if (msg->Time < Self->LastRedimension) { log.trace("Ignoring superseded redimension message (%" PF64 " < %" PF64 ").", msg->Time, Self->LastRedimension); - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } } @@ -29,10 +29,10 @@ static ERROR SURFACE_Redimension(extSurface *Self, struct acRedimension *Args) if (Self->visible()) { // Visibility check because this sub-routine doesn't play nice with hidden surfaces. UBYTE msgbuffer[sizeof(Message) + sizeof(ActionMessage)]; LONG index = 0; - while (!ScanMessages(&index, MSGID_ACTION, msgbuffer, sizeof(msgbuffer))) { + while (ScanMessages(&index, MSGID_ACTION, msgbuffer, sizeof(msgbuffer)) IS ERR::Okay) { auto action = (ActionMessage *)(msgbuffer + sizeof(Message)); if ((action->ActionID IS AC_Redimension) and (action->ObjectID IS Self->UID)) { - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } } } @@ -82,13 +82,13 @@ static ERROR SURFACE_Redimension(extSurface *Self, struct acRedimension *Args) // Check for changes if ((newx IS oldx) and (newy IS oldy) and (newwidth IS oldwidth) and (newheight IS oldheight)) { - return ERR_Okay|ERF_Notified; + return ERR::Okay|ERR::Notified; } log.traceBranch("%dx%d %dx%d (req. %dx%d, %dx%d) Depth: %.0f $%.8x", newx, newy, newwidth, newheight, F2T(Args->X), F2T(Args->Y), F2T(Args->Width), F2T(Args->Height), Args->Depth, LONG(Self->Flags)); - ERROR error = resize_layer(Self, newx, newy, newwidth, newheight, newwidth, newheight, F2T(Args->Depth), 0.0, 0); - return error|ERF_Notified; + ERR error = resize_layer(Self, newx, newy, newwidth, newheight, newwidth, newheight, F2T(Args->Depth), 0.0, 0); + return error|ERR::Notified; } /********************************************************************************************************************* @@ -97,15 +97,15 @@ Resize: Alters the dimensions of a surface object. -END- *********************************************************************************************************************/ -static ERROR SURFACE_Resize(extSurface *Self, struct acResize *Args) +static ERR SURFACE_Resize(extSurface *Self, struct acResize *Args) { - if (!Args) return ERR_NullArgs|ERF_Notified; + if (!Args) return ERR::NullArgs|ERR::Notified; if (((!Args->Width) or (Args->Width IS Self->Width)) and - ((!Args->Height) or (Args->Height IS Self->Height))) return ERR_Okay|ERF_Notified; + ((!Args->Height) or (Args->Height IS Self->Height))) return ERR::Okay|ERR::Notified; struct acRedimension redimension = { (DOUBLE)Self->X, (DOUBLE)Self->Y, 0, Args->Width, Args->Height, Args->Depth }; - return Action(AC_Redimension, Self, &redimension)|ERF_Notified; + return Action(AC_Redimension, Self, &redimension)|ERR::Notified; } /********************************************************************************************************************* @@ -142,23 +142,23 @@ Failed *********************************************************************************************************************/ -static ERROR SURFACE_SetDisplay(extSurface *Self, struct gfxSetDisplay *Args) +static ERR SURFACE_SetDisplay(extSurface *Self, struct gfxSetDisplay *Args) { pf::Log log; - if ((!Args) or (Args->Width < 0) or (Args->Height < 0)) return log.warning(ERR_Args); - if (Self->ParentID) return log.warning(ERR_Failed); + if ((!Args) or (Args->Width < 0) or (Args->Height < 0)) return log.warning(ERR::Args); + if (Self->ParentID) return log.warning(ERR::Failed); LONG newx = Args->X; LONG newy = Args->Y; LONG newwidth = (!Args->Width) ? Self->Width : Args->Width; LONG newheight = (!Args->Height) ? Self->Height : Args->Height; - //if ((newx IS Self->X) and (newy IS Self->Y) and (newwidth IS Self->Width) and (newheight IS Self->Height)) return ERR_Okay; + //if ((newx IS Self->X) and (newy IS Self->Y) and (newwidth IS Self->Width) and (newheight IS Self->Height)) return ERR::Okay; log.branch("%dx%d,%dx%d, BPP %d", newx, newy, newwidth, newheight, Args->BitsPerPixel); - ERROR error = resize_layer(Self, newx, newy, newwidth, newheight, + ERR error = resize_layer(Self, newx, newy, newwidth, newheight, Args->InsideWidth, Args->InsideHeight, Args->BitsPerPixel, Args->RefreshRate, Args->Flags); diff --git a/src/display/defs.h b/src/display/defs.h index 36ec5282e..c4e2b783a 100644 --- a/src/display/defs.h +++ b/src/display/defs.h @@ -96,10 +96,6 @@ #define BLEND_MAX_THRESHOLD 255 #define BLEND_MIN_THRESHOLD 1 -#ifndef PI -#define PI (3.141592653589793238462643383279f) -#endif - #define ALIGN32(a) (((a) + 3) & (~3)) #define SURFACE_READ (0x0001) // Read access @@ -201,14 +197,14 @@ enum { struct ptrSetWinCursor { PTC Cursor; }; struct ptrGrabX11Pointer { OBJECTID SurfaceID; }; -INLINE ERROR ptrSetWinCursor(OBJECTPTR Ob, PTC Cursor) { +INLINE ERR ptrSetWinCursor(OBJECTPTR Ob, PTC Cursor) { struct ptrSetWinCursor args = { Cursor }; return Action(MT_PtrSetWinCursor, Ob, &args); } #define ptrUngrabX11Pointer(obj) Action(MT_PtrUngrabX11Pointer,(obj),0) -INLINE ERROR ptrGrabX11Pointer(OBJECTPTR Ob, OBJECTID SurfaceID) { +INLINE ERR ptrGrabX11Pointer(OBJECTPTR Ob, OBJECTID SurfaceID) { struct ptrGrabX11Pointer args = { SurfaceID }; return Action(MT_PtrGrabX11Pointer, Ob, &args); } @@ -397,6 +393,7 @@ class extDisplay : public objDisplay { APTR WindowHandle; Window XWindowHandle; }; + Pixmap XPixmap; #elif __ANDROID__ ANativeWindow *WindowHandle; #else @@ -420,43 +417,44 @@ class extDisplay : public objDisplay { #endif }; -extern ERROR create_bitmap_class(void); -extern ERROR create_clipboard_class(void); -extern ERROR create_display_class(void); -extern ERROR create_pointer_class(void); -extern ERROR create_surface_class(void); -extern ERROR get_surface_abs(OBJECTID, LONG *, LONG *, LONG *, LONG *); +extern void clean_clipboard(void); +extern ERR create_bitmap_class(void); +extern ERR create_clipboard_class(void); +extern ERR create_display_class(void); +extern ERR create_pointer_class(void); +extern ERR create_surface_class(void); +extern ERR get_surface_abs(OBJECTID, LONG *, LONG *, LONG *, LONG *); extern void input_event_loop(HOSTHANDLE, APTR); -extern ERROR lock_surface(extBitmap *, WORD); -extern ERROR unlock_surface(extBitmap *); -extern ERROR get_display_info(OBJECTID, DISPLAYINFO *, LONG); -extern void resize_feedback(FUNCTION *, OBJECTID, LONG X, LONG Y, LONG Width, LONG Height); -extern void forbidDrawing(void); -extern void forbidExpose(void); -extern void permitDrawing(void); -extern void permitExpose(void); -extern ERROR apply_style(OBJECTPTR, OBJECTPTR, CSTRING); -extern ERROR load_styles(void); -extern LONG find_bitmap_owner(const SURFACELIST &, LONG); -extern void move_layer(extSurface *, LONG, LONG); -extern void move_layer_pos(SURFACELIST &, LONG, LONG); -extern void prepare_background(extSurface *, const SURFACELIST &, LONG, extBitmap *, const ClipRectangle &, BYTE); -extern void process_surface_callbacks(extSurface *, extBitmap *); -extern void refresh_pointer(extSurface *Self); -extern ERROR track_layer(extSurface *); -extern void untrack_layer(OBJECTID); -extern BYTE restrict_region_to_parents(const SURFACELIST &, LONG, ClipRectangle &, bool); -extern ERROR load_style_values(void); -extern ERROR resize_layer(extSurface *, LONG X, LONG Y, LONG, LONG, LONG, LONG, LONG BPP, DOUBLE, LONG); -extern void redraw_nonintersect(OBJECTID, const SURFACELIST &, LONG, const ClipRectangle &, const ClipRectangle &, IRF, EXF); -extern ERROR _expose_surface(OBJECTID, const SURFACELIST &, LONG, LONG, LONG, LONG, LONG, EXF); -extern ERROR _redraw_surface(OBJECTID, const SURFACELIST &, LONG, LONG, LONG, LONG, LONG, IRF); -extern void _redraw_surface_do(extSurface *, const SURFACELIST &, LONG, ClipRectangle &, extBitmap *, IRF); -extern void check_styles(STRING Path, OBJECTPTR *Script) __attribute__((unused)); -extern ERROR update_surface_copy(extSurface *); -extern ERROR update_display(extDisplay *, extBitmap *, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); - -extern ERROR gfxRedrawSurface(OBJECTID, LONG, LONG, LONG, LONG, IRF); +extern ERR lock_surface(extBitmap *, WORD); +extern ERR unlock_surface(extBitmap *); +extern ERR get_display_info(OBJECTID, DISPLAYINFO *, LONG); +extern void resize_feedback(FUNCTION *, OBJECTID, LONG X, LONG Y, LONG Width, LONG Height); +extern void forbidDrawing(void); +extern void forbidExpose(void); +extern void permitDrawing(void); +extern void permitExpose(void); +extern ERR apply_style(OBJECTPTR, OBJECTPTR, CSTRING); +extern ERR load_styles(void); +extern LONG find_bitmap_owner(const SURFACELIST &, LONG); +extern void move_layer(extSurface *, LONG, LONG); +extern void move_layer_pos(SURFACELIST &, LONG, LONG); +extern void prepare_background(extSurface *, const SURFACELIST &, LONG, extBitmap *, const ClipRectangle &, BYTE); +extern void process_surface_callbacks(extSurface *, extBitmap *); +extern void refresh_pointer(extSurface *Self); +extern ERR track_layer(extSurface *); +extern void untrack_layer(OBJECTID); +extern BYTE restrict_region_to_parents(const SURFACELIST &, LONG, ClipRectangle &, bool); +extern ERR load_style_values(void); +extern ERR resize_layer(extSurface *, LONG X, LONG Y, LONG, LONG, LONG, LONG, LONG BPP, DOUBLE, LONG); +extern void redraw_nonintersect(OBJECTID, const SURFACELIST &, LONG, const ClipRectangle &, const ClipRectangle &, IRF, EXF); +extern ERR _expose_surface(OBJECTID, const SURFACELIST &, LONG, LONG, LONG, LONG, LONG, EXF); +extern ERR _redraw_surface(OBJECTID, const SURFACELIST &, LONG, LONG, LONG, LONG, LONG, IRF); +extern void _redraw_surface_do(extSurface *, const SURFACELIST &, LONG, ClipRectangle &, extBitmap *, IRF); +extern void check_styles(STRING Path, OBJECTPTR *Script) __attribute__((unused)); +extern ERR update_surface_copy(extSurface *); +extern ERR update_display(extDisplay *, extBitmap *, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); + +extern ERR gfxRedrawSurface(OBJECTID, LONG, LONG, LONG, LONG, IRF); #ifdef DBG_LAYERS extern void print_layer_list(STRING Function, SurfaceControl *Ctl, LONG POI) @@ -487,7 +485,7 @@ extern std::list glClips; extern std::unordered_map glWindowHooks; extern std::vector glFocusList; -extern std::mutex glFocusLock; +extern std::recursive_mutex glFocusLock; extern std::recursive_mutex glSurfaceLock; extern std::recursive_mutex glInputLock; @@ -509,7 +507,7 @@ extern const CSTRING glInputNames[LONG(JET::END)]; #ifdef _GLES_ // OpenGL related prototypes GLenum alloc_texture(LONG Width, LONG Height, GLuint *TextureID); void refresh_display_from_egl(objDisplay *Self); -ERROR init_egl(void); +ERR init_egl(void); void free_egl(void); #endif @@ -554,6 +552,7 @@ extern void handle_motion_notify(XMotionEvent *); extern void handle_stack_change(XCirculateEvent *); extern void init_xcursors(void); extern void free_xcursors(void); +extern ERR resize_pixmap(extDisplay *, LONG, LONG); extern WORD glDGAAvailable; extern APTR glDGAMemory; @@ -643,7 +642,7 @@ inline LONG find_surface_list(OBJECTID SurfaceID, LONG Limit = -1) inline LONG find_parent_list(const SURFACELIST &list, extSurface *Self) { - if ((Self->ListIndex < LONG(list.size())) and (list[Self->ListIndex].SurfaceID IS Self->UID)) { + if ((Self->ListIndex < std::ssize(list)) and (list[Self->ListIndex].SurfaceID IS Self->UID)) { for (LONG i=Self->ListIndex-1; i >= 0; i--) { if (list[i].SurfaceID IS Self->ParentID) return i; } @@ -666,11 +665,13 @@ class extBitmap : public objBitmap { LONG prvAFlags; // Private allocation flags #ifdef __xwindows__ struct { + Window window; XImage ximage; Drawable drawable; XImage *readable; XShmSegmentInfo ShmInfo; GC gc; + LONG pix_width, pix_height; bool XShmImage; } x11; diff --git a/src/display/display-driver.cpp b/src/display/display-driver.cpp index d0977be04..eec0104c6 100644 --- a/src/display/display-driver.cpp +++ b/src/display/display-driver.cpp @@ -11,8 +11,8 @@ that is distributed with this package. Please refer to it for further informati using namespace display; #endif -ERROR GET_HDensity(extDisplay *Self, LONG *Value); -ERROR GET_VDensity(extDisplay *Self, LONG *Value); +ERR GET_HDensity(extDisplay *Self, LONG *Value); +ERR GET_VDensity(extDisplay *Self, LONG *Value); //******************************************************************************************************************** @@ -101,8 +101,7 @@ static void android_term_window(LONG); const InputType glInputType[LONG(JET::END)] = { { JTYPE::NIL, JTYPE::NIL }, // UNUSED - { JTYPE::DIGITAL|JTYPE::MOVEMENT, JTYPE::MOVEMENT }, // JET::DIGITAL_X - { JTYPE::DIGITAL|JTYPE::MOVEMENT, JTYPE::MOVEMENT }, // JET::DIGITAL_Y + { JTYPE::DIGITAL|JTYPE::MOVEMENT, JTYPE::MOVEMENT }, // JET::DIGITAL_XY { JTYPE::BUTTON, JTYPE::BUTTON }, // JET::BUTTON_1 { JTYPE::BUTTON, JTYPE::BUTTON }, // JET::BUTTON_2 { JTYPE::BUTTON, JTYPE::BUTTON }, // JET::BUTTON_3 @@ -121,31 +120,25 @@ const InputType glInputType[LONG(JET::END)] = { { JTYPE::BUTTON, JTYPE::BUTTON }, // JET::LEFT_BUMPER_2 { JTYPE::BUTTON, JTYPE::BUTTON }, // JET::RIGHT_BUMPER_1 { JTYPE::BUTTON, JTYPE::BUTTON }, // JET::RIGHT_BUMPER_2 - { JTYPE::ANALOG|JTYPE::MOVEMENT, JTYPE::MOVEMENT }, // JET::ANALOG_X - { JTYPE::ANALOG|JTYPE::MOVEMENT, JTYPE::MOVEMENT }, // JET::ANALOG_Y + { JTYPE::ANALOG|JTYPE::MOVEMENT, JTYPE::MOVEMENT }, // JET::ANALOG_XY { JTYPE::ANALOG|JTYPE::MOVEMENT, JTYPE::MOVEMENT }, // JET::ANALOG_Z - { JTYPE::ANALOG|JTYPE::MOVEMENT, JTYPE::MOVEMENT }, // JET::ANALOG2_X - { JTYPE::ANALOG|JTYPE::MOVEMENT, JTYPE::MOVEMENT }, // JET::ANALOG2_Y + { JTYPE::ANALOG|JTYPE::MOVEMENT, JTYPE::MOVEMENT }, // JET::ANALOG2_XY { JTYPE::ANALOG|JTYPE::MOVEMENT, JTYPE::MOVEMENT }, // JET::ANALOG2_Z { JTYPE::EXT_MOVEMENT, JTYPE::EXT_MOVEMENT }, // JET::WHEEL { JTYPE::EXT_MOVEMENT, JTYPE::EXT_MOVEMENT }, // JET::WHEEL_TILT - { JTYPE::EXT_MOVEMENT, JTYPE::EXT_MOVEMENT }, // JET::PEN_TILT_VERTICAL - { JTYPE::EXT_MOVEMENT, JTYPE::EXT_MOVEMENT }, // JET::PEN_TILT_HORIZONTAL - { JTYPE::MOVEMENT, JTYPE::MOVEMENT }, // JET::ABS_X - { JTYPE::MOVEMENT, JTYPE::MOVEMENT }, // JET::ABS_Y - { JTYPE::FEEDBACK, JTYPE::FEEDBACK }, // JET::ENTER_SURFACE - { JTYPE::FEEDBACK, JTYPE::FEEDBACK }, // JET::LEAVE_SURFACE + { JTYPE::EXT_MOVEMENT, JTYPE::EXT_MOVEMENT }, // JET::PEN_TILT_XY + { JTYPE::MOVEMENT, JTYPE::MOVEMENT }, // JET::ABS_XY + { JTYPE::CROSSING, JTYPE::CROSSING }, // JET::CROSSING_IN + { JTYPE::CROSSING, JTYPE::CROSSING }, // JET::CROSSING_OUT { JTYPE::EXT_MOVEMENT, JTYPE::EXT_MOVEMENT }, // JET::PRESSURE - { JTYPE::EXT_MOVEMENT, JTYPE::EXT_MOVEMENT }, // JET::DEVICE_TILT_X - { JTYPE::EXT_MOVEMENT, JTYPE::EXT_MOVEMENT }, // JET::DEVICE_TILT_Y + { JTYPE::EXT_MOVEMENT, JTYPE::EXT_MOVEMENT }, // JET::DEVICE_TILT_XY { JTYPE::EXT_MOVEMENT, JTYPE::EXT_MOVEMENT }, // JET::DEVICE_TILT_Z - { JTYPE::FEEDBACK, JTYPE::FEEDBACK } // JET::DISPLAY_EDGE + { JTYPE::EXT_MOVEMENT, JTYPE::EXT_MOVEMENT } // JET::DISPLAY_EDGE }; const CSTRING glInputNames[LONG(JET::END)] = { "", - "DIGITAL_X", - "DIGITAL_Y", + "DIGITAL_XY", "BUTTON_1", "BUTTON_2", "BUTTON_3", @@ -164,23 +157,18 @@ const CSTRING glInputNames[LONG(JET::END)] = { "LEFT_BUMPER_2", "RIGHT_BUMPER_1", "RIGHT_BUMPER_2", - "ANALOG_X", - "ANALOG_Y", + "ANALOG_XY", "ANALOG_Z", - "ANALOG2_X", - "ANALOG2_Y", + "ANALOG2_XY", "ANALOG2_Z", "WHEEL", "WHEEL_TILT", - "PEN_TILT_VERTICAL", - "PEN_TILT_HORIZONTAL", - "ABS_X", - "ABS_Y", - "ENTERED_SURFACE", - "LEFT_SURFACE", + "PEN_TILT_XY", + "ABS_XY", + "CROSSING_IN", + "CROSSING_OUT", "PRESSURE", - "DEVICE_TILT_X", - "DEVICE_TILT_Y", + "DEVICE_TILT_XY", "DEVICE_TILT_Z", "DISPLAY_EDGE" }; @@ -213,7 +201,6 @@ OBJECTID glPointerID = 0; DISPLAYINFO glDisplayInfo; APTR glDither = NULL; bool glSixBitDisplay = false; -static MsgHandler *glExposeHandler = NULL; TIMER glRefreshPointerTimer = 0; extBitmap *glComposite = NULL; static auto glDisplayType = DT::NATIVE; @@ -226,7 +213,7 @@ char glpDPMS[20] = "Standby"; UBYTE *glDemultiply = NULL; std::vector glFocusList; -std::mutex glFocusLock; +std::recursive_mutex glFocusLock; std::recursive_mutex glSurfaceLock; THREADVAR WORD tlNoDrawing = 0, tlNoExpose = 0, tlVolatileIndex = 0; @@ -235,7 +222,7 @@ THREADVAR OBJECTID tlFreeExpose = 0; //******************************************************************************************************************** // Alpha blending data. -INLINE UBYTE clipByte(LONG value) +inline UBYTE clipByte(LONG value) { value = (0 & (-(WORD)(value < 0))) | (value & (-(WORD)!(value < 0))); value = (255 & (-(WORD)(value > 255))) | (value & (-(WORD)!(value > 255))); @@ -291,7 +278,7 @@ int pthread_mutex_timedlock (pthread_mutex_t *mutex, int Timeout) // display is unavailable then this function will fail even if the lock could otherwise be granted. #ifdef _GLES_ -ERROR lock_graphics_active(CSTRING Caller) +ERR lock_graphics_active(CSTRING Caller) { pf::Log log(__FUNCTION__); @@ -307,23 +294,23 @@ ERROR lock_graphics_active(CSTRING Caller) if ((glEGLState != EGL_INITIALISED) or (glEGLDisplay IS EGL_NO_DISPLAY)) { pthread_mutex_unlock(&glGraphicsMutex); //log.trace("EGL not initialised."); - return ERR_NotInitialised; + return ERR::NotInitialised; } if ((glEGLContext != EGL_NO_CONTEXT) and (!glLockCount)) { // eglMakeCurrent() allows our thread to use OpenGL. if (eglMakeCurrent(glEGLDisplay, glEGLSurface, glEGLSurface, glEGLContext) == EGL_FALSE) { // Failure probably indicates that a power management event has occurred (requires re-initialisation). pthread_mutex_unlock(&glGraphicsMutex); - return ERR_NotInitialised; + return ERR::NotInitialised; } } glLockCount++; - return ERR_Okay; + return ERR::Okay; } else { log.warning("Failed to get lock for %s. Locked by %s. Error: %s", Caller, glLastLock, strerror(errno)); - return ERR_TimeOut; + return ERR::TimeOut; } } @@ -470,30 +457,57 @@ int CatchXIOError(Display *XDisplay) return 0; } +//******************************************************************************************************************** +// Resize the pixmap buffer for a window, but only if the new dimensions exceed the existing values. + +extern ERR resize_pixmap(extDisplay *Self, LONG Width, LONG Height) +{ + auto bmp = (extBitmap *)Self->Bitmap; + if ((bmp->Flags & BMF::ALPHA_CHANNEL) != BMF::NIL) return ERR::Okay; // Composite window + + if ((bmp->x11.pix_width > Width) and (bmp->x11.pix_height > Height)) return ERR::Okay; + + if (Width > bmp->x11.pix_width) bmp->x11.pix_width = Width; + if (Height > bmp->x11.pix_height) bmp->x11.pix_height = Height; + + auto xbpp = DefaultDepth(XDisplay, DefaultScreen(XDisplay)); + + if ((bmp->Flags & BMF::FIXED_DEPTH) != BMF::NIL) xbpp = bmp->BitsPerPixel; + + if (auto pixmap = XCreatePixmap(XDisplay, Self->XWindowHandle, bmp->x11.pix_width, bmp->x11.pix_height, xbpp)) { + XSetWindowBackgroundPixmap(XDisplay, Self->XWindowHandle, pixmap); + if (Self->XPixmap) XFreePixmap(XDisplay, Self->XPixmap); + Self->XPixmap = pixmap; + bmp->x11.drawable = pixmap; + return ERR::Okay; + } + else return ERR::AllocMemory; +} + #endif //******************************************************************************************************************** -ERROR get_display_info(OBJECTID DisplayID, DISPLAYINFO *Info, LONG InfoSize) +ERR get_display_info(OBJECTID DisplayID, DISPLAYINFO *Info, LONG InfoSize) { pf::Log log(__FUNCTION__); //log.traceBranch("Display: %d, Info: %p, Size: %d", DisplayID, Info, InfoSize); - if (!Info) return log.warning(ERR_NullArgs); + if (!Info) return log.warning(ERR::NullArgs); if (InfoSize != sizeof(DisplayInfoV3)) { log.error("Invalid InfoSize of %d (V3: %d)", InfoSize, (LONG)sizeof(DisplayInfoV3)); - return log.warning(ERR_Args); + return log.warning(ERR::Args); } extDisplay *display; if (DisplayID) { if (glDisplayInfo.DisplayID IS DisplayID) { CopyMemory(&glDisplayInfo, Info, InfoSize); - return ERR_Okay; + return ERR::Okay; } - else if (!AccessObject(DisplayID, 5000, &display)) { + else if (AccessObject(DisplayID, 5000, &display) IS ERR::Okay) { Info->DisplayID = DisplayID; Info->Flags = display->Flags; Info->Width = display->Width; @@ -527,9 +541,9 @@ ERROR get_display_info(OBJECTID DisplayID, DISPLAYINFO *Info, LONG InfoSize) Info->PixelFormat.AlphaPos = display->Bitmap->ColourFormat->AlphaPos; ReleaseObject(display); - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } else { // If no display is specified, return default display settings for the main monitor and availability flags. @@ -652,20 +666,20 @@ ERROR get_display_info(OBJECTID DisplayID, DISPLAYINFO *Info, LONG InfoSize) } else { adUnlockAndroid(); - return log.warning(ERR_SystemCall); + return log.warning(ERR::SystemCall); } adUnlockAndroid(); } - else return log.warning(ERR_TimeOut); + else return log.warning(ERR::TimeOut); CopyMemory(glDisplayInfo, Info, InfoSize); - return ERR_Okay; + return ERR::Okay; #else if (glDisplayInfo.DisplayID) { CopyMemory(glDisplayInfo, Info, InfoSize); - return ERR_Okay; + return ERR::Okay; } else { Info->Width = 1024; @@ -701,13 +715,13 @@ ERROR get_display_info(OBJECTID DisplayID, DISPLAYINFO *Info, LONG InfoSize) else Info->AmtColours = 1<BitsPerPixel; log.trace("%dx%dx%d", Info->Width, Info->Height, Info->BitsPerPixel); - return ERR_Okay; + return ERR::Okay; } } //******************************************************************************************************************** -static ERROR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) +static ERR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) { pf::Log log(__FUNCTION__); @@ -726,13 +740,13 @@ static ERROR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) create_bitmap_class(); create_clipboard_class(); create_surface_class(); - return ERR_Okay; + return ERR::Okay; } #endif if (auto driver_name = (CSTRING)GetResourcePtr(RES::DISPLAY_DRIVER)) { log.msg("User requested display driver '%s'", driver_name); - if ((!StrMatch(driver_name, "none")) or (!StrMatch(driver_name, "headless"))) { + if ((StrMatch(driver_name, "none") IS ERR::Okay) or (StrMatch(driver_name, "headless") IS ERR::Okay)) { glHeadless = true; } } @@ -751,7 +765,7 @@ static ERROR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) #ifdef __ANDROID__ if (GetResource(RES::SYSTEM_STATE) >= 0) { - if (objModule::load("android", (OBJECTPTR *)&modAndroid, &AndroidBase) != ERR_Okay) return ERR_InitModule; + if (objModule::load("android", (OBJECTPTR *)&modAndroid, &AndroidBase) != ERR::Okay) return ERR::InitModule; FUNCTION fInitWindow, fTermWindow; SET_CALLBACK_STDC(fInitWindow, &android_init_window); // Sets EGL for re-initialisation and draws the display. @@ -759,8 +773,8 @@ static ERROR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) if (adAddCallbacks(ACB_INIT_WINDOW, &fInitWindow, ACB_TERM_WINDOW, &fTermWindow, - TAGEND) != ERR_Okay) { - return ERR_SystemCall; + TAGEND) != ERR::Okay) { + return ERR::SystemCall; } } #endif @@ -794,7 +808,7 @@ static ERROR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) XSetErrorHandler((XErrorHandler)CatchXError); XSetIOErrorHandler(CatchXIOError); } - else return ERR_Failed; + else return ERR::Failed; // Try to load XRandR if we are the display manager, but it's okay if not available @@ -804,7 +818,7 @@ static ERROR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) acSetVar(modXRR, "XDisplay", buffer); modXRR->set(FID_Name, "xrandr"); if (!InitObject(modXRR)) { - if (modXRR->getPtr(FID_ModBase, &XRandRBase) != ERR_Okay) XRandRBase = NULL; + if (modXRR->getPtr(FID_ModBase, &XRandRBase) != ERR::Okay) XRandRBase = NULL; } } else XRandRBase = NULL; @@ -872,9 +886,9 @@ static ERROR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) #elif _WIN32 if ((glInstance = winGetModuleHandle())) { - if (!winCreateScreenClass()) return log.warning(ERR_SystemCall); + if (!winCreateScreenClass()) return log.warning(ERR::SystemCall); } - else return log.warning(ERR_SystemCall); + else return log.warning(ERR::SystemCall); winDisableBatching(); @@ -882,11 +896,11 @@ static ERROR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) #endif - if (create_pointer_class() != ERR_Okay) return log.warning(ERR_AddClass); - if (create_display_class() != ERR_Okay) return log.warning(ERR_AddClass); - if (create_bitmap_class() != ERR_Okay) return log.warning(ERR_AddClass); - if (create_clipboard_class() != ERR_Okay) return log.warning(ERR_AddClass); - if (create_surface_class() != ERR_Okay) return log.warning(ERR_AddClass); + if (create_pointer_class() != ERR::Okay) return log.warning(ERR::AddClass); + if (create_display_class() != ERR::Okay) return log.warning(ERR::AddClass); + if (create_bitmap_class() != ERR::Okay) return log.warning(ERR::AddClass); + if (create_clipboard_class() != ERR::Okay) return log.warning(ERR::AddClass); + if (create_surface_class() != ERR::Okay) return log.warning(ERR::AddClass); // Initialise 64K alpha blending table, for cutting down on multiplications. @@ -911,18 +925,18 @@ static ERROR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) glpDisplayDepth = info.BitsPerPixel; } #else - objConfig::create config = { fl::Path("user:config/display.cfg") }; + auto config = objConfig::create { fl::Path("user:config/display.cfg") }; if (config.ok()) { cfgRead(*config, "DISPLAY", "Maximise", &glpMaximise); if ((glDisplayType IS DT::X11) or (glDisplayType IS DT::WINGDI)) { log.msg("Using hosted window dimensions: %dx%d,%dx%d", glpDisplayX, glpDisplayY, glpDisplayWidth, glpDisplayHeight); - if ((cfgRead(*config, "DISPLAY", "WindowWidth", &glpDisplayWidth) != ERR_Okay) or (!glpDisplayWidth)) { + if ((cfgRead(*config, "DISPLAY", "WindowWidth", &glpDisplayWidth) != ERR::Okay) or (!glpDisplayWidth)) { cfgRead(*config, "DISPLAY", "Width", &glpDisplayWidth); } - if ((cfgRead(*config, "DISPLAY", "WindowHeight", &glpDisplayHeight) != ERR_Okay) or (!glpDisplayHeight)) { + if ((cfgRead(*config, "DISPLAY", "WindowHeight", &glpDisplayHeight) != ERR::Okay) or (!glpDisplayHeight)) { cfgRead(*config, "DISPLAY", "Height", &glpDisplayHeight); } @@ -944,14 +958,14 @@ static ERROR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) cfgRead(*config, "DISPLAY", "GammaGreen", &glpGammaGreen); cfgRead(*config, "DISPLAY", "GammaBlue", &glpGammaBlue); CSTRING dpms; - if (!cfgReadValue(*config, "DISPLAY", "DPMS", &dpms)) { + if (cfgReadValue(*config, "DISPLAY", "DPMS", &dpms) IS ERR::Okay) { StrCopy(dpms, glpDPMS, sizeof(glpDPMS)); } } #endif STRING icon_path; - if (ResolvePath("iconsource:", RSF::NIL, &icon_path) != ERR_Okay) { // The client can set iconsource: to redefine the icon origins + if (ResolvePath("iconsource:", RSF::NIL, &icon_path) != ERR::Okay) { // The client can set iconsource: to redefine the icon origins icon_path = StrClone("styles:icons/"); } @@ -959,14 +973,14 @@ static ERROR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) auto src = std::string(icon_path) + "Default.zip"; if (!(glIconArchive = objCompression::create::integral(fl::Path(src), fl::ArchiveName("icons"), fl::Flags(CMF::READ_ONLY)))) { - return ERR_CreateObject; + return ERR::CreateObject; } FreeResource(icon_path); // The icons: special volume is a simple reference to the archive path. - if (SetVolume("icons", "archive:icons/", "misc/picture", NULL, NULL, VOLUME::REPLACE|VOLUME::HIDDEN)) return ERR_SetVolume; + if (SetVolume("icons", "archive:icons/", "misc/picture", NULL, NULL, VOLUME::REPLACE|VOLUME::HIDDEN) != ERR::Okay) return ERR::SetVolume; #ifdef _WIN32 // Get any existing Windows clipboard content @@ -976,27 +990,28 @@ static ERROR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) #endif - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR CMDOpen(OBJECTPTR Module) +static ERR CMDOpen(OBJECTPTR Module) { Module->set(FID_FunctionList, glFunctions); - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** -static ERROR CMDExpunge(void) +static ERR CMDExpunge(void) { pf::Log log(__FUNCTION__); - ERROR error = ERR_Okay; + ERR error = ERR::Okay; + + clean_clipboard(); glClips.clear(); if (glDither) { FreeResource(glDither); glDither = NULL; } - if (glExposeHandler) { FreeResource(glExposeHandler); glExposeHandler = NULL; } if (glRefreshPointerTimer) { UpdateTimer(glRefreshPointerTimer, 0); glRefreshPointerTimer = 0; } if (glComposite) { FreeResource(glComposite); glComposite = NULL; } if (glCompress) { FreeResource(glCompress); glCompress = NULL; } @@ -1032,7 +1047,7 @@ static ERROR CMDExpunge(void) // termination. In order to resolve this problem we return DoNotExpunge to prevent the removal of X11 // dependent code. - error = ERR_DoNotExpunge; + error = ERR::DoNotExpunge; } #elif __ANDROID__ @@ -1113,7 +1128,7 @@ GLenum alloc_texture(LONG Width, LONG Height, GLuint *TextureID) ** PLEASE NOTE: EGL's design for embedded devices means that only one Display object can be active at any time. */ -ERROR init_egl(void) +ERR init_egl(void) { pf::Log log(__FUNCTION__); EGLint format; @@ -1123,7 +1138,7 @@ ERROR init_egl(void) if (glEGLDisplay != EGL_NO_DISPLAY) { log.msg("EGL display is already initialised."); - return ERR_Okay; + return ERR::Okay; } depth = glEGLPreferredDepth; @@ -1169,13 +1184,13 @@ ERROR init_egl(void) glEGLContext = eglCreateContext(glEGLDisplay, config, NULL, NULL); } else { - log.warning(ERR_SystemCall); - return ERR_SystemCall; + log.warning(ERR::SystemCall); + return ERR::SystemCall; } if (eglMakeCurrent(glEGLDisplay, glEGLSurface, glEGLSurface, glEGLContext) == EGL_FALSE) { - log.warning(ERR_SystemCall); - return ERR_SystemCall; + log.warning(ERR::SystemCall); + return ERR::SystemCall; } eglQuerySurface(glEGLDisplay, glEGLSurface, EGL_WIDTH, &glEGLWidth); @@ -1211,13 +1226,13 @@ ERROR init_egl(void) log.msg("Click-slop calculated as %d.", pointer->ClickSlop); ReleaseObject(pointer); } - else log.warning(ERR_AccessObject); + else log.warning(ERR::AccessObject); } else log.warning("Failed to get Android Config object."); } glEGLState = EGL_INITIALISED; - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -1277,7 +1292,7 @@ void free_egl(void) pthread_mutex_unlock(&glGraphicsMutex); } - else log.warning(ERR_LockFailed); + else log.warning(ERR::LockFailed); log.msg("EGL successfully terminated."); } @@ -1286,7 +1301,7 @@ void free_egl(void) //******************************************************************************************************************** // Updates the display using content from a source bitmap. -ERROR update_display(extDisplay *Self, extBitmap *Bitmap, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) +ERR update_display(extDisplay *Self, extBitmap *Bitmap, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) { #ifdef _WIN32 auto dest = Self->Bitmap; @@ -1301,33 +1316,33 @@ ERROR update_display(extDisplay *Self, extBitmap *Bitmap, LONG X, LONG Y, LONG W if ((xdest < dest->Clip.Left)) { width = width - (dest->Clip.Left - xdest); - if (width < 1) return ERR_Okay; + if (width < 1) return ERR::Okay; x = x + (dest->Clip.Left - xdest); xdest = dest->Clip.Left; } - else if (xdest >= dest->Clip.Right) return ERR_Okay; + else if (xdest >= dest->Clip.Right) return ERR::Okay; if ((ydest < dest->Clip.Top)) { height = height - (dest->Clip.Top - ydest); - if (height < 1) return ERR_Okay; + if (height < 1) return ERR::Okay; y = y + (dest->Clip.Top - ydest); ydest = dest->Clip.Top; } - else if (ydest >= dest->Clip.Bottom) return ERR_Okay; + else if (ydest >= dest->Clip.Bottom) return ERR::Okay; // Check if the source that we are copying from is within its own drawable area. if (x < 0) { - if ((width += x) < 1) return ERR_Okay; + if ((width += x) < 1) return ERR::Okay; x = 0; } - else if (x >= Bitmap->Width) return ERR_Okay; + else if (x >= Bitmap->Width) return ERR::Okay; if (y < 0) { - if ((height += y) < 1) return ERR_Okay; + if ((height += y) < 1) return ERR::Okay; y = 0; } - else if (y >= Bitmap->Height) return ERR_Okay; + else if (y >= Bitmap->Height) return ERR::Okay; // Clip the Width and Height @@ -1337,8 +1352,8 @@ ERROR update_display(extDisplay *Self, extBitmap *Bitmap, LONG X, LONG Y, LONG W if ((x + width) >= Bitmap->Width) width = Bitmap->Width - x; if ((y + height) >= Bitmap->Height) height = Bitmap->Height - y; - if (width < 1) return ERR_Okay; - if (height < 1) return ERR_Okay; + if (width < 1) return ERR::Okay; + if (height < 1) return ERR::Okay; // Adjust coordinates by offset values @@ -1361,7 +1376,7 @@ ERROR update_display(extDisplay *Self, extBitmap *Bitmap, LONG X, LONG Y, LONG W Bitmap->ColourFormat->BlueMask << Bitmap->ColourFormat->BluePos, ((Self->Flags & SCR::COMPOSITE) != SCR::NIL) ? (Bitmap->ColourFormat->AlphaMask << Bitmap->ColourFormat->AlphaPos) : 0, Self->Opacity); - return ERR_Okay; + return ERR::Okay; #else return(gfxCopyArea(Bitmap, (extBitmap *)Self->Bitmap, BAF::NIL, X, Y, Width, Height, XDest, YDest)); #endif diff --git a/src/display/display.fdl b/src/display/display.fdl index c340111cf..9c89aeabb 100644 --- a/src/display/display.fdl +++ b/src/display/display.fdl @@ -1,6 +1,6 @@ --$FLUID:Include -module({ name="Display", copyright="Paul Manias 2003-2023", version=1.0, status="stable", prefix="gfx" }, function() +module({ name="Display", copyright="Paul Manias 2003-2024", version=1.0, status="stable", prefix="gfx" }, function() restrict(function() loadFile(glPath .. 'common.fdl') @@ -370,7 +370,7 @@ module({ name="Display", copyright="Paul Manias 2003-2023", version=1.0, status= if (BitsPerPixel > 8) return packPixel(Red, Green, Blue, Alpha); else { struct bmpGetColour args = { Red, Green, Blue, Alpha }; - if (!Action(MT_BmpGetColour, this, &args)) return args.Colour; + if (Action(MT_BmpGetColour, this, &args) IS ERR::Okay) return args.Colour; return 0; } } @@ -379,7 +379,7 @@ module({ name="Display", copyright="Paul Manias 2003-2023", version=1.0, status= if (BitsPerPixel > 8) return packPixel(RGB); else { struct bmpGetColour args = { RGB.Red, RGB.Green, RGB.Blue, RGB.Alpha }; - if (!Action(MT_BmpGetColour, this, &args)) return args.Colour; + if (Action(MT_BmpGetColour, this, &args) IS ERR::Okay) return args.Colour; return 0; } } @@ -425,7 +425,7 @@ module({ name="Display", copyright="Paul Manias 2003-2023", version=1.0, status= inline ULONG packPixelWB(struct RGB8 &RGB) { return (RGB.Red << ColourFormat->RedPos) | (RGB.Green << ColourFormat->GreenPos) | (RGB.Blue << ColourFormat->BluePos) | (RGB.Alpha << ColourFormat->AlphaPos); } - + inline ULONG packPixelWB(struct RGB8 &RGB, UBYTE Alpha) { return (RGB.Red << ColourFormat->RedPos) | (RGB.Green << ColourFormat->GreenPos) | (RGB.Blue << ColourFormat->BluePos) | (Alpha << ColourFormat->AlphaPos); } @@ -571,10 +571,10 @@ module({ name="Display", copyright="Paul Manias 2003-2023", version=1.0, status= [[ // These coordinate fields are considered private but may be accessed by some internal classes, like Document LONG XOffset, YOffset; // Fixed horizontal and vertical offset - DOUBLE XOffsetPercent; // Relative horizontal offset - DOUBLE YOffsetPercent; // Relative vertical offset - DOUBLE WidthPercent, HeightPercent; // Relative width and height - DOUBLE XPercent, YPercent; // Relative coordinate + DOUBLE XOffsetPercent; // Scaled horizontal offset + DOUBLE YOffsetPercent; // Scaled vertical offset + DOUBLE WidthPercent, HeightPercent; // Scaled width and height + DOUBLE XPercent, YPercent; // Scaled coordinate ]], [[ inline bool visible() const { return (Flags & RNF::VISIBLE) != RNF::NIL; } @@ -648,24 +648,24 @@ module({ name="Display", copyright="Paul Manias 2003-2023", version=1.0, status= // Stubs -INLINE ERROR drwInvalidateRegionID(OBJECTID ObjectID, LONG X, LONG Y, LONG Width, LONG Height) { +inline ERR drwInvalidateRegionID(OBJECTID ObjectID, LONG X, LONG Y, LONG Width, LONG Height) { struct drwInvalidateRegion args = { X, Y, Width, Height }; return ActionMsg(MT_DrwInvalidateRegion, ObjectID, &args); } -INLINE ERROR drwExposeID(OBJECTID ObjectID, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags) { +inline ERR drwExposeID(OBJECTID ObjectID, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags) { struct drwExpose args = { X, Y, Width, Height, Flags }; return ActionMsg(MT_DrwExpose, ObjectID, &args); } -INLINE ERROR drwSetOpacityID(OBJECTID ObjectID, DOUBLE Value, DOUBLE Adjustment) { +inline ERR drwSetOpacityID(OBJECTID ObjectID, DOUBLE Value, DOUBLE Adjustment) { struct drwSetOpacity args = { Value, Adjustment}; return ActionMsg(MT_DrwSetOpacity, ObjectID, &args); } -INLINE ERROR drwAddCallback(OBJECTPTR Surface, APTR Callback) { +inline ERR drwAddCallback(OBJECTPTR Surface, APTR Callback) { if (Callback) { - auto call = make_function_stdc(Callback); + auto call = FUNCTION(Callback); struct drwAddCallback args = { &call }; return Action(MT_DrwAddCallback, Surface, &args); } @@ -675,9 +675,9 @@ INLINE ERROR drwAddCallback(OBJECTPTR Surface, APTR Callback) { } } -INLINE ERROR drwRemoveCallback(OBJECTPTR Surface, APTR Callback) { +inline ERR drwRemoveCallback(OBJECTPTR Surface, APTR Callback) { if (Callback) { - auto call = make_function_stdc(Callback); + auto call = FUNCTION(Callback); struct drwRemoveCallback args = { &call }; return Action(MT_DrwRemoveCallback, Surface, &args); } @@ -686,5 +686,14 @@ INLINE ERROR drwRemoveCallback(OBJECTPTR Surface, APTR Callback) { return Action(MT_DrwRemoveCallback, Surface, &args); } } + + +namespace fl { + using namespace pf; + +constexpr FieldValue WindowType(SWIN Value) { return FieldValue(FID_WindowType, LONG(Value)); } + +} // namespace + ]]) end) diff --git a/src/display/lib_bitmap.cpp b/src/display/lib_bitmap.cpp index 5bcd17ce5..5a4850b4b 100644 --- a/src/display/lib_bitmap.cpp +++ b/src/display/lib_bitmap.cpp @@ -37,7 +37,7 @@ static size_t glDitherSize = 0; } \ } -static ERROR dither(extBitmap *Bitmap, extBitmap *Dest, ColourFormat *Format, LONG Width, LONG Height, +static ERR dither(extBitmap *Bitmap, extBitmap *Dest, ColourFormat *Format, LONG Width, LONG Height, LONG SrcX, LONG SrcY, LONG DestX, LONG DestY) { pf::Log log(__FUNCTION__); @@ -50,13 +50,13 @@ static ERROR dither(extBitmap *Bitmap, extBitmap *Dest, ColourFormat *Format, LO WORD index; UBYTE rmask, gmask, bmask; - if ((Width < 1) or (Height < 1)) return ERR_Okay; + if ((Width < 1) or (Height < 1)) return ERR::Okay; // Punch the developer for making stupid mistakes if ((Dest->BitsPerPixel >= 24) and (!Format)) { log.warning("Dithering attempted to a %dbpp bitmap.", Dest->BitsPerPixel); - return ERR_Failed; + return ERR::Failed; } // Do a straight copy if the bitmap is too small for dithering @@ -68,7 +68,7 @@ static ERROR dither(extBitmap *Bitmap, extBitmap *Dest, ColourFormat *Format, LO Dest->DrawUCRPixel(Dest, x, y, &brgb); } } - return ERR_Okay; + return ERR::Okay; } // Allocate buffer for dithering @@ -76,8 +76,8 @@ static ERROR dither(extBitmap *Bitmap, extBitmap *Dest, ColourFormat *Format, LO if (Width * sizeof(RGB16) * 2 > glDitherSize) { if (glDither) { FreeResource(glDither); glDither = NULL; } - if (AllocMemory(Width * sizeof(RGB16) * 2, MEM::NO_CLEAR|MEM::UNTRACKED, &glDither) != ERR_Okay) { - return ERR_AllocMemory; + if (AllocMemory(Width * sizeof(RGB16) * 2, MEM::NO_CLEAR|MEM::UNTRACKED, &glDither) != ERR::Okay) { + return ERR::AllocMemory; } glDitherSize = Width * sizeof(RGB16) * 2; } @@ -208,7 +208,7 @@ static ERROR dither(extBitmap *Bitmap, extBitmap *Dest, ColourFormat *Format, LO } } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -231,7 +231,7 @@ will also need to have the `BMF::ALPHA_CHANNEL` flag set to indicate that an alp The quality of 32-bit alpha blending can be improved by selecting the `BAF::LINEAR` flag. This enables an additional computation whereby each RGB value is converted to linear sRGB colour space before performing the blend. The discernible value of using this option largely depends on the level of opaqueness of either bitmap. Note that this -option is not usable if either bitmap is already in a linear colourspace (`ERR_InvalidState` will be returned if that +option is not usable if either bitmap is already in a linear colourspace (`ERR::InvalidState` will be returned if that is the case). -INPUT- @@ -303,7 +303,7 @@ UBYTE validate_clip(CSTRING Header, CSTRING Name, extBitmap *Bitmap) return 0; } -ERROR gfxCopyArea(extBitmap *Bitmap, extBitmap *dest, BAF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG DestX, LONG DestY) +ERR gfxCopyArea(extBitmap *Bitmap, extBitmap *dest, BAF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG DestX, LONG DestY) { pf::Log log(__FUNCTION__); RGB8 pixel, src; @@ -312,25 +312,25 @@ ERROR gfxCopyArea(extBitmap *Bitmap, extBitmap *dest, BAF Flags, LONG X, LONG Y, ULONG colour; UBYTE *data, *srcdata; - if (!dest) return ERR_NullArgs; + if (!dest) return ERR::NullArgs; if (dest->Class->ClassID != ID_BITMAP) { log.warning("Destination #%d is not a Bitmap.", dest->UID); - return ERR_InvalidObject; + return ERR::InvalidObject; } - if (!Bitmap->initialised()) return log.warning(ERR_NotInitialised); + if (!Bitmap->initialised()) return log.warning(ERR::NotInitialised); //log.trace("%dx%d,%dx%d to %dx%d, Offset: %dx%d to %dx%d", X, Y, Width, Height, DestX, DestY, Bitmap->XOffset, Bitmap->YOffset, dest->XOffset, dest->YOffset); - if (validate_clip(__FUNCTION__, "Source", Bitmap)) return ERR_Okay; + if (validate_clip(__FUNCTION__, "Source", Bitmap)) return ERR::Okay; if (Bitmap != dest) { // Validate the clipping region of the destination - if (validate_clip(__FUNCTION__, "Dest", dest)) return ERR_Okay; + if (validate_clip(__FUNCTION__, "Dest", dest)) return ERR::Okay; } if ((Flags & BAF::LINEAR) != BAF::NIL) { - if ((Bitmap->ColourSpace IS CS::LINEAR_RGB) or (dest->ColourSpace IS CS::LINEAR_RGB)) return log.warning(ERR_InvalidState); - if ((Bitmap->BitsPerPixel != 32) or ((Bitmap->Flags & BMF::ALPHA_CHANNEL) IS BMF::NIL)) return log.warning(ERR_InvalidState); + if ((Bitmap->ColourSpace IS CS::LINEAR_RGB) or (dest->ColourSpace IS CS::LINEAR_RGB)) return log.warning(ERR::InvalidState); + if ((Bitmap->BitsPerPixel != 32) or ((Bitmap->Flags & BMF::ALPHA_CHANNEL) IS BMF::NIL)) return log.warning(ERR::InvalidState); } if (Bitmap IS dest) { // Use this clipping routine only if we are copying within the same bitmap @@ -341,7 +341,7 @@ ERROR gfxCopyArea(extBitmap *Bitmap, extBitmap *dest, BAF Flags, LONG X, LONG Y, } else if (X >= Bitmap->Clip.Right) { log.trace("Clipped: X >= Bitmap->ClipRight (%d >= %d)", X, Bitmap->Clip.Right); - return ERR_Okay; + return ERR::Okay; } if (Y < Bitmap->Clip.Top) { @@ -351,31 +351,31 @@ ERROR gfxCopyArea(extBitmap *Bitmap, extBitmap *dest, BAF Flags, LONG X, LONG Y, } else if (Y >= Bitmap->Clip.Bottom) { log.trace("Clipped: Y >= Bitmap->ClipBottom (%d >= %d)", Y, Bitmap->Clip.Bottom); - return ERR_Okay; + return ERR::Okay; } // Clip the destination coordinates if ((DestX < dest->Clip.Left)) { Width = Width - (dest->Clip.Left - DestX); - if (Width < 1) return ERR_Okay; + if (Width < 1) return ERR::Okay; X = X + (dest->Clip.Left - DestX); DestX = dest->Clip.Left; } else if (DestX >= dest->Clip.Right) { log.trace("Clipped: DestX >= RightClip (%d >= %d)", DestX, dest->Clip.Right); - return ERR_Okay; + return ERR::Okay; } if ((DestY < dest->Clip.Top)) { Height = Height - (dest->Clip.Top - DestY); - if (Height < 1) return ERR_Okay; + if (Height < 1) return ERR::Okay; Y = Y + (dest->Clip.Top - DestY); DestY = dest->Clip.Top; } else if (DestY >= dest->Clip.Bottom) { log.trace("Clipped: DestY >= BottomClip (%d >= %d)", DestY, dest->Clip.Bottom); - return ERR_Okay; + return ERR::Okay; } // Clip the Width and Height @@ -391,37 +391,37 @@ ERROR gfxCopyArea(extBitmap *Bitmap, extBitmap *dest, BAF Flags, LONG X, LONG Y, if (DestX < dest->Clip.Left) { Width = Width - (dest->Clip.Left - DestX); - if (Width < 1) return ERR_Okay; + if (Width < 1) return ERR::Okay; X = X + (dest->Clip.Left - DestX); DestX = dest->Clip.Left; } - else if (DestX >= dest->Clip.Right) return ERR_Okay; + else if (DestX >= dest->Clip.Right) return ERR::Okay; if (DestY < dest->Clip.Top) { Height = Height - (dest->Clip.Top - DestY); - if (Height < 1) return ERR_Okay; + if (Height < 1) return ERR::Okay; Y = Y + (dest->Clip.Top - DestY); DestY = dest->Clip.Top; } - else if (DestY >= dest->Clip.Bottom) return ERR_Okay; + else if (DestY >= dest->Clip.Bottom) return ERR::Okay; // Check if the source that we are copying from is within its own drawable area. if (X < Bitmap->Clip.Left) { DestX += (Bitmap->Clip.Left - X); Width = Width - (Bitmap->Clip.Left - X); - if (Width < 1) return ERR_Okay; + if (Width < 1) return ERR::Okay; X = Bitmap->Clip.Left; } - else if (X >= Bitmap->Clip.Right) return ERR_Okay; + else if (X >= Bitmap->Clip.Right) return ERR::Okay; if (Y < Bitmap->Clip.Top) { DestY += (Bitmap->Clip.Top - Y); Height = Height - (Bitmap->Clip.Top - Y); - if (Height < 1) return ERR_Okay; + if (Height < 1) return ERR::Okay; Y = Bitmap->Clip.Top; } - else if (Y >= Bitmap->Clip.Bottom) return ERR_Okay; + else if (Y >= Bitmap->Clip.Bottom) return ERR::Okay; // Clip the Width and Height of the source area, based on the imposed clip region. @@ -431,8 +431,8 @@ ERROR gfxCopyArea(extBitmap *Bitmap, extBitmap *dest, BAF Flags, LONG X, LONG Y, if ((Y + Height) >= Bitmap->Clip.Bottom) Height = Bitmap->Clip.Bottom - Y; } - if (Width < 1) return ERR_Okay; - if (Height < 1) return ERR_Okay; + if (Width < 1) return ERR::Okay; + if (Height < 1) return ERR::Okay; // Adjust coordinates by offset values @@ -516,7 +516,7 @@ ERROR gfxCopyArea(extBitmap *Bitmap, extBitmap *dest, BAF Flags, LONG X, LONG Y, } } - return ERR_Okay; + return ERR::Okay; } #elif __xwindows__ @@ -582,17 +582,19 @@ ERROR gfxCopyArea(extBitmap *Bitmap, extBitmap *dest, BAF Flags, LONG X, LONG Y, } else XPutImage(XDisplay, dest->x11.drawable, dest->getGC(), &Bitmap->x11.ximage, X, Y, DestX, DestY, Width, Height); - XSync(XDisplay, False); // Essential because the graphics won't otherwise be immediately pushed to the display. + if ((Bitmap->Flags & BMF::ALPHA_CHANNEL) != BMF::NIL) { // Composite window + XSync(XDisplay, False); + } + else XClearWindow(XDisplay, dest->x11.window); // 'Clear' the window to the pixmap background if ((Bitmap->Flags & BMF::ALPHA_CHANNEL) != BMF::NIL) bmpDemultiply(Bitmap); } } else { // Both the source and the destination are pixmaps - XCopyArea(XDisplay, Bitmap->x11.drawable, dest->x11.drawable, - dest->getGC(), X, Y, Width, Height, DestX, DestY); + XCopyArea(XDisplay, Bitmap->x11.drawable, dest->x11.drawable, dest->getGC(), X, Y, Width, Height, DestX, DestY); } - return ERR_Okay; + return ERR::Okay; } #elif _GLES_ @@ -601,7 +603,7 @@ ERROR gfxCopyArea(extBitmap *Bitmap, extBitmap *dest, BAF Flags, LONG X, LONG Y, if ((Bitmap->DataFlags & MEM::VIDEO) != MEM::NIL) { // Source is the video display. // No simple way to support this in OpenGL - we have to copy the display into a texture buffer, then copy the texture back to the display. - ERROR error; + ERR error; if (!lock_graphics_active(__func__)) { GLuint texture; if (alloc_texture(Bitmap->Width, Bitmap->Height, &texture) IS GL_NO_ERROR) { @@ -612,13 +614,13 @@ ERROR gfxCopyArea(extBitmap *Bitmap, extBitmap *dest, BAF Flags, LONG X, LONG Y, glBindTexture(GL_TEXTURE_2D, 0); eglSwapBuffers(glEGLDisplay, glEGLSurface); glDeleteTextures(1, &texture); - error = ERR_Okay; + error = ERR::Okay; } - else error = log.warning(ERR_OpenGL); + else error = log.warning(ERR::OpenGL); unlock_graphics(); } - else error = ERR_LockFailed; + else error = ERR::LockFailed; return error; } @@ -630,7 +632,7 @@ ERROR gfxCopyArea(extBitmap *Bitmap, extBitmap *dest, BAF Flags, LONG X, LONG Y, else { // RAM-to-video blitting. We have to allocate a temporary texture, copy the data to it and then blit that to the display. - ERROR error; + ERR error; if (!lock_graphics_active(__func__)) { GLuint texture; if (alloc_texture(Bitmap->Width, Bitmap->Height, &texture) IS GL_NO_ERROR) { @@ -640,16 +642,16 @@ ERROR gfxCopyArea(extBitmap *Bitmap, extBitmap *dest, BAF Flags, LONG X, LONG Y, glBindTexture(GL_TEXTURE_2D, 0); eglSwapBuffers(glEGLDisplay, glEGLSurface); } - else error = ERR_OpenGL; + else error = ERR::OpenGL; glDeleteTextures(1, &texture); - error = ERR_Okay; + error = ERR::Okay; } - else error = log.warning(ERR_OpenGL); + else error = log.warning(ERR::OpenGL); unlock_graphics(); } - else error = ERR_LockFailed; + else error = ERR::LockFailed; return error; } @@ -662,8 +664,8 @@ ERROR gfxCopyArea(extBitmap *Bitmap, extBitmap *dest, BAF Flags, LONG X, LONG Y, if (((Flags & BAF::BLEND) != BAF::NIL) and (Bitmap->BitsPerPixel IS 32) and ((Bitmap->Flags & BMF::ALPHA_CHANNEL) != BMF::NIL)) { // 32-bit alpha blending support - if (!lock_surface(Bitmap, SURFACE_READ)) { - if (!lock_surface(dest, SURFACE_WRITE)) { + if (lock_surface(Bitmap, SURFACE_READ) IS ERR::Okay) { + if (lock_surface(dest, SURFACE_WRITE) IS ERR::Okay) { UBYTE red, green, blue, *dest_lookup; UWORD alpha; @@ -894,13 +896,13 @@ ERROR gfxCopyArea(extBitmap *Bitmap, extBitmap *dest, BAF Flags, LONG X, LONG Y, unlock_surface(Bitmap); } - return ERR_Okay; + return ERR::Okay; } else if ((Bitmap->Flags & BMF::TRANSPARENT) != BMF::NIL) { // Transparent colour copying. In this mode, the alpha component of individual source pixels is ignored - if (!lock_surface(Bitmap, SURFACE_READ)) { - if (!lock_surface(dest, SURFACE_WRITE)) { + if (lock_surface(Bitmap, SURFACE_READ) IS ERR::Okay) { + if (lock_surface(dest, SURFACE_WRITE) IS ERR::Okay) { if (Bitmap->Opacity < 255) { // Transparent mask with translucent pixels (consistent blend level) srctable = glAlphaLookup.data() + (Bitmap->Opacity<<8); desttable = glAlphaLookup.data() + ((255-Bitmap->Opacity)<<8); @@ -987,11 +989,11 @@ ERROR gfxCopyArea(extBitmap *Bitmap, extBitmap *dest, BAF Flags, LONG X, LONG Y, unlock_surface(Bitmap); } - return ERR_Okay; + return ERR::Okay; } else { // Straight copy operation - if (!lock_surface(Bitmap, SURFACE_READ)) { - if (!lock_surface(dest, SURFACE_WRITE)) { + if (lock_surface(Bitmap, SURFACE_READ) IS ERR::Okay) { + if (lock_surface(dest, SURFACE_WRITE) IS ERR::Okay) { if (Bitmap->Opacity < 255) { // Translucent draw srctable = glAlphaLookup.data() + (Bitmap->Opacity<<8); desttable = glAlphaLookup.data() + ((255-Bitmap->Opacity)<<8); @@ -1125,7 +1127,7 @@ ERROR gfxCopyArea(extBitmap *Bitmap, extBitmap *dest, BAF Flags, LONG X, LONG Y, unlock_surface(Bitmap); } - return ERR_Okay; + return ERR::Okay; } } @@ -1192,7 +1194,7 @@ static ULONG read_surface32(BITMAPSURFACE *Surface, WORD X, WORD Y) return ((ULONG *)((UBYTE *)Surface->Data + (Surface->LineWidth * Y) + (X<<2)))[0]; } -ERROR gfxCopyRawBitmap(BITMAPSURFACE *Surface, extBitmap *Bitmap, +ERR gfxCopyRawBitmap(BITMAPSURFACE *Surface, extBitmap *Bitmap, CSRF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) { @@ -1205,10 +1207,10 @@ ERROR gfxCopyRawBitmap(BITMAPSURFACE *Surface, extBitmap *Bitmap, UBYTE *data, *srcdata; ULONG (*read_surface)(BITMAPSURFACE *, WORD, WORD); - if ((!Surface) or (!Bitmap)) return log.warning(ERR_NullArgs); + if ((!Surface) or (!Bitmap)) return log.warning(ERR::NullArgs); if ((!Surface->Data) or (Surface->LineWidth < 1) or (!Surface->BitsPerPixel)) { - return log.warning(ERR_Args); + return log.warning(ERR::Args); } srcwidth = Surface->LineWidth / Surface->BytesPerPixel; @@ -1217,34 +1219,34 @@ ERROR gfxCopyRawBitmap(BITMAPSURFACE *Surface, extBitmap *Bitmap, if ((XDest < Bitmap->Clip.Left)) { Width = Width - (Bitmap->Clip.Left - X); - if (Width < 1) return ERR_Okay; + if (Width < 1) return ERR::Okay; X = X + (Bitmap->Clip.Left - X); XDest = Bitmap->Clip.Left; } - else if (XDest >= Bitmap->Clip.Right) return ERR_Okay; + else if (XDest >= Bitmap->Clip.Right) return ERR::Okay; if ((YDest < Bitmap->Clip.Top)) { Height = Height - (Bitmap->Clip.Top - YDest); - if (Height < 1) return ERR_Okay; + if (Height < 1) return ERR::Okay; Y = Y + (Bitmap->Clip.Top - YDest); YDest = Bitmap->Clip.Top; } - else if (YDest >= Bitmap->Clip.Bottom) return ERR_Okay; + else if (YDest >= Bitmap->Clip.Bottom) return ERR::Okay; // Check if the source that we are blitting from is within its own drawable area. if ((Flags & CSRF::CLIP) != CSRF::NIL) { if (X < 0) { - if ((Width += X) < 1) return ERR_Okay; + if ((Width += X) < 1) return ERR::Okay; X = 0; } - else if (X >= srcwidth) return ERR_Okay; + else if (X >= srcwidth) return ERR::Okay; if (Y < 0) { - if ((Height += Y) < 1) return ERR_Okay; + if ((Height += Y) < 1) return ERR::Okay; Y = 0; } - else if (Y >= Surface->Height) return ERR_Okay; + else if (Y >= Surface->Height) return ERR::Okay; } // Clip the width and height @@ -1257,8 +1259,8 @@ ERROR gfxCopyRawBitmap(BITMAPSURFACE *Surface, extBitmap *Bitmap, if ((Y + Height) >= Surface->Clip.Bottom) Height = Surface->Clip.Bottom - Y; } - if (Width < 1) return ERR_Okay; - if (Height < 1) return ERR_Okay; + if (Width < 1) return ERR::Okay; + if (Height < 1) return ERR::Okay; // Adjust coordinates by offset values @@ -1279,7 +1281,7 @@ ERROR gfxCopyRawBitmap(BITMAPSURFACE *Surface, extBitmap *Bitmap, else read_surface = read_surface_msb24; break; case 4: read_surface = read_surface32; break; - default: return log.warning(ERR_Args); + default: return log.warning(ERR::Args); } #ifdef __xwindows__ @@ -1318,12 +1320,12 @@ ERROR gfxCopyRawBitmap(BITMAPSURFACE *Surface, extBitmap *Bitmap, XPutImage(XDisplay, Bitmap->x11.drawable, Bitmap->getGC(), &ximage, X, Y, XDest, YDest, Width, Height); - return ERR_Okay; + return ERR::Okay; } #endif // __xwindows__ - if (lock_surface(Bitmap, SURFACE_WRITE) IS ERR_Okay) { + if (lock_surface(Bitmap, SURFACE_WRITE) IS ERR::Okay) { if (((Flags & CSRF::ALPHA) != CSRF::NIL) and (Surface->BitsPerPixel IS 32)) { // 32-bit alpha blending support ULONG *sdata = (ULONG *)((BYTE *)Surface->Data + (Y * Surface->LineWidth) + (X<<2)); @@ -1563,7 +1565,7 @@ ERROR gfxCopyRawBitmap(BITMAPSURFACE *Surface, extBitmap *Bitmap, unlock_surface(Bitmap); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1611,7 +1613,7 @@ void gfxDrawRectangle(extBitmap *Bitmap, LONG X, LONG Y, LONG Width, LONG Height return; } - if (!Bitmap->initialised()) { log.warning(ERR_NotInitialised); return; } + if (!Bitmap->initialised()) { log.warning(ERR::NotInitialised); return; } X += Bitmap->XOffset; Y += Bitmap->YOffset; @@ -1644,7 +1646,7 @@ void gfxDrawRectangle(extBitmap *Bitmap, LONG X, LONG Y, LONG Width, LONG Height UBYTE opacity = ((Flags & BAF::BLEND) != BAF::NIL) ? Bitmap->unpackAlpha(Colour) : Bitmap->Opacity; if (opacity < 255) { - if (!lock_surface(Bitmap, SURFACE_READWRITE)) { + if (lock_surface(Bitmap, SURFACE_READWRITE) IS ERR::Okay) { UWORD wordpixel; if (Bitmap->BitsPerPixel IS 32) { @@ -1777,7 +1779,7 @@ void gfxDrawRectangle(extBitmap *Bitmap, LONG X, LONG Y, LONG Width, LONG Height // Standard rectangle data support - if (!lock_surface(Bitmap, SURFACE_WRITE)) { + if (lock_surface(Bitmap, SURFACE_WRITE) IS ERR::Okay) { if (!Bitmap->Data) { unlock_surface(Bitmap); return; @@ -2094,12 +2096,12 @@ NullArgs *********************************************************************************************************************/ -ERROR gfxResample(extBitmap *Bitmap, ColourFormat *Format) +ERR gfxResample(extBitmap *Bitmap, ColourFormat *Format) { - if ((!Bitmap) or (!Format)) return ERR_NullArgs; + if ((!Bitmap) or (!Format)) return ERR::NullArgs; dither(Bitmap, Bitmap, Format, Bitmap->Width, Bitmap->Height, 0, 0, 0, 0); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* diff --git a/src/display/lib_cursor.cpp b/src/display/lib_cursor.cpp index f20c4cdb0..b12681760 100644 --- a/src/display/lib_cursor.cpp +++ b/src/display/lib_cursor.cpp @@ -138,14 +138,14 @@ objPointer * gfxAccessPointer(void) objPointer *pointer = NULL; if (!glPointerID) { - if (!FindObject("SystemPointer", ID_POINTER, FOF::NIL, &glPointerID)) { + if (FindObject("SystemPointer", ID_POINTER, FOF::NIL, &glPointerID) IS ERR::Okay) { AccessObject(glPointerID, 2000, &pointer); } return pointer; } - if (AccessObject(glPointerID, 2000, &pointer) IS ERR_NoMatchingObject) { - if (!FindObject("SystemPointer", ID_POINTER, FOF::NIL, &glPointerID)) { + if (AccessObject(glPointerID, 2000, &pointer) IS ERR::NoMatchingObject) { + if (FindObject("SystemPointer", ID_POINTER, FOF::NIL, &glPointerID) IS ERR::Okay) { AccessObject(glPointerID, 2000, &pointer); } } @@ -180,20 +180,20 @@ NoSupport: The device does not support a cursor (common for touch screen display *********************************************************************************************************************/ -ERROR gfxGetCursorInfo(CursorInfo *Info, LONG Size) +ERR gfxGetCursorInfo(CursorInfo *Info, LONG Size) { - if (!Info) return ERR_NullArgs; + if (!Info) return ERR::NullArgs; #ifdef __ANDROID__ // TODO: Some Android devices probably do support a mouse or similar input device. ClearMemory(Info, sizeof(CursorInfo)); - return ERR_NoSupport; + return ERR::NoSupport; #else Info->Width = 32; Info->Height = 32; Info->BitsPerPixel = 1; Info->Flags = 0; - return ERR_Okay; + return ERR::Okay; #endif } @@ -202,12 +202,12 @@ ERROR gfxGetCursorInfo(CursorInfo *Info, LONG Size) -FUNCTION- GetCursorPos: Returns the coordinates of the UI pointer. -This function is used to retrieve the current coordinates of the user interface pointer. If the device is touch-screen -based then the coordinates will reflect the last position that a touch event occurred. +This function will return the current coordinates of the mouse cursor. If the device is touch-screen based then the +coordinates will reflect the last position that a touch event occurred. -INPUT- -&double X: 32-bit variable that will store the pointer's horizontal coordinate. -&double Y: 32-bit variable that will store the pointer's vertical coordinate. +&double X: Variable that will store the pointer's horizontal coordinate. +&double Y: Variable that will store the pointer's vertical coordinate. -ERRORS- Okay @@ -215,7 +215,7 @@ AccessObject: Failed to access the SystemPointer object. *********************************************************************************************************************/ -ERROR gfxGetCursorPos(DOUBLE *X, DOUBLE *Y) +ERR gfxGetCursorPos(DOUBLE *X, DOUBLE *Y) { objPointer *pointer; @@ -223,12 +223,12 @@ ERROR gfxGetCursorPos(DOUBLE *X, DOUBLE *Y) if (X) *X = pointer->X; if (Y) *Y = pointer->Y; ReleaseObject(pointer); - return ERR_Okay; + return ERR::Okay; } else { pf::Log log(__FUNCTION__); log.warning("Failed to grab the mouse pointer."); - return ERR_Failed; + return ERR::Failed; } } @@ -244,8 +244,8 @@ The X and Y parameters will not be set if a failure occurs. -INPUT- oid Surface: Unique ID of the surface that the coordinates need to be relative to. -&double X: 32-bit variable that will store the pointer's horizontal coordinate. -&double Y: 32-bit variable that will store the pointer's vertical coordinate. +&double X: Variable that will store the pointer's horizontal coordinate. +&double Y: Variable that will store the pointer's vertical coordinate. -ERRORS- Okay: @@ -253,15 +253,15 @@ AccessObject: Failed to access the SystemPointer object. *********************************************************************************************************************/ -ERROR gfxGetRelativeCursorPos(OBJECTID SurfaceID, DOUBLE *X, DOUBLE *Y) +ERR gfxGetRelativeCursorPos(OBJECTID SurfaceID, DOUBLE *X, DOUBLE *Y) { pf::Log log(__FUNCTION__); objPointer *pointer; LONG absx, absy; - if (get_surface_abs(SurfaceID, &absx, &absy, 0, 0) != ERR_Okay) { + if (get_surface_abs(SurfaceID, &absx, &absy, 0, 0) != ERR::Okay) { log.warning("Failed to get info for surface #%d.", SurfaceID); - return ERR_Failed; + return ERR::Failed; } if ((pointer = gfxAccessPointer())) { @@ -269,11 +269,11 @@ ERROR gfxGetRelativeCursorPos(OBJECTID SurfaceID, DOUBLE *X, DOUBLE *Y) if (Y) *Y = pointer->Y - absy; ReleaseObject(pointer); - return ERR_Okay; + return ERR::Okay; } else { log.warning("Failed to grab the mouse pointer."); - return ERR_AccessObject; + return ERR::AccessObject; } } @@ -301,9 +301,9 @@ AccessObject: Failed to access the pointer object. *********************************************************************************************************************/ -ERROR gfxLockCursor(OBJECTID SurfaceID) +ERR gfxLockCursor(OBJECTID SurfaceID) { - return ERR_NoSupport; + return ERR::NoSupport; } /********************************************************************************************************************* @@ -328,12 +328,11 @@ Args *********************************************************************************************************************/ -ERROR gfxRestoreCursor(PTC Cursor, OBJECTID OwnerID) +ERR gfxRestoreCursor(PTC Cursor, OBJECTID OwnerID) { pf::Log log(__FUNCTION__); - extPointer *pointer; - if ((pointer = (extPointer *)gfxAccessPointer())) { + if (auto pointer = (extPointer *)gfxAccessPointer()) { /* OBJECTPTR caller; caller = CurrentContext(); @@ -359,12 +358,9 @@ ERROR gfxRestoreCursor(PTC Cursor, OBJECTID OwnerID) } ReleaseObject(pointer); - return ERR_Okay; - } - else { - log.warning("Failed to access the mouse pointer."); - return ERR_AccessObject; + return ERR::Okay; } + else return ERR::Okay; // The cursor not existing is not necessarily a problem. } /********************************************************************************************************************* @@ -404,7 +400,7 @@ AccessObject: Failed to access the internally maintained image object. *********************************************************************************************************************/ -ERROR gfxSetCursor(OBJECTID ObjectID, CRF Flags, PTC CursorID, CSTRING Name, OBJECTID OwnerID) +ERR gfxSetCursor(OBJECTID ObjectID, CRF Flags, PTC CursorID, CSTRING Name, OBJECTID OwnerID) { pf::Log log(__FUNCTION__); extPointer *pointer; @@ -413,16 +409,16 @@ ERROR gfxSetCursor(OBJECTID ObjectID, CRF Flags, PTC CursorID, CSTRING Name, OBJ /* if (!OwnerID) { log.warning("An Owner must be provided to this function."); - return ERR_Args; + return ERR::Args; } */ // Validate the cursor ID - if ((LONG(CursorID) < 0) or (LONG(CursorID) >= LONG(PTC::END))) return log.warning(ERR_OutOfRange); + if ((LONG(CursorID) < 0) or (LONG(CursorID) >= LONG(PTC::END))) return log.warning(ERR::OutOfRange); if (!(pointer = (extPointer *)gfxAccessPointer())) { log.warning("Failed to access the mouse pointer."); - return ERR_AccessObject; + return ERR::AccessObject; } if (Name) log.traceBranch("Object: %d, Flags: $%.8x, Owner: %d (Current %d), Cursor: %s", ObjectID, LONG(Flags), OwnerID, pointer->CursorOwnerID, Name); @@ -433,7 +429,7 @@ ERROR gfxSetCursor(OBJECTID ObjectID, CRF Flags, PTC CursorID, CSTRING Name, OBJ if (CursorID IS PTC::NIL) { if (Name) { for (LONG i=0; CursorLookup[i].Name; i++) { - if (!StrMatch(CursorLookup[i].Name, Name)) { + if (StrMatch(CursorLookup[i].Name, Name) IS ERR::Okay) { CursorID = PTC(CursorLookup[i].Value); break; } @@ -445,23 +441,23 @@ ERROR gfxSetCursor(OBJECTID ObjectID, CRF Flags, PTC CursorID, CSTRING Name, OBJ // Return if the cursor is currently pwn3d by someone if ((pointer->CursorOwnerID) and (pointer->CursorOwnerID != OwnerID)) { - if ((pointer->CursorOwnerID < 0) and (CheckObjectExists(pointer->CursorOwnerID) != ERR_True)) pointer->CursorOwnerID = 0; + if ((pointer->CursorOwnerID < 0) and (CheckObjectExists(pointer->CursorOwnerID) != ERR::True)) pointer->CursorOwnerID = 0; else if ((Flags & CRF::BUFFER) != CRF::NIL) { // If the BUFFER option is used, then we can buffer the change so that it // will be activated as soon as the current holder releases the cursor. - log.extmsg("Request buffered, pointer owned by #%d.", pointer->CursorOwnerID); + log.detail("Request buffered, pointer owned by #%d.", pointer->CursorOwnerID); pointer->BufferCursor = CursorID; pointer->BufferOwner = OwnerID; pointer->BufferFlags = Flags; pointer->BufferObject = ObjectID; ReleaseObject(pointer); - return ERR_Okay; + return ERR::Okay; } else { ReleaseObject(pointer); - return ERR_LockFailed; // The pointer is locked by someone else + return ERR::LockFailed; // The pointer is locked by someone else } } @@ -472,7 +468,7 @@ ERROR gfxSetCursor(OBJECTID ObjectID, CRF Flags, PTC CursorID, CSTRING Name, OBJ if ((Flags & CRF::NO_BUTTONS) != CRF::NIL) { if ((pointer->Buttons[0].LastClicked) or (pointer->Buttons[1].LastClicked) or (pointer->Buttons[2].LastClicked)) { ReleaseObject(pointer); - return ERR_NothingDone; + return ERR::NothingDone; } } @@ -504,7 +500,7 @@ ERROR gfxSetCursor(OBJECTID ObjectID, CRF Flags, PTC CursorID, CSTRING Name, OBJ if ((pointer->SurfaceID) and (!AccessObject(pointer->SurfaceID, 1000, &surface))) { if ((surface->DisplayID) and (!AccessObject(surface->DisplayID, 1000, &display))) { - if ((display->getPtr(FID_WindowHandle, &xwin) IS ERR_Okay) and (xwin)) { + if ((display->getPtr(FID_WindowHandle, &xwin) IS ERR::Okay) and (xwin)) { xcursor = get_x11_cursor(CursorID); XDefineCursor(XDisplay, (Window)xwin, xcursor); XFlush(XDisplay); @@ -569,7 +565,7 @@ ERROR gfxSetCursor(OBJECTID ObjectID, CRF Flags, PTC CursorID, CSTRING Name, OBJ } ReleaseObject(pointer); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -627,7 +623,7 @@ AccessObject: Failed to access the internally maintained image object. *********************************************************************************************************************/ -ERROR gfxSetCustomCursor(OBJECTID ObjectID, CRF Flags, objBitmap *Bitmap, LONG HotX, LONG HotY, OBJECTID OwnerID) +ERR gfxSetCustomCursor(OBJECTID ObjectID, CRF Flags, objBitmap *Bitmap, LONG HotX, LONG HotY, OBJECTID OwnerID) { // If the driver doesn't support custom cursors then divert to gfxSetCursor() return gfxSetCursor(ObjectID, Flags, PTC::DEFAULT, NULL, OwnerID); @@ -650,7 +646,7 @@ AccessObject: Failed to access the SystemPointer object. *********************************************************************************************************************/ -ERROR gfxSetCursorPos(DOUBLE X, DOUBLE Y) +ERR gfxSetCursorPos(DOUBLE X, DOUBLE Y) { struct acMoveToPoint move = { X, Y, 0, MTF::X|MTF::Y }; if (auto pointer = gfxAccessPointer()) { @@ -659,7 +655,7 @@ ERROR gfxSetCursorPos(DOUBLE X, DOUBLE Y) } else ActionMsg(AC_MoveToPoint, glPointerID, &move); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -704,23 +700,23 @@ InUse: A drag and drop operation has already been started. *********************************************************************************************************************/ -ERROR gfxStartCursorDrag(OBJECTID Source, LONG Item, CSTRING Datatypes, OBJECTID Surface) +ERR gfxStartCursorDrag(OBJECTID Source, LONG Item, CSTRING Datatypes, OBJECTID Surface) { pf::Log log(__FUNCTION__); log.branch("Source: %d, Item: %d, Surface: %d", Source, Item, Surface); - if (!Source) return log.warning(ERR_NullArgs); + if (!Source) return log.warning(ERR::NullArgs); if (auto pointer = (extPointer *)gfxAccessPointer()) { if (!pointer->Buttons[0].LastClicked) { gfxReleasePointer(pointer); - return log.warning(ERR_Failed); + return log.warning(ERR::Failed); } if (pointer->DragSourceID) { gfxReleasePointer(pointer); - return ERR_InUse; + return ERR::InUse; } pointer->DragSurface = Surface; @@ -729,7 +725,7 @@ ERROR gfxStartCursorDrag(OBJECTID Source, LONG Item, CSTRING Datatypes, OBJECTID StrCopy(Datatypes, pointer->DragData, sizeof(pointer->DragData)); SURFACEINFO *info; - if (!gfxGetSurfaceInfo(Surface, &info)) { + if (gfxGetSurfaceInfo(Surface, &info) IS ERR::Okay) { pointer->DragParent = info->ParentID; } @@ -741,9 +737,9 @@ ERROR gfxStartCursorDrag(OBJECTID Source, LONG Item, CSTRING Datatypes, OBJECTID } gfxReleasePointer(pointer); - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } /********************************************************************************************************************* @@ -765,26 +761,26 @@ NotLocked: A lock is not present, or the lock belongs to another surface. *********************************************************************************************************************/ -ERROR gfxUnlockCursor(OBJECTID SurfaceID) +ERR gfxUnlockCursor(OBJECTID SurfaceID) { pf::Log log(__FUNCTION__); - if (!SurfaceID) return log.warning(ERR_NullArgs); + if (!SurfaceID) return log.warning(ERR::NullArgs); if (auto pointer = (extPointer *)gfxAccessPointer()) { if (pointer->AnchorID IS SurfaceID) { pointer->AnchorID = 0; ReleaseObject(pointer); - return ERR_Okay; + return ERR::Okay; } else { ReleaseObject(pointer); - return ERR_NotLocked; + return ERR::NotLocked; } } else { log.warning("Failed to access the mouse pointer."); - return ERR_AccessObject; + return ERR::AccessObject; } } diff --git a/src/display/lib_display.cpp b/src/display/lib_display.cpp index 83d17a89c..a7954b7ac 100644 --- a/src/display/lib_display.cpp +++ b/src/display/lib_display.cpp @@ -33,24 +33,23 @@ oid Display: Object ID of the display to be analysed. *********************************************************************************************************************/ -ERROR gfxGetDisplayInfo(OBJECTID DisplayID, DISPLAYINFO **Result) +ERR gfxGetDisplayInfo(OBJECTID DisplayID, DISPLAYINFO **Result) { static THREADVAR DISPLAYINFO *t_info = NULL; - if (!Result) return ERR_NullArgs; + if (!Result) return ERR::NullArgs; if (!t_info) { // Each thread gets an allocation that can't be resource tracked, so MEM::HIDDEN is used in this case. // Note that this could conceivably cause memory leaks if temporary threads were to use this function. - if (AllocMemory(sizeof(DISPLAYINFO), MEM::NO_CLEAR|MEM::HIDDEN, &t_info)) { - return ERR_AllocMemory; + if (AllocMemory(sizeof(DISPLAYINFO), MEM::NO_CLEAR|MEM::HIDDEN, &t_info) != ERR::Okay) { + return ERR::AllocMemory; } } - ERROR error; - if (!(error = get_display_info(DisplayID, t_info, sizeof(DISPLAYINFO)))) { + if (auto error = get_display_info(DisplayID, t_info, sizeof(DISPLAYINFO)); error IS ERR::Okay) { *Result = t_info; - return ERR_Okay; + return ERR::Okay; } else return error; } @@ -110,7 +109,7 @@ Search: There are no more display modes to return that are a match for the Filte *********************************************************************************************************************/ -ERROR gfxScanDisplayModes(CSTRING Filter, DISPLAYINFO *Info, LONG Size) +ERR gfxScanDisplayModes(CSTRING Filter, DISPLAYINFO *Info, LONG Size) { #ifdef __snap__ @@ -125,7 +124,7 @@ ERROR gfxScanDisplayModes(CSTRING Filter, DISPLAYINFO *Info, LONG Size) WORD f_maxrefresh, c_maxrefresh; BYTE interlace, matched; - if ((!Info) or (Size < sizeof(DisplayInfoV3))) return ERR_Args; + if ((!Info) or (Size < sizeof(DisplayInfoV3))) return ERR::Args; // Reset all filters @@ -216,14 +215,14 @@ ERROR gfxScanDisplayModes(CSTRING Filter, DISPLAYINFO *Info, LONG Size) Info->MaxRefresh = maxrefresh; Info->RefreshRate = refresh; Info->Index = i + 1; - return ERR_Okay; + return ERR::Okay; } - return ERR_Search; + return ERR::Search; #else - return ERR_NoSupport; + return ERR::NoSupport; #endif } @@ -244,7 +243,7 @@ Okay *********************************************************************************************************************/ -ERROR gfxSetHostOption(HOST Option, LARGE Value) +ERR gfxSetHostOption(HOST Option, LARGE Value) { #if defined(_WIN32) || defined(__xwindows__) pf::Log log(__FUNCTION__); @@ -269,7 +268,7 @@ ERROR gfxSetHostOption(HOST Option, LARGE Value) } #endif - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* diff --git a/src/display/lib_input.cpp b/src/display/lib_input.cpp index 6a12bc76a..a3289fa1a 100644 --- a/src/display/lib_input.cpp +++ b/src/display/lib_input.cpp @@ -17,7 +17,7 @@ EventBuffer glInputEvents; -FUNCTION- GetInputTypeName: Returns the string name for an input type. -This function converts JET integer constants to their string equivalent. +This function converts `JET` integer constants to their string equivalent. -INPUT- int(JET) Type: JET type integer. @@ -51,7 +51,7 @@ A callback is required for receiving the input events. The following C++ code i events in the callback:
    -ERROR consume_input_events(const InputEvent *Events, LONG Handle)
    +ERR consume_input_events(const InputEvent *Events, LONG Handle)
     {
        for (auto e=Events; e; e=e->Next) {
           if (((e->Flags & JTYPE::BUTTON) != JTYPE::NIL) and (e->Value > 0)) {
    @@ -59,19 +59,19 @@ ERROR consume_input_events(const InputEvent *Events, LONG Handle)
           }
        }
     
    -   return ERR_Okay;
    +   return ERR::Okay;
     }
     
    All processable events are referenced in the InputEvent structure in the Events parameter. -JET constants are as follows and take note of `ENTERED_SURFACE` and `LEFT_SURFACE` which are software generated and not +`JET` constants are as follows and take note of `CROSSED_IN` and `CROSSED_OUT` which are software generated and not a device event: -The JTYPE values for the Flags field are as follows. Note that these flags also serve as input masks for the -SubscribeInput() function, so to receive a message of the given type the appropriate JTYPE flag must have been set in the +The `JTYPE` values for the Flags field are as follows. Note that these flags also serve as input masks for the +SubscribeInput() function, so to receive a message of the given type the appropriate `JTYPE` flag must have been set in the original subscription call. @@ -89,12 +89,12 @@ oid DeviceFilter: Optional. Only the input messages that match the given device *********************************************************************************************************************/ -ERROR gfxSubscribeInput(FUNCTION *Callback, OBJECTID SurfaceFilter, JTYPE InputMask, OBJECTID DeviceFilter, LONG *Handle) +ERR gfxSubscribeInput(FUNCTION *Callback, OBJECTID SurfaceFilter, JTYPE InputMask, OBJECTID DeviceFilter, LONG *Handle) { static LONG counter = 1; pf::Log log(__FUNCTION__); - if ((!Callback) or (!Handle)) return log.warning(ERR_NullArgs); + if ((!Callback) or (!Handle)) return log.warning(ERR::NullArgs); log.branch("Surface Filter: #%d, Mask: $%.4x", SurfaceFilter, LONG(InputMask)); @@ -111,7 +111,7 @@ ERROR gfxSubscribeInput(FUNCTION *Callback, OBJECTID SurfaceFilter, JTYPE InputM if (glInputEvents.processing) glNewSubscriptions.push_back(std::make_pair(*Handle, is)); else glInputCallbacks.emplace(*Handle, is); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -132,18 +132,18 @@ NotFound *********************************************************************************************************************/ -ERROR gfxUnsubscribeInput(LONG Handle) +ERR gfxUnsubscribeInput(LONG Handle) { pf::Log log(__FUNCTION__); - if (!Handle) return log.warning(ERR_NullArgs); + if (!Handle) return log.warning(ERR::NullArgs); log.branch("Handle: %d", Handle); const std::lock_guard lock(glInputLock); auto it = glInputCallbacks.find(Handle); - if (it IS glInputCallbacks.end()) return log.warning(ERR_NotFound); + if (it IS glInputCallbacks.end()) return log.warning(ERR::NotFound); else { if (glInputEvents.processing) { // Cannot erase during input processing ClearMemory(&it->second, sizeof(it->second)); @@ -151,7 +151,7 @@ ERROR gfxUnsubscribeInput(LONG Handle) else glInputCallbacks.erase(it); } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -192,21 +192,21 @@ void input_event_loop(HOSTHANDLE FD, APTR Data) // Data is not defined glInputLock.unlock(); auto &cb = sub.Callback; - if (cb.Type IS CALL_STDC) { + if (sub.Callback.isC()) { pf::ScopedObjectLock lock(cb.StdC.Context, 2000); // Ensure that the object can't be removed until after input processing if (lock.granted()) { pf::SwitchContext ctx(cb.StdC.Context); - auto func = (ERROR (*)(InputEvent *, LONG))cb.StdC.Routine; - func(first, handle); + auto func = (ERR (*)(InputEvent *, LONG, APTR))cb.StdC.Routine; + func(first, handle, cb.StdC.Meta); } } - else if (cb.Type IS CALL_SCRIPT) { + else if (sub.Callback.isScript()) { const ScriptArg args[] = { { "Events:InputEvent", first, FD_PTR|FDF_STRUCT }, { "Handle", handle }, }; - ERROR result; - scCallback(cb.Script.Script, cb.Script.ProcedureID, args, ARRAYSIZE(args), &result); + ERR result; + scCallback(cb.Script.Script, cb.Script.ProcedureID, args, std::ssize(args), &result); } glInputLock.lock(); diff --git a/src/display/lib_surfaces.cpp b/src/display/lib_surfaces.cpp index dabbbf550..4256e5912 100644 --- a/src/display/lib_surfaces.cpp +++ b/src/display/lib_surfaces.cpp @@ -31,13 +31,13 @@ void winDragDropFromHost_Drop(int SurfaceID, char *Datatypes) if (!modal_id) { SURFACEINFO *info; - if (!gfxGetSurfaceInfo(pointer->OverObjectID, &info)) { - pf::ScopedObjectLock<> display(info->DisplayID); + if (gfxGetSurfaceInfo(pointer->OverObjectID, &info) IS ERR::Okay) { + pf::ScopedObjectLock display(info->DisplayID); if (display.granted()) { acDragDrop(pointer->OverObjectID, *display, -1, Datatypes); } } - else log.warning(ERR_GetSurfaceInfo); + else log.warning(ERR::GetSurfaceInfo); } else log.msg("Program is modal - drag/drop cancelled."); @@ -49,20 +49,21 @@ void winDragDropFromHost_Drop(int SurfaceID, char *Datatypes) //******************************************************************************************************************** -ERROR get_surface_abs(OBJECTID SurfaceID, LONG *AbsX, LONG *AbsY, LONG *Width, LONG *Height) +ERR get_surface_abs(OBJECTID SurfaceID, LONG *AbsX, LONG *AbsY, LONG *Width, LONG *Height) { const std::lock_guard lock(glSurfaceLock); - LONG i; - for (i=0; (glSurfaces[i].SurfaceID) and (glSurfaces[i].SurfaceID != SurfaceID); i++); - - if (!glSurfaces[i].SurfaceID) return ERR_Search; + for (auto &record : glSurfaces) { + if (record.SurfaceID IS SurfaceID) { + if (AbsX) *AbsX = record.Left; + if (AbsY) *AbsY = record.Top; + if (Width) *Width = record.Width; + if (Height) *Height = record.Height; + return ERR::Okay; + } + } - if (AbsX) *AbsX = glSurfaces[i].Left; - if (AbsY) *AbsY = glSurfaces[i].Top; - if (Width) *Width = glSurfaces[i].Width; - if (Height) *Height = glSurfaces[i].Height; - return ERR_Okay; + return ERR::Search; } //******************************************************************************************************************** @@ -135,7 +136,7 @@ LONG find_bitmap_owner(const SURFACELIST &List, LONG Index) // // Surface levels start at 1, which indicates the top-most level. -ERROR track_layer(extSurface *Self) +ERR track_layer(extSurface *Self) { pf::Log log(__FUNCTION__); @@ -172,7 +173,7 @@ ERROR track_layer(extSurface *Self) LONG parent; if ((parent = find_parent_list(glSurfaces, Self)) IS -1) { log.warning("Failed to find parent surface #%d.", Self->ParentID); - return ERR_Search; + return ERR::Search; } record.setArea(glSurfaces[parent].Left + Self->X, glSurfaces[parent].Top + Self->Y, @@ -195,7 +196,7 @@ ERROR track_layer(extSurface *Self) else glSurfaces.push_back(record); } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -213,12 +214,12 @@ void untrack_layer(OBJECTID ObjectID) // Mark all subsequent child layers as invisible - LONG end; - for (end=i+1; (end < LONG(glSurfaces.size())) and (glSurfaces[end].Level > glSurfaces[i].Level); end++) { + size_t end; + for (end=i+1; (end < glSurfaces.size()) and (glSurfaces[end].Level > glSurfaces[i].Level); end++) { glSurfaces[end].Flags &= ~RNF::VISIBLE; } - if (end >= LONG(glSurfaces.size())) glSurfaces.resize(i); + if (end >= glSurfaces.size()) glSurfaces.resize(i); else glSurfaces.erase(glSurfaces.begin() + i, glSurfaces.begin() + end); #ifdef DBG_LAYERS @@ -229,12 +230,10 @@ void untrack_layer(OBJECTID ObjectID) //******************************************************************************************************************** -ERROR update_surface_copy(extSurface *Self) +ERR update_surface_copy(extSurface *Self) { - LONG i; - - if (!Self) return ERR_NullArgs; - if (!Self->initialised()) return ERR_Okay; + if (!Self) return ERR::NullArgs; + if (!Self->initialised()) return ERR::Okay; const std::lock_guard lock(glSurfaceLock); auto &list = glSurfaces; @@ -242,6 +241,7 @@ ERROR update_surface_copy(extSurface *Self) // Calculate absolute coordinates by looking for the parent of this object. Then simply add the parent's // absolute X,Y coordinates to our X and Y fields. + LONG i; LONG absx, absy; if (Self->ParentID) { if ((i = find_parent_list(list, Self)) != -1) { @@ -301,7 +301,7 @@ ERROR update_surface_copy(extSurface *Self) } } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -331,7 +331,7 @@ void move_layer_pos(SURFACELIST &List, LONG Src, LONG Dest) // // This function is also useful for skipping the dimension limits normally imposed when resizing. -ERROR resize_layer(extSurface *Self, LONG X, LONG Y, LONG Width, LONG Height, LONG InsideWidth, +ERR resize_layer(extSurface *Self, LONG X, LONG Y, LONG Width, LONG Height, LONG InsideWidth, LONG InsideHeight, LONG BPP, DOUBLE RefreshRate, LONG DeviceFlags) { if (!Width) Width = Self->Width; @@ -342,12 +342,12 @@ ERROR resize_layer(extSurface *Self, LONG X, LONG Y, LONG Width, LONG Height, LO Self->Y = Y; Self->Width = Width; Self->Height = Height; - return ERR_Okay; + return ERR::Okay; } if ((Self->X IS X) and (Self->Y IS Y) and (Self->Width IS Width) and (Self->Height IS Height) and (Self->ParentID)) { - return ERR_Okay; + return ERR::Okay; } pf::Log log; @@ -357,16 +357,16 @@ ERROR resize_layer(extSurface *Self, LONG X, LONG Y, LONG Width, LONG Height, LO if (Self->BitmapOwnerID IS Self->UID) { pf::ScopedObjectLock bitmap(Self->BufferID, 5000); if (bitmap.granted()) { - if (!bitmap->resize(Width, Height, BPP)) { + if (bitmap->resize(Width, Height, BPP) IS ERR::Okay) { Self->LineWidth = bitmap->LineWidth; Self->BytesPerPixel = bitmap->BytesPerPixel; Self->BitsPerPixel = bitmap->BitsPerPixel; Self->Data = bitmap->Data; UpdateSurfaceRecord(Self); } - else return log.warning(ERR_Resize); + else return log.warning(ERR::Resize); } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } if (!Self->ParentID) { @@ -376,17 +376,17 @@ ERROR resize_layer(extSurface *Self, LONG X, LONG Y, LONG Width, LONG Height, LO if (InsideHeight < Height) InsideHeight = Height; OBJECTPTR display; - if (!AccessObject(Self->DisplayID, 5000, &display)) { // NB: SetDisplay() always processes coordinates relative to the client area in order to resolve issues when in hosted mode. - if (gfxSetDisplay(display, X, Y, Width, Height, InsideWidth, InsideHeight, BPP, RefreshRate, DeviceFlags)) { + if (AccessObject(Self->DisplayID, 5000, &display) IS ERR::Okay) { // NB: SetDisplay() always processes coordinates relative to the client area in order to resolve issues when in hosted mode. + if (gfxSetDisplay(display, X, Y, Width, Height, InsideWidth, InsideHeight, BPP, RefreshRate, DeviceFlags) != ERR::Okay) { ReleaseObject(display); - return log.warning(ERR_Redimension); + return log.warning(ERR::Redimension); } - display->get(FID_Width, &Width); - display->get(FID_Height, &Height); + Width = display->get(FID_Width); + Height = display->get(FID_Height); ReleaseObject(display); } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } auto oldx = Self->X; @@ -400,7 +400,7 @@ ERROR resize_layer(extSurface *Self, LONG X, LONG Y, LONG Width, LONG Height, LO Self->Height = Height; UpdateSurfaceRecord(Self); - if (!Self->initialised()) return ERR_Okay; + if (!Self->initialised()) return ERR::Okay; // Send a Resize notification to our subscribers. Basically, this informs our surface children to resize themselves // to the new dimensions. Surface objects are not permitted to redraw themselves when they receive the Redimension @@ -409,11 +409,11 @@ ERROR resize_layer(extSurface *Self, LONG X, LONG Y, LONG Width, LONG Height, LO forbidDrawing(); struct acRedimension redimension = { (DOUBLE)X, (DOUBLE)Y, 0, (DOUBLE)Width, (DOUBLE)Height, (DOUBLE)BPP }; - NotifySubscribers(Self, AC_Redimension, &redimension, ERR_Okay); + NotifySubscribers(Self, AC_Redimension, &redimension, ERR::Okay); permitDrawing(); - if (Self->invisible()) return ERR_Okay; + if (Self->invisible()) return ERR::Okay; if (!tlNoDrawing) { // Post the drawing update. This method is the only reliable way to generate updates when our surface may @@ -424,7 +424,7 @@ ERROR resize_layer(extSurface *Self, LONG X, LONG Y, LONG Width, LONG Height, LO LONG index; if ((index = find_surface_list(Self)) IS -1) { // The surface might not be listed if the parent is in the process of being dstroyed. - return ERR_Search; + return ERR::Search; } pf::Log log; @@ -463,7 +463,7 @@ ERROR resize_layer(extSurface *Self, LONG X, LONG Y, LONG Width, LONG Height, LO } refresh_pointer(Self); - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -489,7 +489,7 @@ static void check_bmp_buffer_depth(extSurface *Self, objBitmap *Bitmap) if ((Bitmap->Flags & BMF::FIXED_DEPTH) != BMF::NIL) return; // Don't change bitmaps marked as fixed-depth DISPLAYINFO *info; - if (!gfxGetDisplayInfo(Self->DisplayID, &info)) { + if (gfxGetDisplayInfo(Self->DisplayID, &info) IS ERR::Okay) { if (info->BitsPerPixel != Bitmap->BitsPerPixel) { log.msg("[%d] Updating buffer Bitmap %dx%dx%d to match new display depth of %dbpp.", Bitmap->UID, Bitmap->Width, Bitmap->Height, Bitmap->BitsPerPixel, info->BitsPerPixel); acResize(Bitmap, Bitmap->Width, Bitmap->Height, info->BitsPerPixel); @@ -514,27 +514,28 @@ void process_surface_callbacks(extSurface *Self, extBitmap *Bitmap) for (LONG i=0; i < Self->CallbackCount; i++) { Bitmap->Opacity = 255; - if (Self->Callback[i].Function.Type IS CALL_STDC) { - auto routine = (void (*)(APTR, extSurface *, objBitmap *))Self->Callback[i].Function.StdC.Routine; + auto &cb = Self->Callback[i].Function; + if (cb.isC()) { + auto routine = (void (*)(APTR, extSurface *, objBitmap *, APTR))cb.StdC.Routine; #ifdef DBG_DRAW_ROUTINES pf::Log log(__FUNCTION__); - log.branch("%d/%d: Routine: %p, Object: %p, Context: %p", i, Self->CallbackCount, routine, Self->Callback[i].Object, Self->Callback[i].Function.StdC.Context); + log.branch("%d/%d: Routine: %p, Object: %p, Context: %p", i, Self->CallbackCount, routine, Self->Callback[i].Object, cb.StdC.Context); #endif - if (Self->Callback[i].Function.StdC.Context) { - pf::SwitchContext context(Self->Callback[i].Function.StdC.Context); - routine(Self->Callback[i].Function.StdC.Context, Self, Bitmap); + if (cb.StdC.Context) { + pf::SwitchContext context(cb.StdC.Context); + routine(cb.StdC.Context, Self, Bitmap, cb.StdC.Meta); } - else routine(Self->Callback[i].Object, Self, Bitmap); + else routine(Self->Callback[i].Object, Self, Bitmap, cb.StdC.Meta); } - else if (Self->Callback[i].Function.Type IS CALL_SCRIPT) { + else if (cb.isScript()) { const ScriptArg args[] = { { "Surface", Self, FD_OBJECTPTR }, { "Bitmap", Bitmap, FD_OBJECTPTR } }; - auto script = Self->Callback[i].Function.Script.Script; - scCallback(script, Self->Callback[i].Function.Script.ProcedureID, args, ARRAYSIZE(args), NULL); + auto script = cb.Script.Script; + scCallback(script, cb.Script.ProcedureID, args, std::ssize(args), NULL); } } @@ -619,7 +620,7 @@ void print_layer_list(STRING Function, LONG POI) // Error checks if (!list[i].SurfaceID) fprintf(stderr, " <---- ERROR"); - else if (CheckObjectExists(list[i].SurfaceID) != ERR_True) fprintf(stderr, " <---- OBJECT MISSING"); + else if (CheckObjectExists(list[i].SurfaceID) != ERR::True) fprintf(stderr, " <---- OBJECT MISSING"); // Does the parent exist in the layer list? @@ -641,7 +642,7 @@ void print_layer_list(STRING Function, LONG POI) CheckIfChild: Checks if a surface is a child of another particular surface. This function checks if a surface identified by the Child value is the child of the surface identified by the Parent -value. `ERR_True` is returned if the surface is confirmed as being a child of the parent, or if the Child and Parent +value. `ERR::True` is returned if the surface is confirmed as being a child of the parent, or if the Child and Parent values are equal. All other return codes indicate false or failure. -INPUT- @@ -656,13 +657,13 @@ AccessMemory: Failed to access the internal surface list. *********************************************************************************************************************/ -ERROR gfxCheckIfChild(OBJECTID ParentID, OBJECTID ChildID) +ERR gfxCheckIfChild(OBJECTID ParentID, OBJECTID ChildID) { pf::Log log(__FUNCTION__); log.traceBranch("Parent: %d, Child: %d", ParentID, ChildID); - if ((!ParentID) or (!ChildID)) return ERR_NullArgs; + if ((!ParentID) or (!ChildID)) return ERR::NullArgs; const std::lock_guard lock(glSurfaceLock); @@ -673,12 +674,12 @@ ERROR gfxCheckIfChild(OBJECTID ParentID, OBJECTID ChildID) for (++i; (i < LONG(glSurfaces.size())) and (glSurfaces[i].Level > level); i++) { if (glSurfaces[i].SurfaceID IS ChildID) { log.trace("Child confirmed."); - return ERR_True; + return ERR::True; } } } - return ERR_False; + return ERR::False; } /********************************************************************************************************************* @@ -709,12 +710,12 @@ AccessMemory: Failed to access the internal surfacelist memory structure *********************************************************************************************************************/ -ERROR gfxCopySurface(OBJECTID SurfaceID, extBitmap *Bitmap, BDF Flags, +ERR gfxCopySurface(OBJECTID SurfaceID, extBitmap *Bitmap, BDF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest) { pf::Log log(__FUNCTION__); - if ((!SurfaceID) or (!Bitmap)) return log.warning(ERR_NullArgs); + if ((!SurfaceID) or (!Bitmap)) return log.warning(ERR::NullArgs); log.traceBranch("%dx%d,%dx%d TO %dx%d, Flags $%.8x", X, Y, Width, Height, XDest, YDest, LONG(Flags)); @@ -744,7 +745,7 @@ ERROR gfxCopySurface(OBJECTID SurfaceID, extBitmap *Bitmap, BDF Flags, if (((Flags & BDF::DITHER) != BDF::NIL) or (!list_root.Data)) { extBitmap *src; - if (!AccessObject(list_root.BitmapID, 4000, &src)) { + if (AccessObject(list_root.BitmapID, 4000, &src) IS ERR::Okay) { src->XOffset = list_i.Left - list_root.Left; src->YOffset = list_i.Top - list_root.Top; src->Clip.Left = 0; @@ -760,9 +761,9 @@ ERROR gfxCopySurface(OBJECTID SurfaceID, extBitmap *Bitmap, BDF Flags, else gfxCopyArea(src, Bitmap, ((Flags & BDF::DITHER) != BDF::NIL) ? BAF::DITHER : BAF::NIL, X, Y, Width, Height, XDest, YDest); ReleaseObject(src); - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); } else { surface.Data = list_root.Data; @@ -778,12 +779,12 @@ ERROR gfxCopySurface(OBJECTID SurfaceID, extBitmap *Bitmap, BDF Flags, if (composite) gfxCopyRawBitmap(&surface, Bitmap, CSRF::DEFAULT_FORMAT|CSRF::OFFSET|CSRF::ALPHA, X, Y, Width, Height, XDest, YDest); else gfxCopyRawBitmap(&surface, Bitmap, CSRF::DEFAULT_FORMAT|CSRF::OFFSET, X, Y, Width, Height, XDest, YDest); - return ERR_Okay; + return ERR::Okay; } } } - return ERR_Search; + return ERR::Search; } /********************************************************************************************************************* @@ -810,19 +811,19 @@ AccessMemory: The internal surfacelist could not be accessed *********************************************************************************************************************/ -ERROR gfxExposeSurface(OBJECTID SurfaceID, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags) +ERR gfxExposeSurface(OBJECTID SurfaceID, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags) { pf::Log log(__FUNCTION__); - if (tlNoDrawing) return ERR_Okay; - if (!SurfaceID) return ERR_NullArgs; - if ((Width < 1) or (Height < 1)) return ERR_Okay; + if (tlNoDrawing) return ERR::Okay; + if (!SurfaceID) return ERR::NullArgs; + if ((Width < 1) or (Height < 1)) return ERR::Okay; const std::lock_guard lock(glSurfaceLock); LONG index; if ((index = find_surface_list(SurfaceID)) IS -1) { // The surface might not be listed if the parent is in the process of being dstroyed. log.traceWarning("Surface %d is not in the surfacelist.", SurfaceID); - return ERR_Search; + return ERR::Search; } return _expose_surface(SurfaceID, glSurfaces, index, X, Y, Width, Height, Flags); @@ -843,7 +844,7 @@ oid: The UID of the modal surface, or zero. OBJECTID gfxGetModalSurface(void) { // Safety check: Confirm that the object still exists - if ((glModalID) and (CheckObjectExists(glModalID) != ERR_True)) { + if ((glModalID) and (CheckObjectExists(glModalID) != ERR::True)) { pf::Log log(__FUNCTION__); log.msg("Modal surface #%d no longer exists.", glModalID); glModalID = 0; @@ -876,27 +877,27 @@ AccessMemory: Failed to access the internal surfacelist memory structure. *********************************************************************************************************************/ -ERROR gfxGetSurfaceCoords(OBJECTID SurfaceID, LONG *X, LONG *Y, LONG *AbsX, LONG *AbsY, LONG *Width, LONG *Height) +ERR gfxGetSurfaceCoords(OBJECTID SurfaceID, LONG *X, LONG *Y, LONG *AbsX, LONG *AbsY, LONG *Width, LONG *Height) { pf::Log log(__FUNCTION__); if (!SurfaceID) { DISPLAYINFO *display; - if (!gfxGetDisplayInfo(0, &display)) { + if (gfxGetDisplayInfo(0, &display) IS ERR::Okay) { if (X) *X = 0; if (Y) *Y = 0; if (AbsX) *AbsX = 0; if (AbsY) *AbsY = 0; if (Width) *Width = display->Width; if (Height) *Height = display->Height; - return ERR_Okay; + return ERR::Okay; } - else return ERR_Failed; + else return ERR::Failed; } LONG i; const std::lock_guard lock(glSurfaceLock); - if ((i = find_surface_list(SurfaceID)) IS -1) return ERR_Search; + if ((i = find_surface_list(SurfaceID)) IS -1) return ERR::Search; if (X) *X = glSurfaces[i].X; if (Y) *Y = glSurfaces[i].Y; @@ -905,7 +906,7 @@ ERROR gfxGetSurfaceCoords(OBJECTID SurfaceID, LONG *X, LONG *Y, LONG *AbsX, LONG if (AbsX) *AbsX = glSurfaces[i].Left; if (AbsY) *AbsY = glSurfaces[i].Top; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -930,21 +931,21 @@ AccessMemory *********************************************************************************************************************/ -ERROR gfxGetSurfaceFlags(OBJECTID SurfaceID, RNF *Flags) +ERR gfxGetSurfaceFlags(OBJECTID SurfaceID, RNF *Flags) { pf::Log log(__FUNCTION__); if (Flags) *Flags = RNF::NIL; - else return log.warning(ERR_NullArgs); + else return log.warning(ERR::NullArgs); - if (!SurfaceID) return log.warning(ERR_NullArgs); + if (!SurfaceID) return log.warning(ERR::NullArgs); const std::lock_guard lock(glSurfaceLock); LONG i; - if ((i = find_surface_list(SurfaceID)) IS -1) return ERR_Search; + if ((i = find_surface_list(SurfaceID)) IS -1) return ERR::Search; *Flags = glSurfaces[i].Flags; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -968,14 +969,14 @@ AccessMemory: Failed to access the internal surfacelist memory structure. *********************************************************************************************************************/ -ERROR gfxGetSurfaceInfo(OBJECTID SurfaceID, SURFACEINFO **Info) +ERR gfxGetSurfaceInfo(OBJECTID SurfaceID, SURFACEINFO **Info) { pf::Log log(__FUNCTION__); static THREADVAR SURFACEINFO info; // Note that a SurfaceID of zero is fine (returns the root surface). - if (!Info) return log.warning(ERR_NullArgs); + if (!Info) return log.warning(ERR::NullArgs); const std::lock_guard lock(glSurfaceLock); @@ -985,7 +986,7 @@ ERROR gfxGetSurfaceInfo(OBJECTID SurfaceID, SURFACEINFO **Info) root = 0; } else { - if ((i = find_surface_list(SurfaceID)) IS -1) return ERR_Search; + if ((i = find_surface_list(SurfaceID)) IS -1) return ERR::Search; root = find_bitmap_owner(glSurfaces, i); } @@ -1006,7 +1007,7 @@ ERROR gfxGetSurfaceInfo(OBJECTID SurfaceID, SURFACEINFO **Info) info.LineWidth = glSurfaces[root].LineWidth; *Info = &info; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1023,7 +1024,7 @@ oid: Returns the ID of the surface object that has the user focus, or zero on fa OBJECTID gfxGetUserFocus(void) { - const std::lock_guard lock(glFocusLock); + const std::lock_guard lock(glFocusLock); if (!glFocusList.empty()) { auto objectid = glFocusList[0]; return objectid; @@ -1056,28 +1057,28 @@ AccessMemory: Failed to access the internal surfacelist memory structure. *********************************************************************************************************************/ -ERROR gfxGetVisibleArea(OBJECTID SurfaceID, LONG *X, LONG *Y, LONG *AbsX, LONG *AbsY, LONG *Width, LONG *Height) +ERR gfxGetVisibleArea(OBJECTID SurfaceID, LONG *X, LONG *Y, LONG *AbsX, LONG *AbsY, LONG *Width, LONG *Height) { pf::Log log(__FUNCTION__); if (!SurfaceID) { DISPLAYINFO *display; - if (!gfxGetDisplayInfo(0, &display)) { + if (gfxGetDisplayInfo(0, &display) IS ERR::Okay) { if (X) *X = 0; if (Y) *Y = 0; if (Width) *Width = display->Width; if (Height) *Height = display->Height; if (AbsX) *AbsX = 0; if (AbsY) *AbsY = 0; - return ERR_Okay; + return ERR::Okay; } - else return ERR_Failed; + else return ERR::Failed; } const std::lock_guard lock(glSurfaceLock); LONG i; - if ((i = find_surface_list(SurfaceID)) IS -1) return ERR_Search; + if ((i = find_surface_list(SurfaceID)) IS -1) return ERR::Search; auto clip = glSurfaces[i].area(); @@ -1090,7 +1091,7 @@ ERROR gfxGetVisibleArea(OBJECTID SurfaceID, LONG *X, LONG *Y, LONG *AbsX, LONG * if (AbsX) *AbsX = clip.Left; if (AbsY) *AbsY = clip.Top; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1130,13 +1131,13 @@ AccessMemory: Failed to access the internal surface list. *********************************************************************************************************************/ -ERROR gfxRedrawSurface(OBJECTID SurfaceID, LONG Left, LONG Top, LONG Right, LONG Bottom, IRF Flags) +ERR gfxRedrawSurface(OBJECTID SurfaceID, LONG Left, LONG Top, LONG Right, LONG Bottom, IRF Flags) { pf::Log log(__FUNCTION__); if (tlNoDrawing) { log.trace("tlNoDrawing: %d", tlNoDrawing); - return ERR_Okay; + return ERR::Okay; } const std::lock_guard lock(glSurfaceLock); @@ -1144,7 +1145,7 @@ ERROR gfxRedrawSurface(OBJECTID SurfaceID, LONG Left, LONG Top, LONG Right, LONG LONG index; if ((index = find_surface_list(SurfaceID)) IS -1) { log.traceWarning("Unable to find surface #%d in surface list.", SurfaceID); - return ERR_Search; + return ERR::Search; } return _redraw_surface(SurfaceID, glSurfaces, index, Left, Top, Right, Bottom, Flags); @@ -1152,7 +1153,7 @@ ERROR gfxRedrawSurface(OBJECTID SurfaceID, LONG Left, LONG Top, LONG Right, LONG //******************************************************************************************************************** -ERROR _redraw_surface(OBJECTID SurfaceID, const SURFACELIST &list, LONG index, +ERR _redraw_surface(OBJECTID SurfaceID, const SURFACELIST &list, LONG index, LONG Left, LONG Top, LONG Right, LONG Bottom, IRF Flags) { pf::Log log("redraw_surface"); @@ -1183,7 +1184,7 @@ ERROR _redraw_surface(OBJECTID SurfaceID, const SURFACELIST &list, LONG index, _redraw_surface(list[parent_index].SurfaceID, list, parent_index, Left, Top, Right, Bottom, Flags & (~IRF::IGNORE_CHILDREN)); } else log.trace("Failed to find parent surface #%d", list[index].ParentID); // No big deal, this often happens when freeing a bunch of surfaces due to the parent/child relationships. - return ERR_Okay; + return ERR::Okay; } // Check if any of the parent surfaces are invisible @@ -1191,7 +1192,7 @@ ERROR _redraw_surface(OBJECTID SurfaceID, const SURFACELIST &list, LONG index, if ((Flags & IRF::FORCE_DRAW) IS IRF::NIL) { if (list[index].invisible() or (check_visibility(list, index) IS FALSE)) { log.trace("Surface is not visible."); - return ERR_Okay; + return ERR::Okay; } } @@ -1220,17 +1221,16 @@ ERROR _redraw_surface(OBJECTID SurfaceID, const SURFACELIST &list, LONG index, } } - if ((Left >= Right) or (Top >= Bottom)) return ERR_Okay; + if ((Left >= Right) or (Top >= Bottom)) return ERR::Okay; // Draw the surface graphics into the bitmap buffer extSurface *surface; - ERROR error; - if (!(error = AccessObject(list[index].SurfaceID, 5000, &surface))) { + if (auto error = AccessObject(list[index].SurfaceID, 5000, &surface); error IS ERR::Okay) { log.trace("Area: %dx%d,%dx%d", Left, Top, Right-Left, Bottom-Top); extBitmap *bitmap; - if (!AccessObject(list[index].BitmapID, 5000, &bitmap)) { + if (AccessObject(list[index].BitmapID, 5000, &bitmap) IS ERR::Okay) { // Check if there has been a change in the video bit depth. If so, regenerate the bitmap with a matching depth. check_bmp_buffer_depth(surface, bitmap); @@ -1240,19 +1240,17 @@ ERROR _redraw_surface(OBJECTID SurfaceID, const SURFACELIST &list, LONG index, } else { ReleaseObject(surface); - return log.warning(ERR_AccessObject); + return log.warning(ERR::AccessObject); } ReleaseObject(surface); } - else { - // If the object does not exist then its task has crashed and we need to remove it from the surface list. - - if (error IS ERR_NoMatchingObject) { + else { // If the object does not exist then its task has crashed and we need to remove it from the surface list. + if (error IS ERR::NoMatchingObject) { log.warning("Removing references to surface object #%d (owner crashed).", list[index].SurfaceID); untrack_layer(list[index].SurfaceID); } - else log.warning("Unable to access surface object #%d, error %d.", list[index].SurfaceID, error); + else log.warning("Unable to access surface object #%d, error %d.", list[index].SurfaceID, LONG(error)); return error; } @@ -1286,7 +1284,7 @@ ERROR _redraw_surface(OBJECTID SurfaceID, const SURFACELIST &list, LONG index, } } - return ERR_Okay; + return ERR::Okay; } //******************************************************************************************************************** @@ -1500,7 +1498,7 @@ OBJECTID gfxSetModalSurface(OBJECTID SurfaceID) if (SurfaceID) { extSurface *surface; OBJECTID divert = 0; - if (!AccessObject(SurfaceID, 3000, &surface)) { + if (AccessObject(SurfaceID, 3000, &surface) IS ERR::Okay) { if (surface->invisible()) { divert = surface->PrevModalID; if (!divert) SurfaceID = 0; @@ -1524,7 +1522,7 @@ OBJECTID gfxSetModalSurface(OBJECTID SurfaceID) // Do not change the primary focus if the targetted surface already has it (this ensures that if any children have the focus, they will keep it). RNF flags; - if ((!gfxGetSurfaceFlags(SurfaceID, &flags)) and ((flags & RNF::HAS_FOCUS) IS RNF::NIL)) { + if ((gfxGetSurfaceFlags(SurfaceID, &flags) IS ERR::Okay) and ((flags & RNF::HAS_FOCUS) IS RNF::NIL)) { acFocus(SurfaceID); } return old_modal; @@ -1553,7 +1551,7 @@ Args *********************************************************************************************************************/ -ERROR gfxLockBitmap(OBJECTID SurfaceID, objBitmap **Bitmap, LVF *Info) +ERR gfxLockBitmap(OBJECTID SurfaceID, objBitmap **Bitmap, LVF *Info) { pf::Log log(__FUNCTION__); #if 0 @@ -1565,16 +1563,16 @@ ERROR gfxLockBitmap(OBJECTID SurfaceID, objBitmap **Bitmap, LVF *Info) if (Info) *Info = LVF::NIL; - if ((!SurfaceID) or (!Bitmap)) return log.warning(ERR_NullArgs); + if ((!SurfaceID) or (!Bitmap)) return log.warning(ERR::NullArgs); *Bitmap = 0; extSurface *surface; if (!AccessObject(SurfaceID, 5000, &surface)) { extBitmap *bitmap; - if (AccessObject(surface->BufferID, 5000, &bitmap) != ERR_Okay) { + if (AccessObject(surface->BufferID, 5000, &bitmap) != ERR::Okay) { ReleaseObject(surface); - return log.warning(ERR_AccessObject); + return log.warning(ERR::AccessObject); } ReleaseObject(surface); @@ -1584,7 +1582,7 @@ ERROR gfxLockBitmap(OBJECTID SurfaceID, objBitmap **Bitmap, LVF *Info) LONG i; if ((i = find_surface_list(SurfaceID)) IS -1) { ReleaseObject(bitmap); - return ERR_Search; + return ERR::Search; } LONG root = find_bitmap_owner(glSurfaces, i); @@ -1608,7 +1606,7 @@ ERROR gfxLockBitmap(OBJECTID SurfaceID, objBitmap **Bitmap, LVF *Info) bitmap->Clip.Right = bitmap->Width - bitmap->XOffset; if (bitmap->Clip.Right < 0) { ReleaseObject(bitmap); - return ERR_Failed; + return ERR::Failed; } } @@ -1616,20 +1614,20 @@ ERROR gfxLockBitmap(OBJECTID SurfaceID, objBitmap **Bitmap, LVF *Info) bitmap->Clip.Bottom = bitmap->Height - bitmap->YOffset; if (bitmap->ClipBottom < 0) { ReleaseObject(bitmap); - return ERR_Failed; + return ERR::Failed; } } *Bitmap = bitmap; - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); #else if (Info) *Info = LVF::NIL; - if ((!SurfaceID) or (!Bitmap)) return log.warning(ERR_NullArgs); + if ((!SurfaceID) or (!Bitmap)) return log.warning(ERR::NullArgs); SurfaceRecord list_root, list_zero; OBJECTID bitmap_id; @@ -1639,7 +1637,7 @@ ERROR gfxLockBitmap(OBJECTID SurfaceID, objBitmap **Bitmap, LVF *Info) const std::lock_guard lock(glSurfaceLock); LONG i; - if ((i = find_surface_list(SurfaceID)) IS -1) return ERR_Search; + if ((i = find_surface_list(SurfaceID)) IS -1) return ERR::Search; LONG root = find_bitmap_owner(glSurfaces, i); @@ -1651,16 +1649,16 @@ ERROR gfxLockBitmap(OBJECTID SurfaceID, objBitmap **Bitmap, LVF *Info) if (restrict_region_to_parents(glSurfaces, i, expose, true) IS -1) { // The surface is not within a visible area of the available bitmap space - return ERR_OutOfBounds; + return ERR::OutOfBounds; } } - if (!list_root.BitmapID) return log.warning(ERR_Failed); + if (!list_root.BitmapID) return log.warning(ERR::Failed); // Gain access to the bitmap buffer and set the clipping and offsets to the correct values. extBitmap *bmp; - if (!AccessObject(list_root.BitmapID, 5000, &bmp)) { + if (AccessObject(list_root.BitmapID, 5000, &bmp) IS ERR::Okay) { bmp->XOffset = expose.Left - list_root.Left; // The offset is the position of the surface within the root bitmap bmp->YOffset = expose.Top - list_root.Top; @@ -1683,9 +1681,9 @@ ERROR gfxLockBitmap(OBJECTID SurfaceID, objBitmap **Bitmap, LVF *Info) } *Bitmap = bmp; - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_AccessObject); + else return log.warning(ERR::AccessObject); #endif } @@ -1707,11 +1705,11 @@ Okay: The bitmap has been unlocked successfully. *********************************************************************************************************************/ -ERROR gfxUnlockBitmap(OBJECTID SurfaceID, extBitmap *Bitmap) +ERR gfxUnlockBitmap(OBJECTID SurfaceID, extBitmap *Bitmap) { - if ((!SurfaceID) or (!Bitmap)) return ERR_NullArgs; + if ((!SurfaceID) or (!Bitmap)) return ERR::NullArgs; ReleaseObject(Bitmap); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1734,12 +1732,12 @@ NullArgs *********************************************************************************************************************/ -ERROR gfxWindowHook(OBJECTID SurfaceID, WH Event, FUNCTION *Callback) +ERR gfxWindowHook(OBJECTID SurfaceID, WH Event, FUNCTION *Callback) { - if ((!SurfaceID) or (Event IS WH::NIL) or (!Callback)) return ERR_NullArgs; + if ((!SurfaceID) or (Event IS WH::NIL) or (!Callback)) return ERR::NullArgs; const WindowHook hook(SurfaceID, Event); glWindowHooks[hook] = *Callback; - return ERR_Okay; + return ERR::Okay; } diff --git a/src/display/prototypes.h b/src/display/prototypes.h index bc5e6580e..0346a0db9 100644 --- a/src/display/prototypes.h +++ b/src/display/prototypes.h @@ -2,48 +2,48 @@ extern "C" { objPointer * gfxAccessPointer(); -ERROR gfxCheckIfChild(OBJECTID Parent, OBJECTID Child); -ERROR gfxCopyArea(extBitmap * Bitmap, extBitmap * Dest, BAF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); -ERROR gfxCopyRawBitmap(struct BitmapSurfaceV2 * Surface, extBitmap * Bitmap, CSRF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); -ERROR gfxCopySurface(OBJECTID Surface, extBitmap * Bitmap, BDF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); +ERR gfxCheckIfChild(OBJECTID Parent, OBJECTID Child); +ERR gfxCopyArea(extBitmap * Bitmap, extBitmap * Dest, BAF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); +ERR gfxCopyRawBitmap(struct BitmapSurfaceV2 * Surface, extBitmap * Bitmap, CSRF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); +ERR gfxCopySurface(OBJECTID Surface, extBitmap * Bitmap, BDF Flags, LONG X, LONG Y, LONG Width, LONG Height, LONG XDest, LONG YDest); void gfxDrawPixel(extBitmap * Bitmap, LONG X, LONG Y, ULONG Colour); void gfxDrawRGBPixel(extBitmap * Bitmap, LONG X, LONG Y, struct RGB8 * RGB); void gfxDrawRectangle(extBitmap * Bitmap, LONG X, LONG Y, LONG Width, LONG Height, ULONG Colour, BAF Flags); -ERROR gfxExposeSurface(OBJECTID Surface, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags); +ERR gfxExposeSurface(OBJECTID Surface, LONG X, LONG Y, LONG Width, LONG Height, EXF Flags); void gfxFlipBitmap(extBitmap * Bitmap, FLIP Orientation); void gfxGetColourFormat(struct ColourFormat * Format, LONG BitsPerPixel, LONG RedMask, LONG GreenMask, LONG BlueMask, LONG AlphaMask); -ERROR gfxGetCursorInfo(struct CursorInfo * Info, LONG Size); -ERROR gfxGetCursorPos(DOUBLE * X, DOUBLE * Y); -ERROR gfxGetDisplayInfo(OBJECTID Display, struct DisplayInfoV3 ** Info); +ERR gfxGetCursorInfo(struct CursorInfo * Info, LONG Size); +ERR gfxGetCursorPos(DOUBLE * X, DOUBLE * Y); +ERR gfxGetDisplayInfo(OBJECTID Display, struct DisplayInfoV3 ** Info); DT gfxGetDisplayType(); CSTRING gfxGetInputTypeName(JET Type); OBJECTID gfxGetModalSurface(); -ERROR gfxGetRelativeCursorPos(OBJECTID Surface, DOUBLE * X, DOUBLE * Y); -ERROR gfxGetSurfaceCoords(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height); -ERROR gfxGetSurfaceFlags(OBJECTID Surface, RNF * Flags); -ERROR gfxGetSurfaceInfo(OBJECTID Surface, struct SurfaceInfoV2 ** Info); +ERR gfxGetRelativeCursorPos(OBJECTID Surface, DOUBLE * X, DOUBLE * Y); +ERR gfxGetSurfaceCoords(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height); +ERR gfxGetSurfaceFlags(OBJECTID Surface, RNF * Flags); +ERR gfxGetSurfaceInfo(OBJECTID Surface, struct SurfaceInfoV2 ** Info); OBJECTID gfxGetUserFocus(); -ERROR gfxGetVisibleArea(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height); -ERROR gfxLockBitmap(OBJECTID Surface, objBitmap ** Bitmap, LVF * Info); -ERROR gfxLockCursor(OBJECTID Surface); +ERR gfxGetVisibleArea(OBJECTID Surface, LONG * X, LONG * Y, LONG * AbsX, LONG * AbsY, LONG * Width, LONG * Height); +ERR gfxLockBitmap(OBJECTID Surface, objBitmap ** Bitmap, LVF * Info); +ERR gfxLockCursor(OBJECTID Surface); ULONG gfxReadPixel(extBitmap * Bitmap, LONG X, LONG Y); void gfxReadRGBPixel(extBitmap * Bitmap, LONG X, LONG Y, struct RGB8 ** RGB); -ERROR gfxResample(extBitmap * Bitmap, struct ColourFormat * ColourFormat); -ERROR gfxRestoreCursor(PTC Cursor, OBJECTID Owner); +ERR gfxResample(extBitmap * Bitmap, struct ColourFormat * ColourFormat); +ERR gfxRestoreCursor(PTC Cursor, OBJECTID Owner); DOUBLE gfxScaleToDPI(DOUBLE Value); -ERROR gfxScanDisplayModes(CSTRING Filter, struct DisplayInfoV3 * Info, LONG Size); +ERR gfxScanDisplayModes(CSTRING Filter, struct DisplayInfoV3 * Info, LONG Size); void gfxSetClipRegion(extBitmap * Bitmap, LONG Number, LONG Left, LONG Top, LONG Right, LONG Bottom, LONG Terminate); -ERROR gfxSetCursor(OBJECTID Surface, CRF Flags, PTC Cursor, CSTRING Name, OBJECTID Owner); -ERROR gfxSetCursorPos(DOUBLE X, DOUBLE Y); -ERROR gfxSetCustomCursor(OBJECTID Surface, CRF Flags, objBitmap * Bitmap, LONG HotX, LONG HotY, OBJECTID Owner); -ERROR gfxSetHostOption(HOST Option, LARGE Value); +ERR gfxSetCursor(OBJECTID Surface, CRF Flags, PTC Cursor, CSTRING Name, OBJECTID Owner); +ERR gfxSetCursorPos(DOUBLE X, DOUBLE Y); +ERR gfxSetCustomCursor(OBJECTID Surface, CRF Flags, objBitmap * Bitmap, LONG HotX, LONG HotY, OBJECTID Owner); +ERR gfxSetHostOption(HOST Option, LARGE Value); OBJECTID gfxSetModalSurface(OBJECTID Surface); -ERROR gfxStartCursorDrag(OBJECTID Source, LONG Item, CSTRING Datatypes, OBJECTID Surface); -ERROR gfxSubscribeInput(FUNCTION * Callback, OBJECTID SurfaceFilter, JTYPE Mask, OBJECTID DeviceFilter, LONG * Handle); +ERR gfxStartCursorDrag(OBJECTID Source, LONG Item, CSTRING Datatypes, OBJECTID Surface); +ERR gfxSubscribeInput(FUNCTION * Callback, OBJECTID SurfaceFilter, JTYPE Mask, OBJECTID DeviceFilter, LONG * Handle); void gfxSync(extBitmap * Bitmap); -ERROR gfxUnlockBitmap(OBJECTID Surface, extBitmap * Bitmap); -ERROR gfxUnlockCursor(OBJECTID Surface); -ERROR gfxUnsubscribeInput(LONG Handle); -ERROR gfxWindowHook(OBJECTID SurfaceID, WH Event, FUNCTION * Callback); +ERR gfxUnlockBitmap(OBJECTID Surface, extBitmap * Bitmap); +ERR gfxUnlockCursor(OBJECTID Surface); +ERR gfxUnsubscribeInput(LONG Handle); +ERR gfxWindowHook(OBJECTID SurfaceID, WH Event, FUNCTION * Callback); } // extern c diff --git a/src/display/tests/clipboard.fluid b/src/display/tests/clipboard.fluid index 0676e4196..5e73c2603 100644 --- a/src/display/tests/clipboard.fluid +++ b/src/display/tests/clipboard.fluid @@ -10,7 +10,7 @@ Manual test for confirming that the clibpoard works. local viewport = win:clientViewport({ aspectRatio = ARF_MEET }) local text = viewport.new('VectorText', { - string='Push any key to test paste operations', face='Open Sans', fontSize=20, y=50, x=10, fill='rgb(0,0,0)' + string='Push any key to test paste operations', face='Noto Sans', fontSize=20, y=50, x=10, fill='rgb(0,0,0)' }) local clipboard = obj.new('Clipboard', { }) diff --git a/src/display/win32/clipboard.c b/src/display/win32/clipboard.c index 9b1c800d2..dd8109045 100644 --- a/src/display/win32/clipboard.c +++ b/src/display/win32/clipboard.c @@ -6,6 +6,8 @@ #pragma warning (disable : 4244 4311 4312 4267 4244 4068) // Disable annoying VC++ typecast warnings #endif +#include + #include "keys.h" #include #include @@ -14,8 +16,6 @@ #include #include -#include - #include #include #include @@ -502,7 +502,8 @@ static int get_data(struct rkDropTarget *Self, char *Preference, struct WinDT ** size += DragQueryFile(raw, i, path, sizeof(path)) + 1; } - if ((Self->ItemData = malloc(size))) { + if (!size); + else if ((Self->ItemData = malloc(size))) { if ((Self->DataItems = (struct WinDT *)malloc(sizeof(struct WinDT) * total))) { str = (char *)Self->ItemData; for (item=0; item < total; item++) { diff --git a/src/display/win32/handlers.cpp b/src/display/win32/handlers.cpp index 9fbc92d95..fe759422a 100644 --- a/src/display/win32/handlers.cpp +++ b/src/display/win32/handlers.cpp @@ -48,28 +48,24 @@ void MsgKeyRelease(int Flags, int Value) { MsgKeyRelease(KQ(Flags), KEY(Value)); //******************************************************************************************************************** -void MsgMovement(OBJECTID SurfaceID, DOUBLE AbsX, DOUBLE AbsY, LONG WinX, LONG WinY) +void MsgMovement(OBJECTID SurfaceID, DOUBLE AbsX, DOUBLE AbsY, LONG WinX, LONG WinY, bool NonClient) { if (auto pointer = gfxAccessPointer(); pointer) { pointer->set(FID_Surface, SurfaceID); // Alter the surface of the pointer so that it refers to the correct root window gfxReleasePointer(pointer); - struct dcDeviceInput joy[2]; - joy[0].Type = JET::ABS_X; - joy[0].Flags = JTYPE::NIL; - joy[0].Value = AbsX; + struct dcDeviceInput joy[1]; + joy[0].Type = JET::ABS_XY; + joy[0].Flags = NonClient ? JTYPE::SECONDARY : JTYPE::NIL; + joy[0].Values[0] = AbsX; + joy[0].Values[1] = AbsY; joy[0].Timestamp = PreciseTime(); - joy[1].Type = JET::ABS_Y; - joy[1].Flags = JTYPE::NIL; - joy[1].Value = AbsY; - joy[1].Timestamp = joy[0].Timestamp; - struct acDataFeed feed = { .Object = NULL, .Datatype = DATA::DEVICE_INPUT, .Buffer = &joy, - .Size = sizeof(struct dcDeviceInput) * 2 + .Size = sizeof(struct dcDeviceInput) }; ActionMsg(AC_DataFeed, glPointerID, &feed); } @@ -80,13 +76,13 @@ void MsgMovement(OBJECTID SurfaceID, DOUBLE AbsX, DOUBLE AbsY, LONG WinX, LONG W void MsgWheelMovement(OBJECTID SurfaceID, FLOAT Wheel) { if (!glPointerID) { - if (FindObject("SystemPointer", 0, FOF::NIL, &glPointerID) != ERR_Okay) return; + if (FindObject("SystemPointer", 0, FOF::NIL, &glPointerID) != ERR::Okay) return; } struct dcDeviceInput joy; joy.Type = JET::WHEEL; joy.Flags = JTYPE::NIL; - joy.Value = Wheel; + joy.Values[0] = Wheel; joy.Timestamp = PreciseTime(); struct acDataFeed feed; @@ -111,6 +107,8 @@ void MsgFocusState(OBJECTID SurfaceID, LONG State) } //******************************************************************************************************************** +// If a button press is incoming from the non-client area (e.g. titlebar, resize edge) then the SECONDARY flag is +// applied. void MsgButtonPress(LONG button, LONG State) { @@ -122,24 +120,24 @@ void MsgButtonPress(LONG button, LONG State) if (button & 0x0001) { joy[i].Type = JET::BUTTON_1; - joy[i].Flags = JTYPE::NIL; - joy[i].Value = State; + joy[i].Flags = (button & 0x4000) ? JTYPE::SECONDARY : JTYPE::NIL; + joy[i].Values[0] = State; joy[i].Timestamp = timestamp; i++; } if (button & 0x0002) { joy[i].Type = JET::BUTTON_2; - joy[i].Flags = JTYPE::NIL; - joy[i].Value = State; + joy[i].Flags = (button & 0x4000) ? JTYPE::SECONDARY : JTYPE::NIL; + joy[i].Values[0] = State; joy[i].Timestamp = timestamp; i++; } if (button & 0x0004) { joy[i].Type = JET::BUTTON_3; - joy[i].Flags = JTYPE::NIL; - joy[i].Value = State; + joy[i].Flags = (button & 0x4000) ? JTYPE::SECONDARY : JTYPE::NIL; + joy[i].Values[0] = State; joy[i].Timestamp = timestamp; i++; } @@ -152,7 +150,7 @@ void MsgButtonPress(LONG button, LONG State) feed.Datatype = DATA::DEVICE_INPUT; feed.Buffer = &joy; feed.Size = sizeof(struct dcDeviceInput) * i; - if (ActionMsg(AC_DataFeed, glPointerID, &feed) IS ERR_NoMatchingObject) { + if (ActionMsg(AC_DataFeed, glPointerID, &feed) IS ERR::NoMatchingObject) { glPointerID = 0; } } @@ -170,10 +168,10 @@ void MsgResizedWindow(OBJECTID SurfaceID, LONG WinX, LONG WinY, LONG WinWidth, L if ((!SurfaceID) or (WinWidth < 1) or (WinHeight < 1)) return; objSurface *surface; - if (!AccessObject(SurfaceID, 3000, &surface)) { + if (AccessObject(SurfaceID, 3000, &surface) IS ERR::Okay) { extDisplay *display; OBJECTID display_id = surface->DisplayID; - if (!AccessObject(display_id, 3000, &display)) { + if (AccessObject(display_id, 3000, &display) IS ERR::Okay) { FUNCTION feedback = display->ResizeFeedback; display->X = WinX; display->Y = WinY; @@ -204,7 +202,7 @@ void MsgSetFocus(OBJECTID SurfaceID) { pf::Log log; objSurface *surface; - if (!AccessObject(SurfaceID, 3000, &surface)) { + if (AccessObject(SurfaceID, 3000, &surface) IS ERR::Okay) { if ((!surface->hasFocus()) and (surface->visible())) { log.msg("WM_SETFOCUS: Sending focus to surface #%d.", SurfaceID); QueueAction(AC_Focus, SurfaceID); @@ -222,17 +220,15 @@ void CheckWindowSize(OBJECTID SurfaceID, LONG *Width, LONG *Height) if ((!SurfaceID) or (!Width) or (!Height)) return; objSurface *surface; - if (!AccessObject(SurfaceID, 3000, &surface)) { - LONG minwidth, minheight, maxwidth, maxheight; - LONG left, right, top, bottom; - surface->get(FID_MinWidth, &minwidth); - surface->get(FID_MinHeight, &minheight); - surface->get(FID_MaxWidth, &maxwidth); - surface->get(FID_MaxHeight, &maxheight); - surface->get(FID_LeftMargin, &left); - surface->get(FID_TopMargin, &top); - surface->get(FID_BottomMargin, &bottom); - surface->get(FID_RightMargin, &right); + if (AccessObject(SurfaceID, 3000, &surface) IS ERR::Okay) { + auto minwidth = surface->get(FID_MinWidth); + auto minheight = surface->get(FID_MinHeight); + auto maxwidth = surface->get(FID_MaxWidth); + auto maxheight = surface->get(FID_MaxHeight); + auto left = surface->get(FID_LeftMargin); + auto top = surface->get(FID_TopMargin); + auto bottom = surface->get(FID_BottomMargin); + auto right = surface->get(FID_RightMargin); if (*Width < minwidth + left + right) *Width = minwidth + left + right; if (*Height < minheight + top + bottom) *Height = minheight + top + bottom; @@ -283,27 +279,27 @@ void MsgWindowClose(OBJECTID SurfaceID) if (glWindowHooks.contains(hook)) { auto func = &glWindowHooks[hook]; - ERROR result; + ERR result; - if (func->Type IS CALL_STDC) { + if (func->isC()) { pf::SwitchContext ctx(func->StdC.Context); - auto callback = (ERROR (*)(OBJECTID SurfaceID))func->StdC.Routine; - result = callback(SurfaceID); + auto callback = (ERR (*)(OBJECTID SurfaceID, APTR))func->StdC.Routine; + result = callback(SurfaceID, func->StdC.Meta); } - else if (func->Type IS CALL_SCRIPT) { + else if (func->isScript()) { ScriptArg args[] = { { "SurfaceID", SurfaceID, FDF_OBJECTID } }; - scCallback(func->Script.Script, func->Script.ProcedureID, args, ARRAYSIZE(args), &result); + scCallback(func->Script.Script, func->Script.ProcedureID, args, std::ssize(args), &result); } - else result = ERR_Okay; + else result = ERR::Okay; - if (result IS ERR_Terminate) glWindowHooks.erase(hook); - else if (result IS ERR_Cancelled) { + if (result IS ERR::Terminate) glWindowHooks.erase(hook); + else if (result IS ERR::Cancelled) { log.msg("Window closure cancelled by client."); return; } } - if (!CheckMemoryExists(SurfaceID)) FreeResource(SurfaceID); + if (CheckMemoryExists(SurfaceID) IS ERR::Okay) FreeResource(SurfaceID); } } diff --git a/src/display/win32/windows.cpp b/src/display/win32/windows.cpp index 4d07183bb..e25d16043 100644 --- a/src/display/win32/windows.cpp +++ b/src/display/win32/windows.cpp @@ -3,7 +3,6 @@ //#define DEBUG //#define DBGMSG -//#define DBGMOUSE #define _WIN32_WINNT 0x0600 // Allow Windows Vista function calls #define WINVER 0x0600 @@ -20,6 +19,7 @@ #include #include #include +#include #include @@ -59,6 +59,7 @@ typedef long long LARGE; #define WIN_RMB 0x0002 #define WIN_MMB 0x0004 #define WIN_DBL 0x8000 +#define WIN_NONCLIENT 0x4000 #define BORDERSIZE 6 #define WM_ICONNOTIFY (WM_USER + 101) @@ -83,11 +84,7 @@ HCURSOR glCurrentCursor = 0; static BYTE glScreenClassInit = 0; #ifdef DBGMSG -static struct { - int code; - char *name; -} wincmd[] = { -#ifdef DBGMOUSE +static std::map glCmd = { { { WM_SETCURSOR, "WM_SETCURSOR" }, { WM_NCMOUSEHOVER, "WM_NCMOUSEHOVER" }, { WM_NCMOUSELEAVE, "WM_NCMOUSELEAVE" }, { WM_NCMOUSEMOVE, "WM_NCMOUSEMOVE" }, @@ -96,7 +93,6 @@ static struct { { WM_MBUTTONDBLCLK, "WM_MBUTTONDBLCLK" }, { WM_MOUSEWHEEL, "WM_MOUSEWHEEL" }, { WM_MOUSEFIRST, "WM_MOUSEFIRST" }, { WM_XBUTTONDOWN, "WM_XBUTTONDOWN" }, { WM_XBUTTONUP, "WM_XBUTTONUP" }, { WM_XBUTTONDBLCLK, "WM_XBUTTONDBLCLK" }, { WM_MOUSELAST, "WM_MOUSELAST" }, { WM_MOUSEHOVER, "WM_MOUSEHOVER" }, { WM_MOUSELEAVE, "WM_MOUSELEAVE" }, { WM_NCHITTEST, "WM_NCHITTEST" }, { WM_NCLBUTTONDBLCLK, "WM_NCLBUTTONDBLCLK" }, { WM_NCLBUTTONDOWN, "WM_NCLBUTTONDOWN" }, -#endif { WM_APP, "WM_APP" }, { WM_ACTIVATE, "WM_ACTIVATE" }, { WM_ACTIVATEAPP, "WM_ACTIVATEAPP" }, { WM_AFXFIRST, "WM_AFXFIRST" }, { WM_MOVE, "WM_MOVE" }, { WM_AFXLAST, "WM_AFXLAST" }, { WM_ASKCBFORMATNAME, "WM_ASKCBFORMATNAME" }, { WM_CANCELJOURNAL, "WM_CANCELJOURNAL" }, { WM_CANCELMODE, "WM_CANCELMODE" }, { WM_CAPTURECHANGED, "WM_CAPTURECHANGED" }, { WM_CHANGECBCHAIN, "WM_CHANGECBCHAIN" }, { WM_CHAR, "WM_CHAR" }, { WM_CHARTOITEM, "WM_CHARTOITEM" }, @@ -136,9 +132,8 @@ static struct { { WM_SYSCOMMAND, "WM_SYSCOMMAND" }, { WM_SYSDEADCHAR, "WM_SYSDEADCHAR" }, { WM_SYSKEYDOWN, "WM_SYSKEYDOWN" }, { WM_SYSKEYUP, "WM_SYSKEYUP" }, { WM_TCARD, "WM_TCARD" }, { WM_TIMECHANGE, "WM_TIMECHANGE" }, { WM_TIMER, "WM_TIMER" }, { WM_UNDO, "WM_UNDO" }, { WM_USER, "WM_USER" }, { WM_USERCHANGED, "WM_USERCHANGED" }, { WM_VKEYTOITEM, "WM_VKEYTOITEM" }, { WM_VSCROLL, "WM_VSCROLL" }, { WM_VSCROLLCLIPBOARD, "WM_VSCROLLCLIPBOARD" }, { WM_WINDOWPOSCHANGED, "WM_WINDOWPOSCHANGED" }, { WM_WINDOWPOSCHANGING, "WM_WINDOWPOSCHANGING" }, - { WM_WININICHANGE, "WM_WININICHANGE" }, { WM_KEYFIRST, "WM_KEYFIRST" }, { WM_KEYLAST, "WM_KEYLAST" }, { WM_SYNCPAINT, "WM_SYNCPAINT" }, - { 0, 0 } -}; + { WM_WININICHANGE, "WM_WININICHANGE" }, { WM_KEYFIRST, "WM_KEYFIRST" }, { WM_KEYLAST, "WM_KEYLAST" }, { WM_SYNCPAINT, "WM_SYNCPAINT" } +} }; #endif int winLookupSurfaceID(HWND Window) @@ -538,9 +533,11 @@ int winGetWindowInfo(HWND Window, int *X, int *Y, int *Width, int *Height, int * //******************************************************************************************************************** -static void HandleMovement(HWND window, WPARAM wparam, LPARAM lparam) +static void HandleMovement(HWND window, WPARAM wparam, LPARAM lparam, bool NonClient) { - if (glCursorEntry == FALSE) { + // Note that if the movement is in the non-client portion of the window, we can't mess with the cursor image. + + if ((glCursorEntry == FALSE) and (!NonClient)) { winSetCursor(glDefaultCursor); glCursorEntry = TRUE; @@ -561,7 +558,7 @@ static void HandleMovement(HWND window, WPARAM wparam, LPARAM lparam) if (auto surface_id = winLookupSurfaceID(window)) { POINT point; GetCursorPos(&point); - MsgMovement(surface_id, point.x, point.y, (int)(lparam & 0xffff), (lparam>>16) & 0xffff); + MsgMovement(surface_id, point.x, point.y, (int)(lparam & 0xffff), (lparam>>16) & 0xffff, NonClient); } } @@ -709,16 +706,11 @@ static LRESULT CALLBACK WindowProcedure(HWND window, UINT msgcode, WPARAM wParam RECT winrect, client; #ifdef DBGMSG - int i; - for (i=0; wincmd[i].code; i++) { - if (msgcode == wincmd[i].code) { - fprintf(stderr, "WinProc: %s, $%.8x, $%.8x, Window: %p\n", wincmd[i].name, (int)wParam, (int)lParam, window); - break; - } + if (glCmd.contains(msgcode)) { + fprintf(stderr, "WinProc: %s, $%.8x, $%.8x, Window: %p\n", glCmd[msgcode], (int)wParam, (int)lParam, window); } - - if (!wincmd[i].code) { - fprintf(stderr, "WinProc: %d, $%.8x, $%.8x, Window: %p\n", msgcode, (int)wParam, (int)lParam, window); + else { + fprintf(stderr, "WinProc: 0x%x, $%.8x, $%.8x, Window: %p\n", msgcode, (int)wParam, (int)lParam, window); } #endif @@ -915,7 +907,7 @@ static LRESULT CALLBACK WindowProcedure(HWND window, UINT msgcode, WPARAM wParam else HandleKeyRelease(wParam); return 0; - case WM_MOUSEMOVE: HandleMovement(window, wParam, lParam); return 0; + case WM_MOUSEMOVE: HandleMovement(window, wParam, lParam, false); return 0; case WM_MOUSELEAVE: glCursorEntry = FALSE; return 0; @@ -932,6 +924,22 @@ static LRESULT CALLBACK WindowProcedure(HWND window, UINT msgcode, WPARAM wParam case WM_RBUTTONUP: HandleButtonRelease(window, WIN_RMB); return 0; case WM_MBUTTONUP: HandleButtonRelease(window, WIN_MMB); return 0; + case WM_NCMOUSEMOVE: + HandleMovement(window, wParam, lParam, true); + return DefWindowProc(window, msgcode, wParam, lParam); + + case WM_NCLBUTTONDOWN: + // Click detected on the titlebar or resize area. Quirks in the way that Windows manages + // mouse input mean that we need to signal a button press and release consecutively. + MsgButtonPress(WIN_LMB|WIN_NONCLIENT, 1); + MsgButtonPress(WIN_LMB|WIN_NONCLIENT, 0); + return DefWindowProc(window, msgcode, wParam, lParam); + + case WM_NCLBUTTONDBLCLK: // Double-click detected on the titlebar + MsgButtonPress(WIN_DBL|WIN_LMB|WIN_NONCLIENT, 1); + MsgButtonPress(WIN_DBL|WIN_LMB|WIN_NONCLIENT, 0); + return DefWindowProc(window, msgcode, wParam, lParam); + case WM_ICONNOTIFY: if (lParam == WM_LBUTTONDOWN) { ShowWindow(window, SW_SHOWNORMAL); // Bring window out of minimisation @@ -1526,9 +1534,9 @@ int winGetPixelFormat(int *redmask, int *greenmask, int *bluemask, int *alphamas } if (mred) { - *redmask = mred; + *redmask = mred; *greenmask = mgreen; - *bluemask = mblue; + *bluemask = mblue; *alphamask = malpha; return 0; } @@ -1544,20 +1552,6 @@ void winGetError(int Error, char *Buffer, int BufferSize) //******************************************************************************************************************** -void winDrawLine(HDC hdc, int x1, int y1, int x2, int y2, UBYTE *rgb) -{ - if (auto pen = CreatePen(PS_SOLID, 1, RGB(rgb[0], rgb[1], rgb[2]))) { - if (auto oldpen = SelectObject(hdc, pen)) { - MoveToEx(hdc, x1, y1, NULL); - LineTo(hdc, x2, y2); - SelectObject(hdc, oldpen); - } - DeleteObject(pen); - } -} - -//******************************************************************************************************************** - void winDrawRectangle(HDC hdc, int x, int y, int width, int height, UBYTE red, UBYTE green, UBYTE blue) { RECT rect; @@ -1571,25 +1565,6 @@ void winDrawRectangle(HDC hdc, int x, int y, int width, int height, UBYTE red, U DeleteObject(brush); } -/********************************************************************************************************************* -** Sets a new clipping region for a DC. -*/ - -int winSetClipping(HDC hdc, int left, int top, int right, int bottom) -{ - if ((!right) or (!bottom)) { - SelectClipRgn(hdc, NULL); - return 1; - } - - if (auto region = CreateRectRgn(left, top, right, bottom)) { - SelectClipRgn(hdc, region); - DeleteObject(region); - return 1; - } - return 0; -} - //******************************************************************************************************************** int winBlit(HDC dest, int xdest, int ydest, int width, int height, HDC src, int x, int y) @@ -1609,13 +1584,6 @@ void * winCreateCompatibleDC(void) //******************************************************************************************************************** -void winDeleteObject(void *Object) -{ - DeleteObject(Object); -} - -//******************************************************************************************************************** - void winSetDIBitsToDevice(HDC hdc, int xdest, int ydest, int width, int height, int xstart, int ystart, int scanwidth, int scanheight, int bpp, void *data, int redmask, int greenmask, int bluemask) @@ -1661,36 +1629,11 @@ void winDeleteDC(HDC hdc) //******************************************************************************************************************** -void winGetPixel(HDC hdc, int x, int y, UBYTE *rgb) -{ - COLORREF col; - col = GetPixel(hdc, x, y); - rgb[0] = GetRValue(col); - rgb[1] = GetGValue(col); - rgb[2] = GetBValue(col); -} - -//******************************************************************************************************************** - HBITMAP winCreateBitmap(int width, int height, int bpp) { return CreateBitmap(width, height, 1, bpp, NULL); } -//******************************************************************************************************************** -// This masking technique works so long as the source graphic uses a clear background after determining its original -// mask shape. - -void winDrawTransparentBitmap(HDC hdcDest, HDC hdcSrc, HBITMAP hBitmap, - int x, int y, int xsrc, int ysrc, int width, int height, - int maskx, int masky, HDC hdcMask) -{ - if ((!hdcMask) or (!hdcDest) or (!hdcSrc)) return; - - BitBlt(hdcDest, x, y, width, height, hdcMask, maskx, masky, SRCAND); // Mask out the places where the bitmap will be placed. - BitBlt(hdcDest, x, y, width, height, hdcSrc, xsrc, ysrc, SRCPAINT); // XOR the bitmap with the background on the destination DC. -} - //******************************************************************************************************************** void winTerminate(void) diff --git a/src/display/win32/windows.h b/src/display/win32/windows.h index cd8aff3f6..25c22eea8 100644 --- a/src/display/win32/windows.h +++ b/src/display/win32/windows.h @@ -68,13 +68,8 @@ extern void winGetError(int, char *, int); extern void * winCreateCompatibleDC(void); extern HBITMAP winCreateBitmap(int width, int height, int bpp); extern void winDeleteDC(void *); -extern void winDeleteObject(void *); -extern void winDrawLine(void *, int, int, int, int, unsigned char *); extern void winDrawRectangle(void *, int, int, int, int, unsigned char, unsigned char, unsigned char); -extern void winGetPixel(void *, int, int, unsigned char *); extern int winGetPixelFormat(int *, int *, int *, int *); -extern void * winSelectObject(void *, void *); -extern int winSetClipping(HDC, int, int, int, int); extern void winSetDIBitsToDevice(void *, int, int, int, int, int, int, int, int, int, void *, int, int, int); extern void win32RedrawWindow(HWND, HDC, int X, int Y, int Width, @@ -83,7 +78,7 @@ extern void win32RedrawWindow(HWND, HDC, int X, int Y, int Width, extern void MsgKeyPress(int, int, int); extern void MsgKeyRelease(int, int); -extern void MsgMovement(int, double, double, int, int); +extern void MsgMovement(int, double, double, int, int, bool); extern void MsgWheelMovement(int, float); extern void MsgButtonPress(int, int); extern void MsgFocusState(int SurfaceID, int State); diff --git a/src/display/x11/handlers.cpp b/src/display/x11/handlers.cpp index a22d85489..e8a583d55 100644 --- a/src/display/x11/handlers.cpp +++ b/src/display/x11/handlers.cpp @@ -10,8 +10,8 @@ static inline OBJECTID get_display(Window Window) if (!XDisplay) return 0; - if (XGetWindowProperty(XDisplay, Window, atomSurfaceID, 0, 1, - False, AnyPropertyType, &atom, &format, &nitems, &nbytes, (UBYTE **)&data) IS Success) { + if (XGetWindowProperty(XDisplay, Window, atomSurfaceID, 0, 1, False, AnyPropertyType, &atom, &format, &nitems, + &nbytes, (UBYTE **)&data) IS Success) { display_id = data[0]; XFree(data); return display_id; @@ -44,7 +44,7 @@ void X11ManagerLoop(HOSTHANDLE FD, APTR Data) case ButtonRelease: handle_button_release(&xevent); break; case ConfigureNotify: handle_configure_notify(&xevent.xconfigure); break; case EnterNotify: handle_enter_notify(&xevent.xcrossing); break; - case Expose: handle_exposure(&xevent.xexpose); break; + //case Expose: handle_exposure(&xevent.xexpose); break; case KeyPress: handle_key_press(&xevent); break; case KeyRelease: handle_key_release(&xevent); break; case CirculateNotify: handle_stack_change(&xevent.xcirculate); break; @@ -74,7 +74,7 @@ void X11ManagerLoop(HOSTHANDLE FD, APTR Data) std::vector list; { // Make a local copy of the focus list - const std::lock_guard lock(glFocusLock); + const std::lock_guard lock(glFocusLock); list = glFocusList; } @@ -101,16 +101,16 @@ void X11ManagerLoop(HOSTHANDLE FD, APTR Data) auto func = &glWindowHooks[hook]; ERROR result; - if (func->Type IS CALL_STDC) { + if (func->isC()) { pf::SwitchContext ctx(func->StdC.Context); - auto callback = (ERROR (*)(OBJECTID))func->StdC.Routine; - result = callback(surface_id); + auto callback = (ERROR (*)(OBJECTID, APTR))func->StdC.Routine; + result = callback(surface_id, func->StdC.Meta); } - else if (func->Type IS CALL_SCRIPT) { + else if (func->isScript()) { ScriptArg args[] = { { "SurfaceID", surface_id, FDF_OBJECTID } }; - scCallback(func->Script.Script, func->Script.ProcedureID, args, ARRAYSIZE(args), &result); + scCallback(func->Script.Script, func->Script.ProcedureID, args, std::ssize(args), &result); } else result = ERR_Okay; @@ -196,7 +196,7 @@ void handle_button_press(XEvent *xevent) input.Type = JET::WHEEL; input.Flags = JTYPE::EXT_MOVEMENT|JTYPE::DIGITAL; - input.Value = value; + input.Values[0] = value; input.Timestamp = PreciseTime(); feed.Object = NULL; @@ -212,15 +212,15 @@ void handle_button_press(XEvent *xevent) if ((pointer = gfxAccessPointer())) { if (xevent->xbutton.button IS 1) { input.Type = JET::BUTTON_1; - input.Value = 1; + input.Values[0] = 1; } else if (xevent->xbutton.button IS 2) { input.Type = JET::BUTTON_3; - input.Value = 1; + input.Values[0] = 1; } else if (xevent->xbutton.button IS 3) { input.Type = JET::BUTTON_2; - input.Value = 1; + input.Values[0] = 1; } ReleaseObject(pointer); } @@ -261,22 +261,22 @@ void handle_button_release(XEvent *xevent) feed.Size = sizeof(input); input.Type = JET::NIL; input.Flags = JTYPE::NIL; - input.Value = 0; + input.Values[0] = 0; input.Timestamp = PreciseTime(); objPointer *pointer; if ((pointer = gfxAccessPointer())) { if (xevent->xbutton.button IS 1) { input.Type = JET::BUTTON_1; - input.Value = 0; + input.Values[0] = 0; } else if (xevent->xbutton.button IS 2) { input.Type = JET::BUTTON_3; - input.Value = 0; + input.Values[0] = 0; } else if (xevent->xbutton.button IS 3) { input.Type = JET::BUTTON_2; - input.Value = 0; + input.Values[0] = 0; } ReleaseObject(pointer); } @@ -299,12 +299,11 @@ void handle_stack_change(XCirculateEvent *xevent) } //******************************************************************************************************************** +// Event handler for window resizing and movement void handle_configure_notify(XConfigureEvent *xevent) { pf::Log log(__FUNCTION__); - extDisplay *display; - OBJECTID display_id; LONG x = xevent->x; LONG y = xevent->y; @@ -321,33 +320,27 @@ void handle_configure_notify(XConfigureEvent *xevent) log.traceBranch("Win: %d, Pos: %dx%d,%dx%d", (int)xevent->window, x, y, width, height); - if ((display_id = get_display(xevent->window))) { - // Delete expose events that were generated by X11 during the resize - - // REMOVED: Sometimes ConfigureNotify is called during a window mapping and by deleting expose events, - // we may accidentally kill an expose that we actually need. - // - //while (XCheckTypedWindowEvent(XDisplay, xevent->window, Expose, &event) IS True); - - // Update the display dimensions - + if (auto display_id = get_display(xevent->window)) { + extDisplay *display; if (!AccessObject(display_id, 3000, &display)) { Window childwin; LONG absx, absy; - XTranslateCoordinates(XDisplay, (Window)display->WindowHandle, DefaultRootWindow(XDisplay), 0, 0, &absx, &absy, &childwin); + XTranslateCoordinates(XDisplay, (Window)display->WindowHandle, DefaultRootWindow(XDisplay), + 0, 0, &absx, &absy, &childwin); display->X = absx; display->Y = absy; display->Width = width; display->Height = height; + resize_pixmap(display, width, height); acResize(display->Bitmap, width, height, 0.0); FUNCTION feedback = display->ResizeFeedback; ReleaseObject(display); - // Notification occurs with the display and surface released so as to reduce the potential for dead-locking. + // Notify with the display and surface unlocked, this reduces the potential for dead-locking. log.trace("Sending redimension notification: %dx%d,%dx%d", absx, absy, width, height); @@ -355,7 +348,7 @@ void handle_configure_notify(XConfigureEvent *xevent) } else log.warning("Failed to get display ID for window %u.", (ULONG)xevent->window); } - else log.warning("Failed to get display ID."); + else log.warning("Failed to retrieve Display from X window."); } //******************************************************************************************************************** @@ -723,22 +716,19 @@ void process_movement(Window Window, LONG X, LONG Y) pointer->set(FID_Surface, GetOwnerID(display_id)); // Alter the surface of the pointer so that it refers to the correct root window } - // Refer to the handler code in the Screen class to see how the HostX and HostY fields are updated from afar. + // Refer to the handler code in the Display class to see how the HostX and HostY fields are updated from afar. struct acDataFeed feed; - struct dcDeviceInput input[2]; + struct dcDeviceInput input; feed.Object = NULL; feed.Datatype = DATA::DEVICE_INPUT; feed.Buffer = &input; feed.Size = sizeof(input); - input[0].Type = JET::ABS_X; - input[0].Flags = JTYPE::NIL; - input[0].Value = X; - input[0].Timestamp = PreciseTime(); - input[1].Type = JET::ABS_Y; - input[1].Flags = JTYPE::NIL; - input[1].Value = Y; - input[1].Timestamp = input[0].Timestamp; + input.Type = JET::ABS_XY; + input.Flags = JTYPE::NIL; + input.Values[0] = X; + input.Values[1] = Y; + input.Timestamp = PreciseTime(); Action(AC_DataFeed, pointer, &feed); ReleaseObject(pointer); diff --git a/src/document/CMakeLists.txt b/src/document/CMakeLists.txt index fc736d631..06cc76d5d 100644 --- a/src/document/CMakeLists.txt +++ b/src/document/CMakeLists.txt @@ -3,14 +3,14 @@ set (MOD "document") set (INC_MOD_DOCUMENT TRUE PARENT_SCOPE) -idl_all ("${MOD}.fdl" NAME ${MOD}_defs OUTPUT "${INCLUDE_OUTPUT}/modules/${MOD}.h" APPEND_IDL "module_def.c" +idl_all ("defs/${MOD}.fdl" NAME ${MOD}_defs OUTPUT "${INCLUDE_OUTPUT}/modules/${MOD}.h" APPEND_IDL "defs/module_def.c" FILES "${MOD}.cpp" - ARGS "output-defs=module_def.c" "output-proto=module_def.c" "prototypes=static") + ARGS "output-defs=defs/module_def.c" "output-proto=defs/module_def.c" "prototypes=static") -idl_c ("hashes.fdl" NAME ${MOD}_hashes OUTPUT "${CMAKE_CURRENT_SOURCE_DIR}/hashes.h") +idl_c ("defs/hashes.fdl" NAME ${MOD}_hashes OUTPUT "${CMAKE_CURRENT_SOURCE_DIR}/defs/hashes.h") add_library (${MOD}) - set_module_defaults (${MOD}) - target_sources (${MOD} PRIVATE "${MOD}.cpp") + +flute_test (doc_output "tests/test-doc.fluid") diff --git a/src/document/class/document_class.cpp b/src/document/class/document_class.cpp index fcb144a4b..9fbb15538 100644 --- a/src/document/class/document_class.cpp +++ b/src/document/class/document_class.cpp @@ -3,76 +3,91 @@ -CLASS- Document: Provides document display and editing facilities. -The Document class is a complete Page Layout Engine, providing rich text display -features for creating complex documents and manuals. +The Document class offers a complete page layout engine, providing rich text display features for creating complex +documents and text-based interfaces. Internally, document data is maintained as a serial byte stream and all +object model information from the source is discarded. This simplification of the data makes it possible to +edit the document in-place, much the same as any word processor. Alternatively it can be used for presentation +purposes only, similarly to PDF or HTML formats. Presentation is achieved by building a vector scene graph in +conjunction with the @Vector module. This means that the output is compatible with SVG and can be manipulated in +detail with our existing vector API. Consequently, document formatting is closely integrated with SVG concepts +and seamlessly inherits SVG functionality such as filling and stroking commands. + +
    Safety + +The Document class is intended to be safe to use when loading content from an unknown source. Processing will be +aborted if a problem is found or the document appears to be unrenderable. It is however, not guaranteed that +exploits are impossible. Consideration should also be given to the possibility of exploits that target third party +libraries such as libpng and libjpeg for instance. + +By default, script execution is not enabled when parsing a document source. If support for scripts is enabled, +there is no meaningful level of safety on offer when the document is processed. This feature should not be +used unless the source document has been written by the client, or has otherwise been received from a trusted source. + +To mitigate security problems, we recommend that the application is built with some form of sandbox that will stop +the system being compromised by bad actors. Utilising a project such as Win32 App Isolation +https://github.com/microsoft/win32-app-isolation is one potential way of doing this. -END- *********************************************************************************************************************/ -/* - else if (Args->ActionID IS MT_DrwInheritedFocus) { - // Check that the FocusIndex is accurate (it may have changed if the user clicked on a gadget). - - struct drwInheritedFocus *inherit = (struct drwInheritedFocus *)(Args->Args); - for (LONG i=0; i < Self->TabIndex; i++) { - if (Self->Tabs[i].XRef IS inherit->FocusID) { - Self->FocusIndex = i; - acDrawID(Self->PageID); - break; - } - } - } -*/ -static void notify_disable_surface(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, APTR Args) +static void notify_disable_viewport(OBJECTPTR Object, ACTIONID ActionID, ERR Result, APTR Args) { - if (!Result) acDisable(CurrentContext()); + if (Result IS ERR::Okay) acDisable(CurrentContext()); } -static void notify_enable_surface(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, APTR Args) +static void notify_enable_viewport(OBJECTPTR Object, ACTIONID ActionID, ERR Result, APTR Args) { - if (!Result) acEnable(CurrentContext()); + if (Result IS ERR::Okay) acEnable(CurrentContext()); } -static void notify_focus_surface(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, APTR Args) +static void notify_free_viewport(OBJECTPTR Object, ACTIONID ActionID, ERR Result, APTR Args) { auto Self = (extDocument *)CurrentContext(); + Self->Scene = NULL; + Self->Viewport = NULL; - if (Result) return; - - Self->HasFocus = TRUE; + // If the viewport is being forcibly terminated (e.g. by window closure) then the cleanest way to deal with + // lingering page resources is to remove them now. - if (!Self->prvKeyEvent) { - auto callback = make_function_stdc(key_event); - SubscribeEvent(EVID_IO_KEYBOARD_KEYPRESS, &callback, Self, &Self->prvKeyEvent); - } - - if (Self->FocusIndex != -1) set_focus(Self, Self->FocusIndex, "FocusNotify"); + Self->Resources.clear(); } -static void notify_free_event(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, APTR Args) +// Used by EventCallback for subscribers that disappear without notice. + +static void notify_free_event(OBJECTPTR Object, ACTIONID ActionID, ERR Result, APTR Args) { - ((extDocument *)CurrentContext())->EventCallback.Type = CALL_NONE; + auto Self = (extDocument *)CurrentContext(); + Self->EventCallback.clear(); } -static void notify_lostfocus_surface(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, APTR Args) +//******************************************************************************************************************** + +static void notify_focus_viewport(OBJECTPTR Object, ACTIONID ActionID, ERR Result, APTR Args) { - pf::Log log(__FUNCTION__); auto Self = (extDocument *)CurrentContext(); - if (Result) return; + if (Result != ERR::Okay) return; + + Self->HasFocus = true; + + if (Self->FocusIndex != -1) set_focus(Self, Self->FocusIndex, "FocusNotify"); +} - if (Self->prvKeyEvent) { UnsubscribeEvent(Self->prvKeyEvent); Self->prvKeyEvent = NULL; } +static void notify_lostfocus_viewport(OBJECTPTR Object, ACTIONID ActionID, ERR Result, APTR Args) +{ + if (Result != ERR::Okay) return; - Self->HasFocus = FALSE; + auto Self = (extDocument *)CurrentContext(); + Self->HasFocus = false; // Redraw any selected link so that it is unhighlighted - if ((Self->FocusIndex >= 0) and (Self->FocusIndex < Self->TabIndex)) { - if (Self->Tabs[Self->FocusIndex].Type IS TT_LINK) { - for (LONG i=0; i < Self->TotalLinks; i++) { - if ((Self->Links[i].EscapeCode IS ESC_LINK) and (Self->Links[i].Link->ID IS Self->Tabs[Self->FocusIndex].Ref)) { - acDrawArea(Self->PageID, Self->Links[i].X, Self->Links[i].Y, Self->Links[i].Width, Self->Links[i].Height); + if ((Self->FocusIndex >= 0) and (Self->FocusIndex < LONG(Self->Tabs.size()))) { + if (Self->Tabs[Self->FocusIndex].type IS TT::LINK) { + for (auto &link : Self->Links) { + if (link.origin.uid IS std::get(Self->Tabs[Self->FocusIndex].ref)) { + Self->Page->draw(); break; } } @@ -80,51 +95,53 @@ static void notify_lostfocus_surface(OBJECTPTR Object, ACTIONID ActionID, ERROR } } -static void notify_redimension_surface(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, struct acRedimension *Args) +//******************************************************************************************************************** +// Receiver for events from Self->View. Bear in mind that the XOffset and YOffset of the document's View must +// be zero initially, and will be controlled by the scrollbar. For that reason we don't need to do much here other +// than respond by updating the layout of the page. + +static ERR feedback_view(objVectorViewport *View, FM Event) { pf::Log log(__FUNCTION__); auto Self = (extDocument *)CurrentContext(); - gfxGetSurfaceCoords(Self->SurfaceID, NULL, NULL, NULL, NULL, &Self->SurfaceWidth, &Self->SurfaceHeight); + auto width = View->get(FID_Width); + auto height = View->get(FID_Height); - log.traceBranch("Redimension: %dx%d", Self->SurfaceWidth, Self->SurfaceHeight); + if ((Self->VPWidth IS width) and (Self->VPHeight IS height)) return ERR::Okay; - Self->AreaX = (Self->BorderEdge & DBE_LEFT) ? BORDER_SIZE : 0; - Self->AreaY = (Self->BorderEdge & DBE_TOP) ? BORDER_SIZE : 0; - Self->AreaWidth = Self->SurfaceWidth - (((Self->BorderEdge & DBE_RIGHT) ? BORDER_SIZE : 0)<<1); - Self->AreaHeight = Self->SurfaceHeight - (((Self->BorderEdge & DBE_BOTTOM) ? BORDER_SIZE : 0)<<1); + log.traceBranch("Redimension: %gx%g -> %gx%g", Self->VPWidth, Self->VPHeight, width, height); - acRedimension(Self->ViewID, Self->AreaX, Self->AreaY, 0, Self->AreaWidth, Self->AreaHeight, 0); + Self->VPWidth = width; + Self->VPHeight = height; - DocTrigger *trigger; - for (trigger=Self->Triggers[DRT_BEFORE_LAYOUT]; trigger; trigger=trigger->Next) { - if (trigger->Function.Type IS CALL_SCRIPT) { + for (auto &trigger : Self->Triggers[LONG(DRT::BEFORE_LAYOUT)]) { + if (trigger.isScript()) { // The resize event is triggered just prior to the layout of the document. This allows the trigger // function to resize elements on the page in preparation of the new layout. - OBJECTPTR script; - if ((script = trigger->Function.Script.Script)) { - const ScriptArg args[] = { - { "ViewWidth", FD_LONG, { .Long = Self->AreaWidth } }, - { "ViewHeight", FD_LONG, { .Long = Self->AreaHeight } } - }; - scCallback(script, trigger->Function.Script.ProcedureID, args, ARRAYSIZE(args), NULL); - } + const ScriptArg args[] = { + { "ViewWidth", Self->VPWidth }, + { "ViewHeight", Self->VPHeight } + }; + scCallback(trigger.Script.Script, trigger.Script.ProcedureID, args, std::ssize(args), NULL); } - else if (trigger->Function.Type IS CALL_STDC) { - auto routine = (void (*)(APTR, extDocument *, LONG Width, LONG Height))trigger->Function.StdC.Routine; - if (routine) { - pf::SwitchContext context(trigger->Function.StdC.Context); - routine(trigger->Function.StdC.Context, Self, Self->AreaWidth, Self->AreaHeight); - } + else if (trigger.isC()) { + auto routine = (void (*)(APTR, extDocument *, LONG, LONG, APTR))trigger.StdC.Routine; + pf::SwitchContext context(trigger.StdC.Context); + routine(trigger.StdC.Context, Self, Self->VPWidth, Self->VPHeight, trigger.StdC.Meta); } } - Self->UpdateLayout = TRUE; + Self->UpdatingLayout = true; + +#ifndef RETAIN_LOG_LEVEL + pf::LogLevel level(2); +#endif - AdjustLogLevel(2); layout_doc(Self); - AdjustLogLevel(-2); + + return ERR::Okay; } /********************************************************************************************************************* @@ -137,17 +154,17 @@ belong to the document object. *********************************************************************************************************************/ -static ERROR DOCUMENT_Activate(extDocument *Self, APTR Void) +static ERR DOCUMENT_Activate(extDocument *Self, APTR Void) { pf::Log log; log.branch(); pf::vector list; - if (!ListChildren(Self->UID, &list)) { + if (ListChildren(Self->UID, &list) IS ERR::Okay) { for (unsigned i=0; i < list.size(); i++) acActivate(list[i].ObjectID); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -191,63 +208,12 @@ NullArgs *********************************************************************************************************************/ -static ERROR DOCUMENT_AddListener(extDocument *Self, struct docAddListener *Args) -{ - DocTrigger *trigger; - - if ((!Args) or (!Args->Trigger) or (!Args->Function)) return ERR_NullArgs; - - if (!AllocMemory(sizeof(DocTrigger), MEM::DATA|MEM::NO_CLEAR, &trigger)) { - trigger->Function = *Args->Function; - trigger->Next = Self->Triggers[Args->Trigger]; - Self->Triggers[Args->Trigger] = trigger; - return ERR_Okay; - } - else return ERR_AllocMemory; -} - -/********************************************************************************************************************* - --METHOD- -ApplyFontStyle: Applies DocStyle information to a font. - -This method applies font information from DocStyle structures to new @Font objects. The Font object -should be uninitialised as it is not possible to apply changes to the font face, style or size after initialisation. - --INPUT- -struct(*DocStyle) Style: Pointer to a DocStyle structure. -obj(Font) Font: Pointer to a Font object that the style information will be applied to. - --ERRORS- -Okay -NullArgs --END- - -*********************************************************************************************************************/ - -static ERROR DOCUMENT_ApplyFontStyle(extDocument *Self, struct docApplyFontStyle *Args) +static ERR DOCUMENT_AddListener(extDocument *Self, struct docAddListener *Args) { - pf::Log log; - objFont *font; - DOCSTYLE *style; - - if ((!Args) or (!(style = Args->Style)) or (!(font = Args->Font))) return log.warning(ERR_NullArgs); + if ((!Args) or (Args->Trigger IS DRT::NIL) or (!Args->Function)) return ERR::NullArgs; - log.traceBranch("Apply font styling - Face: %s, Style: %s", style->Font->Face, style->Font->Style); - - if (font->initialised()) { - font->Colour = style->FontColour; - font->Underline = style->FontUnderline; - } - else { - font->setFace(style->Font->Face); - font->setStyle(style->Font->Style); - font->Point = style->Font->Point; - font->Colour = style->FontColour; - font->Underline = style->FontUnderline; - } - - return ERR_Okay; + Self->Triggers[LONG(Args->Trigger)].push_back(*Args->Function); + return ERR::Okay; } /********************************************************************************************************************* @@ -275,19 +241,18 @@ NullArgs *********************************************************************************************************************/ -static ERROR DOCUMENT_CallFunction(extDocument *Self, struct docCallFunction *Args) +static ERR DOCUMENT_CallFunction(extDocument *Self, struct docCallFunction *Args) { pf::Log log; - if ((!Args) or (!Args->Function)) return log.warning(ERR_NullArgs); + if ((!Args) or (!Args->Function)) return log.warning(ERR::NullArgs); // Function is in the format 'function()' or 'script.function()' - OBJECTPTR script; - CSTRING function_name; - ERROR error; - if (!(error = extract_script(Self, Args->Function, &script, &function_name, NULL))) { - return scExec(script, function_name, Args->Args, Args->TotalArgs); + objScript *script; + std::string function_name, args; + if (auto error = extract_script(Self, Args->Function, &script, function_name, args); error IS ERR::Okay) { + return scExec(script, function_name.c_str(), Args->Args, Args->TotalArgs); } else return error; } @@ -297,20 +262,19 @@ static ERROR DOCUMENT_CallFunction(extDocument *Self, struct docCallFunction *Ar -ACTION- Clear: Clears all content from the object. -You can delete all of the document information from a document object by calling the Clear action. All of the document -data will be deleted from the object and the graphics will be automatically updated as a result of calling this action. +Using the Clear() action will delete all of the document's content. The UI will be updated to reflect a clear +document. *********************************************************************************************************************/ -static ERROR DOCUMENT_Clear(extDocument *Self, APTR Void) +static ERR DOCUMENT_Clear(extDocument *Self, APTR Void) { pf::Log log; log.branch(); - unload_doc(Self, 0); - if (Self->XML) { FreeResource(Self->XML); Self->XML = NULL; } - redraw(Self, FALSE); - return ERR_Okay; + unload_doc(Self); + redraw(Self, false); + return ERR::Okay; } /********************************************************************************************************************* @@ -321,13 +285,11 @@ Clipboard: Full support for clipboard activity is provided through this action. *********************************************************************************************************************/ -static ERROR DOCUMENT_Clipboard(extDocument *Self, struct acClipboard *Args) +static ERR DOCUMENT_Clipboard(extDocument *Self, struct acClipboard *Args) { pf::Log log; - STRING buffer; - LONG size; - if ((!Args) or (!Args->Mode)) return log.warning(ERR_NullArgs); + if ((!Args) or (Args->Mode IS CLIPMODE::NIL)) return log.warning(ERR::NullArgs); if ((Args->Mode IS CLIPMODE::CUT) or (Args->Mode IS CLIPMODE::COPY)) { if (Args->Mode IS CLIPMODE::CUT) log.branch("Operation: Cut"); @@ -336,77 +298,59 @@ static ERROR DOCUMENT_Clipboard(extDocument *Self, struct acClipboard *Args) // Calculate the length of the highlighted document if (Self->SelectEnd != Self->SelectStart) { - if (!AllocMemory(Self->SelectEnd - Self->SelectStart + 1, MEM::STRING|MEM::NO_CLEAR, &buffer)) { - // Copy the selected area into the buffer - - LONG i = Self->SelectStart; - LONG pos = 0; - if (auto str = Self->Stream) { - while (str[i]) { - NEXT_CHAR(str, i); - } - } + auto buffer = stream_to_string(Self->Stream, Self->SelectStart, Self->SelectEnd); - buffer[pos] = 0; + // Send the document to the clipboard object - // Send the document to the clipboard object - - objClipboard::create clipboard = { }; - if (clipboard.ok()) { - if (!clipAddText(*clipboard, buffer)) { - // Delete the highlighted document if the CUT mode was used - if (Args->Mode IS CLIPMODE::CUT) { - //delete_selection(Self); - } + objClipboard::create clipboard = { }; + if (clipboard.ok()) { + if (clipAddText(*clipboard, buffer.c_str()) IS ERR::Okay) { + // Delete the highlighted document if the CUT mode was used + if (Args->Mode IS CLIPMODE::CUT) { + //delete_selection(Self); } - else error_dialog("Clipboard Error", "Failed to add document to the system clipboard.", 0); } - - FreeResource(buffer); + else error_dialog("Clipboard Error", "Failed to add document to the system clipboard."); } - else return ERR_AllocMemory; } - return ERR_Okay; + return ERR::Okay; } else if (Args->Mode IS CLIPMODE::PASTE) { log.branch("Operation: Paste"); - if (!(Self->Flags & DCF_EDIT)) { + if ((Self->Flags & DCF::EDIT) IS DCF::NIL) { log.warning("Edit mode is not enabled, paste operation aborted."); - return ERR_Failed; + return ERR::Failed; } objClipboard::create clipboard = { }; if (clipboard.ok()) { struct clipGetFiles get = { .Datatype = CLIPTYPE::TEXT, .Index = 0 }; - if (!Action(MT_ClipGetFiles, *clipboard, &get)) { + if (Action(MT_ClipGetFiles, *clipboard, &get) IS ERR::Okay) { objFile::create file = { fl::Path(get.Files[0]), fl::Flags(FL::READ) }; if (file.ok()) { - if ((!file->get(FID_Size, &size)) and (size > 0)) { + LONG size; + if ((file->get(FID_Size, &size) IS ERR::Okay) and (size > 0)) { if (auto buffer = new (std::nothrow) char[size+1]) { LONG result; - if (!file->read(buffer, size, &result)) { + if (file->read(buffer, size, &result) IS ERR::Okay) { buffer[result] = 0; acDataText(Self, buffer); } - else error_dialog("Clipboard Paste Error", NULL, ERR_Read); + else error_dialog("Clipboard Paste Error", ERR::Read); delete[] buffer; } - else error_dialog("Clipboard Paste Error", NULL, ERR_AllocMemory); + else error_dialog("Clipboard Paste Error", ERR::AllocMemory); } } - else { - char msg[200]; - snprintf(msg, sizeof(msg), "Failed to load clipboard file \"%s\"", get.Files[0]); - error_dialog("Paste Error", msg, 0); - } + else error_dialog("Paste Error", "Failed to load clipboard file \"" + std::string(get.Files[0]) + "\""); } } - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_Args); + else return log.warning(ERR::Args); } /********************************************************************************************************************* @@ -415,9 +359,7 @@ static ERROR DOCUMENT_Clipboard(extDocument *Self, struct acClipboard *Args) DataFeed: Document data can be sent and consumed via feeds. Appending content to an active document can be achieved via the data feed feature. The Document class currently -supports the DATA_DOCUMENT and DATA_XML types for this purpose. - -The surface that is associated with the Document object will be redrawn as a result of calling this action. +supports the `DATA::TEXT` and `DATA::XML` types for this purpose. -ERRORS- Okay @@ -428,72 +370,74 @@ Mismatch: The data type that was passed to the action is not supported by the *********************************************************************************************************************/ -static ERROR DOCUMENT_DataFeed(extDocument *Self, struct acDataFeed *Args) +static ERR DOCUMENT_DataFeed(extDocument *Self, struct acDataFeed *Args) { pf::Log log; - if ((!Args) or (!Args->Buffer)) return log.warning(ERR_NullArgs); + if ((!Args) or (!Args->Buffer)) return log.warning(ERR::NullArgs); - if ((Args->Datatype IS DATA_TEXT) or (Args->Datatype IS DATA_XML)) { + if ((Args->Datatype IS DATA::TEXT) or (Args->Datatype IS DATA::XML)) { // Incoming data is translated on the fly and added to the end of the current document page. The original XML // information is retained in case of refresh. // - // Note that in the case of incoming text identified by DATA_TEXT, it is assumed to be in XML format. - - if (Self->Processing) return log.warning(ERR_Recursion); - - if (!Self->XML) { - if (!(Self->XML = objXML::create::integral(fl::Flags(XMF_ALL_CONTENT|XMF_PARSE_HTML|XMF_STRIP_HEADERS)))) { - return log.warning(ERR_CreateObject); + // NOTE: Content identified by DATA::TEXT is assumed to be in a serialised XML format. + + if (!Self->initialised()) return log.warning(ERR::NotInitialised); + if (Self->Processing) return log.warning(ERR::Recursion); + + objXML::create xml = { + fl::Flags(XMF::ALL_CONTENT|XMF::PARSE_HTML|XMF::STRIP_HEADERS|XMF::WELL_FORMED), + fl::Statement(CSTRING(Args->Buffer)), + fl::ReadOnly(true) + }; + + if (xml.ok()) { + if (Self->Stream.data.empty()) { + // If the document is empty then we use the same process as load_doc() + parser parse(Self, &Self->Stream); + parse.process_page(*xml); } - } - - log.trace("Appending data to XML #%d at tag index %d.", Self->XML->UID, Self->XML->TagCount); - - if (acDataXML(Self->XML, Args->Buffer) != ERR_Okay) { - return log.warning(ERR_SetField); - } - - if (Self->initialised()) { - // Document is initialised. Refresh the document from the XML source. + else Self->Error = insert_xml(Self, &Self->Stream, *xml, xml->Tags, Self->Stream.size(), STYLE::NIL); - acRefresh(Self); - } - else { - // Document is not yet initialised. Processing of the XML will be handled in Init() as required. + Self->UpdatingLayout = true; + if (Self->initialised()) redraw(Self, true); + #ifdef DBG_STREAM + print_stream(Self->Stream); + #endif + return Self->Error; } - - return ERR_Okay; - } - else { - log.msg("Datatype %d not supported.", Args->Datatype); - return ERR_Mismatch; + else return log.warning(ERR::CreateObject); } + else return log.warning(ERR::Mismatch); } /********************************************************************************************************************* -ACTION- -Disable: Disables object functionality. +Disable: Disables user interactivity. -END- *********************************************************************************************************************/ -static ERROR DOCUMENT_Disable(extDocument *Self, APTR Void) +static ERR DOCUMENT_Disable(extDocument *Self, APTR Void) { - Self->Flags |= DCF_DISABLED; - return ERR_Okay; + Self->Flags |= DCF::DISABLED; + return ERR::Okay; } -//******************************************************************************************************************** +/********************************************************************************************************************* +-ACTION- +Draw: Force a page layout update (if changes are pending) and redraw to the display. +-END- +*********************************************************************************************************************/ -static ERROR DOCUMENT_Draw(extDocument *Self, APTR Void) +static ERR DOCUMENT_Draw(extDocument *Self, APTR Void) { - if (Self->SurfaceID) { - if (Self->Processing) QueueAction(AC_Draw, Self->UID); - else redraw(Self, FALSE); - return ERR_Okay; + if (Self->Viewport) { + if (Self->Processing) Self->Viewport->draw(); + else redraw(Self, false); + return ERR::Okay; } - else return ERR_FieldNotSet; + else return ERR::FieldNotSet; } /********************************************************************************************************************* @@ -519,23 +463,19 @@ Search: The cell was not found. *********************************************************************************************************************/ -static ERROR DOCUMENT_Edit(extDocument *Self, struct docEdit *Args) +static ERR DOCUMENT_Edit(extDocument *Self, struct docEdit *Args) { - if (!Args) return ERR_NullArgs; + if (!Args) return ERR::NullArgs; if (!Args->Name) { - if ((Self->CursorIndex IS -1) or (!Self->ActiveEditDef)) return ERR_Okay; - deactivate_edit(Self, TRUE); - return ERR_Okay; + if ((!Self->CursorIndex.valid()) or (!Self->ActiveEditDef)) return ERR::Okay; + deactivate_edit(Self, true); + return ERR::Okay; } - else { - LONG cellindex; - ULONG hashname = StrHash(Args->Name, 0); - if ((cellindex = find_cell(Self, 0, hashname)) >= 0) { - return activate_edit(Self, cellindex, 0); - } - else return ERR_Search; + else if (auto cellindex = Self->Stream.find_editable_cell(Args->Name); cellindex >= 0) { + return activate_cell_edit(Self, cellindex, stream_char(0,0)); } + else return ERR::Search; } /********************************************************************************************************************* @@ -544,10 +484,10 @@ Enable: Enables object functionality. -END- *********************************************************************************************************************/ -static ERROR DOCUMENT_Enable(extDocument *Self, APTR Void) +static ERR DOCUMENT_Enable(extDocument *Self, APTR Void) { - Self->Flags &= ~DCF_DISABLED; - return ERR_Okay; + Self->Flags &= ~DCF::DISABLED; + return ERR::Okay; } /********************************************************************************************************************* @@ -566,19 +506,19 @@ NullArgs *********************************************************************************************************************/ -static ERROR DOCUMENT_FeedParser(extDocument *Self, struct docFeedParser *Args) +static ERR DOCUMENT_FeedParser(extDocument *Self, struct docFeedParser *Args) { pf::Log log; - if ((!Args) or (!Args->String)) return ERR_NullArgs; + if ((!Args) or (!Args->String)) return ERR::NullArgs; - if (!Self->Processing) return log.warning(ERR_Failed); + if (!Self->Processing) return log.warning(ERR::Failed); - return ERR_NoSupport; + return ERR::NoSupport; } /********************************************************************************************************************* @@ -592,8 +532,8 @@ a section of content that may change during run-time viewing, or as place-marker document position. If the named index exists, then the start and end points (as determined by the opening and closing of the index tag) -will be returned as byte indexes in the document stream. The starting byte will refer to an ESC_INDEX_START code and -the end byte will refer to an ESC_INDEX_END code. +will be returned as byte indexes in the document stream. The starting byte will refer to an SCODE::INDEX_START code and +the end byte will refer to an SCODE::INDEX_END code. -INPUT- cstr Name: The name of the index to search for. @@ -607,52 +547,39 @@ Search: The index was not found. *********************************************************************************************************************/ -static ERROR DOCUMENT_FindIndex(extDocument *Self, struct docFindIndex *Args) +static ERR DOCUMENT_FindIndex(extDocument *Self, struct docFindIndex *Args) { pf::Log log; - if ((!Args) or (!Args->Name)) return log.warning(ERR_NullArgs); - - auto stream = Self->Stream; - if (!stream) return ERR_Search; + if ((!Args) or (!Args->Name)) return log.warning(ERR::NullArgs); log.trace("Name: %s", Args->Name); - ULONG name_hash = StrHash(Args->Name, 0); - LONG i = 0; - while (stream[i]) { - if (stream[i] IS CTRL_CODE) { - if (ESCAPE_CODE(stream, i) IS ESC_INDEX_START) { - auto index = escape_data(stream, i); - if (name_hash IS index->NameHash) { - LONG end_id = index->ID; - Args->Start = i; - - NEXT_CHAR(stream, i); - - // Search for the end (ID match) - - while (stream[i]) { - if (stream[i] IS CTRL_CODE) { - if (ESCAPE_CODE(stream, i) IS ESC_INDEX_END) { - auto end = escape_data(stream, i); - if (end_id IS end->ID) { - Args->End = i; - log.trace("Found index at range %d - %d", Args->Start, Args->End); - return ERR_Okay; - } - } + auto name_hash = StrHash(Args->Name); + for (INDEX i=0; i < INDEX(Self->Stream.size()); i++) { + if (Self->Stream[i].code IS SCODE::INDEX_START) { + auto &index = Self->Stream.lookup(i); + if (name_hash IS index.name_hash) { + auto end_id = index.id; + Args->Start = i; + + // Search for the end (ID match) + + for (++i; i < INDEX(Self->Stream.size()); i++) { + if (Self->Stream[i].code IS SCODE::INDEX_END) { + if (end_id IS Self->Stream.lookup(i).id) { + Args->End = i; + log.trace("Found index at range %d - %d", Args->Start, Args->End); + return ERR::Okay; } - NEXT_CHAR(stream, i); } } } } - NEXT_CHAR(stream, i); } - log.extmsg("Failed to find index '%s'", Args->Name); - return ERR_Search; + log.detail("Failed to find index '%s'", Args->Name); + return ERR::Search; } /********************************************************************************************************************* @@ -661,62 +588,38 @@ Focus: Sets the user focus on the document page. -END- *********************************************************************************************************************/ -static ERROR DOCUMENT_Focus(extDocument *Self, APTR Args) +static ERR DOCUMENT_Focus(extDocument *Self, APTR Args) { - acFocus(Self->PageID); - return ERR_Okay; + acFocus(Self->Page); + return ERR::Okay; } //******************************************************************************************************************** -static ERROR DOCUMENT_Free(extDocument *Self, APTR Void) +static ERR DOCUMENT_Free(extDocument *Self, APTR Void) { - if (Self->prvKeyEvent) { UnsubscribeEvent(Self->prvKeyEvent); Self->prvKeyEvent = NULL; } if (Self->FlashTimer) { UpdateTimer(Self->FlashTimer, 0); Self->FlashTimer = 0; } - if (Self->PageID) { FreeResource(Self->PageID); Self->PageID = 0; } - if (Self->ViewID) { FreeResource(Self->ViewID); Self->ViewID = 0; } - if (Self->InsertXML) { FreeResource(Self->InsertXML); Self->InsertXML = NULL; } + Self->Page = NULL; // Page and View are freed by their parent Viewport. + Self->View = NULL; - if ((Self->FocusID) and (Self->FocusID != Self->SurfaceID)) { - OBJECTPTR object; - if (!AccessObject(Self->FocusID, 5000, &object)) { - UnsubscribeAction(object, 0); - ReleaseObject(object); - } - } + if ((Self->Focus) and (Self->Focus != Self->Viewport)) UnsubscribeAction(Self->Focus, 0); - if (Self->SurfaceID) { - OBJECTPTR object; - if (!AccessObject(Self->SurfaceID, 5000, &object)) { - drwRemoveCallback(object, NULL); - UnsubscribeAction(object, 0); - ReleaseObject(object); - } - } + if (Self->PretextXML) { FreeResource(Self->PretextXML); Self->PretextXML = NULL; } - if (Self->PointerLocked) { - gfxRestoreCursor(PTR_DEFAULT, Self->UID); - Self->PointerLocked = FALSE; - } + if (Self->Viewport) UnsubscribeAction(Self->Viewport, 0); - if (Self->PageName) { FreeResource(Self->PageName); Self->PageName = NULL; } - if (Self->Bookmark) { FreeResource(Self->Bookmark); Self->Bookmark = NULL; } + if (Self->EventCallback.isScript()) { + UnsubscribeAction(Self->EventCallback.Script.Script, AC_Free); + Self->EventCallback.clear(); + } - unload_doc(Self, ULD_TERMINATE); + unload_doc(Self, ULD::TERMINATE); - if (Self->TBuffer) { FreeResource(Self->TBuffer); Self->TBuffer = NULL; } - if (Self->Path) { FreeResource(Self->Path); Self->Path = NULL; } - if (Self->XML) { FreeResource(Self->XML); Self->XML = NULL; } - if (Self->FontFace) { FreeResource(Self->FontFace); Self->FontFace = NULL; } - if (Self->Buffer) { FreeResource(Self->Buffer); Self->Buffer = NULL; } - if (Self->Temp) { FreeResource(Self->Temp); Self->Temp = NULL; } - if (Self->WorkingPath) { FreeResource(Self->WorkingPath); Self->WorkingPath = NULL; } - if (Self->Templates) { FreeResource(Self->Templates); Self->Templates = NULL; } - if (Self->InputHandle) { gfxUnsubscribeInput(Self->InputHandle); Self->InputHandle = 0; }; + if (Self->Templates) { FreeResource(Self->Templates); Self->Templates = NULL; } Self->~extDocument(); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -725,145 +628,107 @@ GetVar: Script arguments can be retrieved through this action. -END- *********************************************************************************************************************/ -static ERROR DOCUMENT_GetVar(extDocument *Self, struct acGetVar *Args) +static ERR DOCUMENT_GetVar(extDocument *Self, struct acGetVar *Args) { - if ((!Args) or (!Args->Buffer) or (!Args->Field) or (Args->Size < 2)) return ERR_Args; + if ((!Args) or (!Args->Buffer) or (!Args->Field) or (Args->Size < 2)) return ERR::Args; if (Self->Vars.contains(Args->Field)) { StrCopy(Self->Vars[Args->Field], Args->Buffer, Args->Size); - return ERR_Okay; + return ERR::Okay; } else if (Self->Params.contains(Args->Field)) { StrCopy(Self->Params[Args->Field], Args->Buffer, Args->Size); - return ERR_Okay; + return ERR::Okay; } Args->Buffer[0] = 0; - return ERR_UnsupportedField; + return ERR::UnsupportedField; } //******************************************************************************************************************** -static ERROR DOCUMENT_Init(extDocument *Self, APTR Void) +static ERR DOCUMENT_Init(extDocument *Self, APTR Void) { pf::Log log; - if (!Self->SurfaceID) return log.warning(ERR_UnsupportedOwner); - - if (!Self->FocusID) Self->FocusID = Self->SurfaceID; - - objSurface *surface; - if (!AccessObject(Self->FocusID, 5000, &surface)) { - if (surface->ClassID != ID_SURFACE) { - ReleaseObject(surface); - return log.warning(ERR_WrongObjectType); - } - - if (surface->Flags & RNF_HAS_FOCUS) { - Self->HasFocus = true; - - auto call = make_function_stdc(key_event); - SubscribeEvent(EVID_IO_KEYBOARD_KEYPRESS, &call, Self, &Self->prvKeyEvent); + if (!Self->Viewport) { + if ((Self->Owner) and (Self->Owner->Class->ClassID IS ID_VECTORVIEWPORT)) { + Self->Viewport = (objVectorViewport *)Self->Owner; } - - auto callback = make_function_stdc(notify_focus_surface); - SubscribeAction(surface, AC_Focus, &callback); - - callback = make_function_stdc(notify_lostfocus_surface); - SubscribeAction(surface, AC_LostFocus, &callback); - - ReleaseObject(surface); + else return log.warning(ERR::UnsupportedOwner); } - // Setup the target surface + if (!Self->Focus) Self->Focus = Self->Viewport; - if (!AccessObject(Self->SurfaceID, 5000, &surface)) { - Self->SurfaceWidth = surface->Width; - Self->SurfaceHeight = surface->Height; - - surface->setColour("255,255,255"); - - auto callback = make_function_stdc(notify_disable_surface); - SubscribeAction(surface, AC_Disable, &callback); + if (Self->Focus->Class->ClassID != ID_VECTORVIEWPORT) { + return log.warning(ERR::WrongObjectType); + } - callback = make_function_stdc(notify_enable_surface); - SubscribeAction(surface, AC_Enable, &callback); + if ((Self->Focus->Flags & VF::HAS_FOCUS) != VF::NIL) Self->HasFocus = true; - callback = make_function_stdc(notify_redimension_surface); - SubscribeAction(surface, AC_Redimension, &callback); + if (Self->Viewport->Scene->SurfaceID) { // Make UI subscriptions as long as we're not headless + vecSubscribeKeyboard(Self->Viewport, FUNCTION(key_event)); + SubscribeAction(Self->Focus, AC_Focus, FUNCTION(notify_focus_viewport)); + SubscribeAction(Self->Focus, AC_LostFocus, FUNCTION(notify_lostfocus_viewport)); + SubscribeAction(Self->Viewport, AC_Disable, FUNCTION(notify_disable_viewport)); + SubscribeAction(Self->Viewport, AC_Enable, FUNCTION(notify_enable_viewport)); + } - if (Self->Border.Alpha > 0) { - if (!Self->BorderEdge) Self->BorderEdge = DBE_TOP|DBE_BOTTOM|DBE_RIGHT|DBE_LEFT; - drwAddCallback(surface, (APTR)&draw_border); - } + SubscribeAction(Self->Viewport, AC_Free, FUNCTION(notify_free_viewport)); - Self->AreaX = (Self->BorderEdge & DBE_LEFT) ? BORDER_SIZE : 0; - Self->AreaY = (Self->BorderEdge & DBE_TOP) ? BORDER_SIZE : 0; - Self->AreaWidth = Self->SurfaceWidth - (((Self->BorderEdge & DBE_RIGHT) ? BORDER_SIZE : 0)<<1); - Self->AreaHeight = Self->SurfaceHeight - (((Self->BorderEdge & DBE_BOTTOM) ? BORDER_SIZE : 0)<<1); + Self->VPWidth = Self->Viewport->get(FID_Width); + Self->VPHeight = Self->Viewport->get(FID_Height); - ReleaseObject(surface); - } - else return ERR_AccessObject; + FLOAT bkgd[4] = { 1.0, 1.0, 1.0, 1.0 }; + Self->Viewport->setFillColour(bkgd, 4); // Allocate the view and page areas - if (auto surface = objSurface::create::integral( - fl::Name("rgnDocView"), // Do not change this name - it can be used by objects to detect if they are placed in a document - fl::Parent(Self->SurfaceID), - fl::X(Self->AreaX), fl::Y(Self->AreaY), - fl::Width(Self->AreaWidth), fl::Height(Self->AreaHeight))) { + //if ((Self->Scene = objVectorScene::create::integral( + // fl::Name("docScene"), + // fl::Owner(Self->Viewport->UID)))) { + //} + //else return ERR::CreateObject; - Self->ViewID = surface->UID; - drwAddCallback(surface, (APTR)&draw_background); - } - else return ERR_CreateObject; + Self->Scene = Self->Viewport->Scene; - if (auto surface = objSurface::create::integral( - fl::Name("rgnDocPage"), // Do not change this name - it can be used by objects to detect if they are placed in a document - fl::Parent(Self->ViewID), + if ((Self->View = objVectorViewport::create::global( + fl::Name("docView"), + fl::Owner(Self->Viewport->UID), + fl::Overflow(VOF::HIDDEN), fl::X(0), fl::Y(0), - fl::MaxWidth(0x7fffffff), fl::MaxHeight(0x7fffffff), - fl::Width(MAX_PAGEWIDTH), fl::Height(MAX_PAGEHEIGHT), - fl::Flags(RNF_TRANSPARENT|RNF_GRAB_FOCUS))) { - - drwAddCallback(surface, (APTR)&draw_document); - auto callback = make_function_stdc(consume_input_events); - gfxSubscribeInput(&callback, Self->PageID, JTYPE::MOVEMENT|JTYPE::BUTTON, 0, &Self->InputHandle); - Self->PageID = surface->UID; + fl::XOffset(0), fl::YOffset(0)))) { } - else return ERR_CreateObject; - - acShow(Self->ViewID); - acShow(Self->PageID); - - // TODO: Launch the scrollbar script with references to our Target, Page and View viewports - - if (!(Self->Flags & DCF_NO_SCROLLBARS)) { + else return ERR::CreateObject; + if ((Self->Page = objVectorViewport::create::global( + fl::Name("docPage"), + fl::Owner(Self->View->UID), + fl::X(0), fl::Y(0), + fl::Width(MAX_PAGE_WIDTH), fl::Height(MAX_PAGE_HEIGHT)))) { + // Recent changes mean that page input handling could be merged with inputevent_cell() + // if necessary (VectorScene already manages existing use-cases). + //if (Self->Page->Scene->SurfaceID) { + // vecSubscribeInput(Self->Page, JTYPE::MOVEMENT|JTYPE::BUTTON, FUNCTION(consume_input_events)); + //} } + else return ERR::CreateObject; + + vecSubscribeFeedback(Self->View, FM::PATH_CHANGED, FUNCTION(feedback_view)); // Flash the cursor via the timer - if (Self->Flags & DCF_EDIT) { - auto call = make_function_stdc(flash_cursor); - SubscribeTimer(0.5, &call, &Self->FlashTimer); + if ((Self->Flags & DCF::EDIT) != DCF::NIL) { + SubscribeTimer(0.5, FUNCTION(flash_cursor), &Self->FlashTimer); } // Load a document file into the line array if required - Self->UpdateLayout = TRUE; - if (Self->XML) { // If XML data is already present, it's probably come in through the data channels. - log.trace("XML data already loaded."); - if (Self->Path) process_parameters(Self, Self->Path); - AdjustLogLevel(2); - process_page(Self, Self->XML); - AdjustLogLevel(-2); - } - else if (Self->Path) { + Self->UpdatingLayout = true; + if (!Self->Path.empty()) { if ((Self->Path[0] != '#') and (Self->Path[0] != '?')) { - if (auto error = load_doc(Self, Self->Path, FALSE, 0)) { + if (auto error = load_doc(Self, Self->Path, false); error != ERR::Okay) { return error; } } @@ -874,8 +739,9 @@ static ERROR DOCUMENT_Init(extDocument *Self, APTR Void) } } - redraw(Self, TRUE); - return ERR_Okay; + redraw(Self, true); + + return ERR::Okay; } /********************************************************************************************************************* @@ -900,75 +766,68 @@ Search *********************************************************************************************************************/ -static ERROR DOCUMENT_HideIndex(extDocument *Self, struct docHideIndex *Args) +static ERR DOCUMENT_HideIndex(extDocument *Self, struct docHideIndex *Args) { pf::Log log(__FUNCTION__); LONG tab; - if ((!Args) or (!Args->Name)) return log.warning(ERR_NullArgs); + if ((!Args) or (!Args->Name)) return log.warning(ERR::NullArgs); log.msg("Index: %s", Args->Name); - auto stream = Self->Stream; - if (!stream) return ERR_Search; - - ULONG name_hash = StrHash(Args->Name, 0); - LONG i = 0; - while (stream[i]) { - if (stream[i] IS CTRL_CODE) { - if (ESCAPE_CODE(stream, i) IS ESC_INDEX_START) { - auto index = escape_data(stream, i); - if (name_hash IS index->NameHash) { - if (!index->Visible) return ERR_Okay; // It's already invisible! - - index->Visible = FALSE; - - AdjustLogLevel(2); - Self->UpdateLayout = TRUE; - layout_doc(Self); - AdjustLogLevel(-2); - - // Any objects within the index will need to be hidden. Also, set ParentVisible markers to FALSE. - - NEXT_CHAR(stream, i); - while (stream[i]) { - if (stream[i] IS CTRL_CODE) { - UBYTE code = ESCAPE_CODE(stream, i); - if (code IS ESC_INDEX_END) { - auto end = escape_data(stream, i); - if (index->ID IS end->ID) break; - } - else if (code IS ESC_OBJECT) { - auto escobj = escape_data(stream, i); - if (escobj->ObjectID) acHide(escobj->ObjectID); + auto &stream = Self->Stream; + auto name_hash = StrHash(Args->Name); + for (INDEX i=0; i < INDEX(stream.size()); i++) { + if (stream[i].code IS SCODE::INDEX_START) { + auto &index = Self->Stream.lookup(i); + if (name_hash IS index.name_hash) { + if (!index.visible) return ERR::Okay; // It's already invisible! + + index.visible = false; + + { + #ifndef RETAIN_LOG_LEVEL + pf::LogLevel level(2); + #endif + Self->UpdatingLayout = true; + layout_doc(Self); + } - if ((tab = find_tabfocus(Self, TT_OBJECT, escobj->ObjectID)) >= 0) { - Self->Tabs[tab].Active = FALSE; - } - } - else if (code IS ESC_LINK) { - auto esclink = escape_data(stream, i); - if ((tab = find_tabfocus(Self, TT_LINK, esclink->ID)) >= 0) { - Self->Tabs[tab].Active = FALSE; - } - } - else if (code IS ESC_INDEX_START) { - auto index = escape_data(stream, i); - index->ParentVisible = FALSE; - } - } - NEXT_CHAR(stream, i); - } + // Any objects within the index will need to be hidden. Also, set ParentVisible markers to false. - DRAW_PAGE(Self); - return ERR_Okay; + for (++i; i < INDEX(stream.size()); i++) { + auto code = stream[i].code; + if (code IS SCODE::INDEX_END) { + auto &end = Self->Stream.lookup(i); + if (index.id IS end.id) break; + } + else if (code IS SCODE::IMAGE) { + auto &vec = Self->Stream.lookup(i); + if (!vec.rect.empty()) acHide(vec.rect->UID); + + if (auto tab = find_tabfocus(Self, TT::VECTOR, vec.rect->UID); tab >= 0) { + Self->Tabs[tab].active = false; + } + } + else if (code IS SCODE::LINK) { + auto &esclink = Self->Stream.lookup(i); + if ((tab = find_tabfocus(Self, TT::LINK, esclink.uid)) >= 0) { + Self->Tabs[tab].active = false; + } + } + else if (code IS SCODE::INDEX_START) { + auto &index = Self->Stream.lookup(i); + index.parent_visible = false; + } } + + Self->Viewport->draw(); + return ERR::Okay; } } - NEXT_CHAR(stream, i); } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -992,61 +851,36 @@ int Index: The byte position at which to insert the new content. -ERRORS- Okay NullArgs +NoData +CreateObject +OutOfRange -END- *********************************************************************************************************************/ -static ERROR DOCUMENT_InsertXML(extDocument *Self, struct docInsertXML *Args) +static ERR DOCUMENT_InsertXML(extDocument *Self, struct docInsertXML *Args) { pf::Log log; - if ((!Args) or (!Args->XML)) return log.warning(ERR_NullArgs); - if ((Args->Index < -1) or (Args->Index > Self->StreamLen)) return log.warning(ERR_OutOfRange); - - if (!Self->Stream) return ERR_NoData; - - ERROR error = ERR_Okay; - if (!Self->InsertXML) { - if (!(Self->InsertXML = objXML::create::integral(fl::Statement(Args->XML)))) error = ERR_CreateObject; - } - else error = Self->InsertXML->setStatement(Args->XML); - - if (!error) { - if (!Self->Buffer) { - Self->BufferSize = 65536; - if (AllocMemory(Self->BufferSize, MEM::NO_CLEAR, &Self->Buffer) != ERR_Okay) { - return ERR_AllocMemory; - } - } - - if (!Self->Temp) { - Self->TempSize = 65536; - if (AllocMemory(Self->TempSize, MEM::NO_CLEAR, &Self->Temp) != ERR_Okay) { - return ERR_AllocMemory; - } - } - - if (!Self->VArg) { - if (AllocMemory(sizeof(Self->VArg[0]) * MAX_ARGS, MEM::NO_CLEAR, &Self->VArg) != ERR_Okay) { - return ERR_AllocMemory; - } - } - - Self->UpdateLayout = TRUE; + if ((!Args) or (!Args->XML)) return log.warning(ERR::NullArgs); + if ((Args->Index < -1) or (Args->Index > LONG(Self->Stream.size()))) return log.warning(ERR::OutOfRange); - Self->ParagraphDepth++; // We have to override the paragraph-content sanity check since we're inserting content on post-processing of the original XML + if (Self->Stream.data.empty()) return ERR::NoData; - if (!(error = insert_xml(Self, Self->InsertXML, Self->InsertXML->Tags[0], (Args->Index IS -1) ? Self->StreamLen : Args->Index, IXF_SIBLINGS|IXF_CLOSESTYLE))) { + objXML::create xml = { + fl::Flags(XMF::ALL_CONTENT|XMF::PARSE_HTML|XMF::STRIP_HEADERS), + fl::Statement(Args->XML) + }; - } - else log.warning("Insert failed for: %s", Args->XML); + if (!xml.ok()) { + Self->UpdatingLayout = true; - Self->ParagraphDepth--; + ERR error = insert_xml(Self, &Self->Stream, *xml, xml->Tags, (Args->Index IS -1) ? Self->Stream.size() : Args->Index, STYLE::NIL); + if (error != ERR::Okay) log.warning("Insert failed for: %s", Args->XML); - acClear(Self->InsertXML); // Reduce memory usage + return error; } - - return error; + else return ERR::CreateObject; } /********************************************************************************************************************* @@ -1065,78 +899,38 @@ to the document are complete. -INPUT- cstr Text: A UTF-8 text string. -int Index: The byte position at which to insert the new content. If -1, the text will be inserted at the end of the document stream. +int Index: Reference to a TEXT control code that will receive the content. If -1, the text will be inserted at the end of the document stream. +int Char: A character offset within the TEXT control code that will be injected with content. If -1, the text will be injected at the end of the target string. int Preformat: If TRUE, the text will be treated as pre-formatted (all whitespace, including consecutive whitespace will be recognised). -ERRORS- Okay NullArgs +OutOfRange +Failed -END- *********************************************************************************************************************/ -static ERROR DOCUMENT_InsertText(extDocument *Self, struct docInsertText *Args) +static ERR DOCUMENT_InsertText(extDocument *Self, struct docInsertText *Args) { pf::Log log(__FUNCTION__); - if ((!Args) or (!Args->Text)) return log.warning(ERR_NullArgs); - if ((Args->Index < -1) or (Args->Index > Self->StreamLen)) return log.warning(ERR_OutOfRange); - - if (!Self->Stream) return ERR_NoData; + if ((!Args) or (!Args->Text)) return log.warning(ERR::NullArgs); + if ((Args->Index < -1) or (Args->Index > std::ssize(Self->Stream))) return log.warning(ERR::OutOfRange); log.traceBranch("Index: %d, Preformat: %d", Args->Index, Args->Preformat); - Self->UpdateLayout = TRUE; - - LONG index = Args->Index; - if (index < 0) index = Self->StreamLen; - - // Clear the font style - - ClearMemory(&Self->Style, sizeof(Self->Style)); - Self->Style.FontStyle.Index = -1; - Self->Style.FontChange = FALSE; - Self->Style.StyleChange = FALSE; + Self->UpdatingLayout = true; - // Find the most recent style at the insertion point + INDEX index = Args->Index; + if (index < 0) index = Self->Stream.size(); - auto str = Self->Stream; - LONG i = Args->Index; - PREV_CHAR(str, i); - while (i > 0) { - if ((str[i] IS CTRL_CODE) and (ESCAPE_CODE(str, i) IS ESC_FONT)) { - CopyMemory(escape_data(str, i), &Self->Style.FontStyle, sizeof(escFont)); - log.trace("Found existing font style, font index %d, flags $%.8x.", Self->Style.FontStyle.Index, Self->Style.FontStyle.Options); - break; - } - PREV_CHAR(str, i); - } - - // If no style is available, we need to create a default font style and insert it at the start of the stream. - - if (Self->Style.FontStyle.Index IS -1) { - if ((Self->Style.FontStyle.Index = create_font(Self->FontFace, "Regular", Self->FontSize)) IS -1) { - if ((Self->Style.FontStyle.Index = create_font("Open Sans", "Regular", 12)) IS -1) { - return ERR_Failed; - } - } - - Self->Style.FontStyle.Colour = Self->FontColour; - Self->Style.FontChange = TRUE; - } - - objFont *font; - if ((font = lookup_font(Self->Style.FontStyle.Index, "insert_xml"))) { - StrCopy(font->Face, Self->Style.Face, sizeof(Self->Style.Face)); - Self->Style.Point = font->Point; - } - - // Insert the text - - ERROR error = insert_text(Self, &index, Args->Text, StrLength(Args->Text), Args->Preformat); + stream_char sc(index, 0); + ERR error = insert_text(Self, &Self->Stream, sc, std::string(Args->Text), Args->Preformat); #ifdef DBG_STREAM - print_stream(Self, Self->Stream); + print_stream(Self->Stream); #endif return error; @@ -1144,27 +938,11 @@ static ERROR DOCUMENT_InsertText(extDocument *Self, struct docInsertText *Args) //******************************************************************************************************************** -static ERROR DOCUMENT_NewObject(extDocument *Self, APTR Void) +static ERR DOCUMENT_NewObject(extDocument *Self, APTR Void) { new (Self) extDocument; - Self->UniqueID = 1000; - unload_doc(Self, 0); - return ERR_Okay; -} - -//******************************************************************************************************************** - -static ERROR DOCUMENT_NewOwner(extDocument *Self, struct acNewOwner *Args) -{ - if (!Self->initialised()) { - OBJECTID owner_id = Args->NewOwner->UID; - while ((owner_id) and (GetClassID(owner_id) != ID_SURFACE)) { - owner_id = GetOwnerID(owner_id); - } - if (owner_id) Self->SurfaceID = owner_id; - } - - return ERR_Okay; + unload_doc(Self); + return ERR::Okay; } /********************************************************************************************************************* @@ -1172,15 +950,15 @@ static ERROR DOCUMENT_NewOwner(extDocument *Self, struct acNewOwner *Args) -METHOD- ReadContent: Returns selected content from the document, either as plain text or original byte code. -The ReadContent method extracts content from the document stream, covering a specific area. It can return the data in -its original RIPPLE based format or translate the content into plain-text (control codes are removed). +The ReadContent method extracts content from the document stream, covering a specific area. It can return the data as +a RIPL binary stream, or translate the content into plain-text (control codes are removed). If data is extracted in its original format, no post-processing is performed to fix validity errors that may arise from an invalid data range. For instance, if an opening paragraph code is not closed with a matching paragraph end point, this will remain the case in the resulting data. -INPUT- -int Format: Set to DATA_TEXT to receive plain-text, or DATA_RAW to receive the original byte-code. +int(DATA) Format: Set to TEXT to receive plain-text, or RAW to receive the original byte-code. int Start: An index in the document stream from which data will be extracted. int End: An index in the document stream at which extraction will stop. !str Result: The data is returned in this parameter as an allocated string. @@ -1194,53 +972,43 @@ NoData: Operation successful, but no data was present for extraction. *********************************************************************************************************************/ -static ERROR DOCUMENT_ReadContent(extDocument *Self, struct docReadContent *Args) +static ERR DOCUMENT_ReadContent(extDocument *Self, struct docReadContent *Args) { pf::Log log(__FUNCTION__); - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); Args->Result = NULL; - if ((Args->Start < 0) or (Args->Start >= Self->StreamLen)) return log.warning(ERR_OutOfRange); - if ((Args->End < 0) or (Args->End >= Self->StreamLen)) return log.warning(ERR_OutOfRange); - if (Args->End <= Args->Start) return log.warning(ERR_Args); + if ((Args->Start < 0) or (Args->Start >= std::ssize(Self->Stream))) return log.warning(ERR::OutOfRange); + if ((Args->End < 0) or (Args->End >= std::ssize(Self->Stream))) return log.warning(ERR::OutOfRange); + if (Args->End <= Args->Start) return log.warning(ERR::Args); - if (Args->Format IS DATA_TEXT) { - STRING output; - if (!AllocMemory(Args->End - Args->Start + 1, MEM::NO_CLEAR, &output)) { - LONG j = 0; - LONG i = Args->Start; - while (i < Args->End) { - if (Self->Stream[i] IS CTRL_CODE) { - // Ignore escape codes - } - else output[j++] = Self->Stream[i]; - NEXT_CHAR(Self->Stream, i); - } - output[j] = 0; + if (Args->Format IS DATA::TEXT) { + std::ostringstream buffer; - if (!j) { - FreeResource(output); - return ERR_NoData; + for (INDEX i=Args->Start; i < Args->End; i++) { + if (Self->Stream[i].code IS SCODE::TEXT) { + buffer << Self->Stream.lookup(i).text; } - - Args->Result = output; - return ERR_Okay; } - else return log.warning(ERR_AllocMemory); + + auto str = buffer.str(); + if (str.empty()) return ERR::NoData; + if ((Args->Result = StrClone(str.c_str()))) return ERR::Okay; + else return log.warning(ERR::AllocMemory); } - else if (Args->Format IS DATA_RAW) { + else if (Args->Format IS DATA::RAW) { STRING output; - if (!AllocMemory(Args->End - Args->Start + 1, MEM::NO_CLEAR, &output)) { - CopyMemory(Self->Stream + Args->Start, output, Args->End - Args->Start); + if (AllocMemory(Args->End - Args->Start + 1, MEM::NO_CLEAR, &output) IS ERR::Okay) { + CopyMemory(Self->Stream.data.data() + Args->Start, output, Args->End - Args->Start); output[Args->End - Args->Start] = 0; Args->Result = output; - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_AllocMemory); + else return log.warning(ERR::AllocMemory); } - else return log.warning(ERR_Args); + else return log.warning(ERR::Args); } /********************************************************************************************************************* @@ -1249,63 +1017,43 @@ Refresh: Reloads the document data from the original source location. -END- *********************************************************************************************************************/ -static ERROR DOCUMENT_Refresh(extDocument *Self, APTR Void) +static ERR DOCUMENT_Refresh(extDocument *Self, APTR Void) { pf::Log log; if (Self->Processing) { log.msg("Recursion detected - refresh will be delayed."); QueueAction(AC_Refresh, Self->UID); - return ERR_Okay; + return ERR::Okay; } Self->Processing++; - for (auto trigger=Self->Triggers[DRT_REFRESH]; trigger; trigger=trigger->Next) { - if (trigger->Function.Type IS CALL_SCRIPT) { - // The refresh trigger can return ERR_Skip to prevent a complete reload of the document. - - OBJECTPTR script; - if ((script = trigger->Function.Script.Script)) { - ERROR error; - if (!scCallback(script, trigger->Function.Script.ProcedureID, NULL, 0, &error)) { - if (error IS ERR_Skip) { - log.msg("The refresh request has been handled by an event trigger."); - return ERR_Okay; - } + for (auto &trigger : Self->Triggers[LONG(DRT::REFRESH)]) { + if (trigger.isScript()) { + // The refresh trigger can return ERR::Skip to prevent a complete reload of the document. + + ERR error; + if (scCallback(trigger.Script.Script, trigger.Script.ProcedureID, NULL, 0, &error) IS ERR::Okay) { + if (error IS ERR::Skip) { + log.msg("The refresh request has been handled by an event trigger."); + return ERR::Okay; } } } - else if (trigger->Function.Type IS CALL_STDC) { - auto routine = (void (*)(APTR, extDocument *))trigger->Function.StdC.Routine; - if (routine) { - pf::SwitchContext context(trigger->Function.StdC.Context); - routine(trigger->Function.StdC.Context, Self); - } + else if (trigger.isC()) { + auto routine = (void (*)(APTR, extDocument *))trigger.StdC.Routine; + pf::SwitchContext context(trigger.StdC.Context); + routine(trigger.StdC.Context, Self); } } - ERROR error; - if ((Self->Path) and (Self->Path[0] != '#') and (Self->Path[0] != '?')) { - log.branch("Refreshing from path '%s'", Self->Path); - error = load_doc(Self, Self->Path, TRUE, ULD_REFRESH); - } - else if (Self->XML) { - log.branch("Refreshing from preloaded XML data."); - - AdjustLogLevel(2); - unload_doc(Self, ULD_REFRESH); - process_page(Self, Self->XML); - AdjustLogLevel(-2); - - if (Self->FocusIndex != -1) set_focus(Self, Self->FocusIndex, "Refresh-XML"); - - error = ERR_Okay; - } - else { - log.msg("No location or XML data is present in the document."); - error = ERR_Okay; + ERR error = ERR::Okay; + if ((!Self->Path.empty()) and (Self->Path[0] != '#') and (Self->Path[0] != '?')) { + log.branch("Refreshing from path '%s'", Self->Path.c_str()); + error = load_doc(Self, Self->Path, true, ULD::REFRESH); } + else log.msg("No source Path defined in the document."); Self->Processing--; @@ -1332,21 +1080,21 @@ Args *********************************************************************************************************************/ -static ERROR DOCUMENT_RemoveContent(extDocument *Self, struct docRemoveContent *Args) +static ERR DOCUMENT_RemoveContent(extDocument *Self, struct docRemoveContent *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); - if ((Args->Start < 0) or (Args->Start >= Self->StreamLen)) return log.warning(ERR_OutOfRange); - if ((Args->End < 0) or (Args->End >= Self->StreamLen)) return log.warning(ERR_OutOfRange); - if (Args->End <= Args->Start) return log.warning(ERR_Args); + if ((Args->Start < 0) or (Args->Start >= std::ssize(Self->Stream))) return log.warning(ERR::OutOfRange); + if ((Args->End < 0) or (Args->End >= std::ssize(Self->Stream))) return log.warning(ERR::OutOfRange); + if (Args->End <= Args->Start) return log.warning(ERR::Args); - CopyMemory(Self->Stream + Args->End, Self->Stream + Args->Start, Self->StreamLen - Args->End); - Self->StreamLen -= Args->End - Args->Start; + CopyMemory(Self->Stream.data.data() + Args->End, Self->Stream.data.data() + Args->Start, Self->Stream.data.size() - Args->End); + Self->Stream.data.resize(Self->Stream.data.size() - Args->End - Args->Start); - Self->UpdateLayout = TRUE; - return ERR_Okay; + Self->UpdatingLayout = true; + return ERR::Okay; } /********************************************************************************************************************* @@ -1367,37 +1115,30 @@ NullArgs *********************************************************************************************************************/ -static ERROR DOCUMENT_RemoveListener(extDocument *Self, struct docRemoveListener *Args) +static ERR DOCUMENT_RemoveListener(extDocument *Self, struct docRemoveListener *Args) { - if ((!Args) or (!Args->Trigger) or (!Args->Function)) return ERR_NullArgs; - - DocTrigger *prev = NULL; - if (Args->Function->Type IS CALL_STDC) { - for (auto trigger=Self->Triggers[Args->Trigger]; trigger; trigger=trigger->Next) { - if ((trigger->Function.Type IS CALL_STDC) and (trigger->Function.StdC.Routine IS Args->Function->StdC.Routine)) { - if (prev) prev->Next = trigger->Next; - else Self->Triggers[Args->Trigger] = trigger->Next; - FreeResource(trigger); - return ERR_Okay; + if ((!Args) or (!Args->Trigger) or (!Args->Function)) return ERR::NullArgs; + + if (Args->Function->isC()) { + for (auto it = Self->Triggers[Args->Trigger].begin(); it != Self->Triggers[Args->Trigger].end(); it++) { + if ((it->isC()) and (it->StdC.Routine IS Args->Function->StdC.Routine)) { + Self->Triggers[Args->Trigger].erase(it); + return ERR::Okay; } - prev = trigger; } } - else if (Args->Function->Type IS CALL_SCRIPT) { - for (auto trigger=Self->Triggers[Args->Trigger]; trigger; trigger=trigger->Next) { - if ((trigger->Function.Type IS CALL_SCRIPT) and - (trigger->Function.Script.Script IS Args->Function->Script.Script) and - (trigger->Function.Script.ProcedureID IS Args->Function->Script.ProcedureID)) { - if (prev) prev->Next = trigger->Next; - else Self->Triggers[Args->Trigger] = trigger->Next; - FreeResource(trigger); - return ERR_Okay; + else if (Args->Function->isScript()) { + for (auto it = Self->Triggers[Args->Trigger].begin(); it != Self->Triggers[Args->Trigger].end(); it++) { + if ((it->isScript()) and + (it->Script.Script IS Args->Function->Script.Script) and + (it->Script.ProcedureID IS Args->Function->Script.ProcedureID)) { + Self->Triggers[Args->Trigger].erase(it); + return ERR::Okay; } - prev = trigger; } } - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1406,15 +1147,15 @@ SaveToObject: Use this action to save edited information as an XML document file -END- *********************************************************************************************************************/ -static ERROR DOCUMENT_SaveToObject(extDocument *Self, struct acSaveToObject *Args) +static ERR DOCUMENT_SaveToObject(extDocument *Self, struct acSaveToObject *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); - log.branch("Destination: %d, Lines: %d", Args->Dest->UID, Self->SegCount); + log.branch("Destination: %d", Args->Dest->UID); acWrite(Args->Dest, "Save not supported.", 0, NULL); - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1423,17 +1164,17 @@ ScrollToPoint: Scrolls a document object's graphical content. -END- *********************************************************************************************************************/ -static ERROR DOCUMENT_ScrollToPoint(extDocument *Self, struct acScrollToPoint *Args) +static ERR DOCUMENT_ScrollToPoint(extDocument *Self, struct acScrollToPoint *Args) { - if (!Args) return ERR_NullArgs; + if (!Args) return ERR::NullArgs; - if (Args->Flags & STP_X) Self->XPosition = -Args->X; - if (Args->Flags & STP_Y) Self->YPosition = -Args->Y; + if ((Args->Flags & STP::X) != STP::NIL) Self->XPosition = -Args->X; + if ((Args->Flags & STP::Y) != STP::NIL) Self->YPosition = -Args->Y; // Validation: coordinates must be negative offsets - if (-Self->YPosition > Self->PageHeight - Self->AreaHeight) { - Self->YPosition = -(Self->PageHeight - Self->AreaHeight); + if (-Self->YPosition > Self->PageHeight - Self->VPHeight) { + Self->YPosition = -(Self->PageHeight - Self->VPHeight); } if (Self->YPosition > 0) Self->YPosition = 0; @@ -1441,8 +1182,8 @@ static ERROR DOCUMENT_ScrollToPoint(extDocument *Self, struct acScrollToPoint *A //log.msg("%d, %d / %d, %d", (LONG)Args->X, (LONG)Args->Y, Self->XPosition, Self->YPosition); - acMoveToPoint(Self->PageID, Self->XPosition, Self->YPosition, 0, MTF::X|MTF::Y); - return ERR_Okay; + acMoveToPoint(Self->Page, Self->XPosition, Self->YPosition, 0, MTF::X|MTF::Y); + return ERR::Okay; } /********************************************************************************************************************* @@ -1472,36 +1213,36 @@ OutOfRange *********************************************************************************************************************/ -static ERROR DOCUMENT_SelectLink(extDocument *Self, struct docSelectLink *Args) +static ERR DOCUMENT_SelectLink(extDocument *Self, struct docSelectLink *Args) { pf::Log log; - if (!Args) return log.warning(ERR_NullArgs); + if (!Args) return log.warning(ERR::NullArgs); if ((Args->Name) and (Args->Name[0])) { /* LONG i; - for (i=0; i < Self->TabIndex; i++) { - if (Self->Tabs[i].Type IS TT_OBJECT) { + for (i=0; i < Self->Tabs.size(); i++) { + if (Self->Tabs[i].Type IS TT::OBJECT) { name = GetObjectName(?) - if (!(StrMatch(Args->Name, name))) { + if (!(StrMatch(args->name, name))) { } } - else if (Self->Tabs[i].Type IS TT_LINK) { + else if (Self->Tabs[i].Type IS TT::LINK) { } } */ - return log.warning(ERR_NoSupport); + return log.warning(ERR::NoSupport); } - else if ((Args->Index >= 0) and (Args->Index < Self->TabIndex)) { + else if ((Args->Index >= 0) and (Args->Index < std::ssize(Self->Tabs))) { Self->FocusIndex = Args->Index; set_focus(Self, Args->Index, "SelectLink"); - return ERR_Okay; + return ERR::Okay; } - else return log.warning(ERR_OutOfRange); + else return log.warning(ERR::OutOfRange); } /********************************************************************************************************************* @@ -1510,16 +1251,16 @@ SetVar: Passes variable parameters to loaded documents. -END- *********************************************************************************************************************/ -static ERROR DOCUMENT_SetVar(extDocument *Self, struct acSetVar *Args) +static ERR DOCUMENT_SetVar(extDocument *Self, struct acSetVar *Args) { // Please note that it is okay to set zero-length arguments - if ((!Args) or (!Args->Field)) return ERR_NullArgs; - if (!Args->Field[0]) return ERR_Args; + if ((!Args) or (!Args->Field)) return ERR::NullArgs; + if (!Args->Field[0]) return ERR::Args; Self->Vars[Args->Field] = Args->Value; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* @@ -1544,104 +1285,74 @@ Search: The index could not be found. *********************************************************************************************************************/ -static ERROR DOCUMENT_ShowIndex(extDocument *Self, struct docShowIndex *Args) +static ERR DOCUMENT_ShowIndex(extDocument *Self, struct docShowIndex *Args) { pf::Log log; - if ((!Args) or (!Args->Name)) return log.warning(ERR_NullArgs); + if ((!Args) or (!Args->Name)) return log.warning(ERR::NullArgs); log.branch("Index: %s", Args->Name); - auto stream = Self->Stream; - if (!stream) return ERR_Search; - - ULONG name_hash = StrHash(Args->Name, 0); - LONG i = 0; - while (stream[i]) { - if (stream[i] IS CTRL_CODE) { - if (ESCAPE_CODE(stream, i) IS ESC_INDEX_START) { - auto index = escape_data(stream, i); - if (name_hash IS index->NameHash) { - - if (index->Visible) return ERR_Okay; // It's already visible! - - index->Visible = TRUE; - if (index->ParentVisible) { // We are visible, but parents must also be visible to show content - // Show all objects and manage the ParentVisible status of any child indexes - - AdjustLogLevel(2); - Self->UpdateLayout = TRUE; - layout_doc(Self); - AdjustLogLevel(-2); - - NEXT_CHAR(stream, i); - while (stream[i]) { - if (stream[i] IS CTRL_CODE) { - UBYTE code = ESCAPE_CODE(stream, i); - if (code IS ESC_INDEX_END) { - auto end = escape_data(stream, i); - if (index->ID IS end->ID) break; - } - else if (code IS ESC_OBJECT) { - auto escobj = escape_data(stream, i); - if (escobj->ObjectID) acShow(escobj->ObjectID); - - LONG tab; - if ((tab = find_tabfocus(Self, TT_OBJECT, escobj->ObjectID)) >= 0) { - Self->Tabs[tab].Active = TRUE; - } - } - else if (code IS ESC_LINK) { - auto esclink = escape_data(stream, i); - - LONG tab; - if ((tab = find_tabfocus(Self, TT_LINK, esclink->ID)) >= 0) { - Self->Tabs[tab].Active = TRUE; - } - } - else if (code IS ESC_INDEX_START) { - auto index = escape_data(stream, i); - index->ParentVisible = TRUE; - - if (!index->Visible) { - // The child index is not visible, so skip to the end of it before continuing this - // process. - - NEXT_CHAR(stream, i); - while (stream[i]) { - if (stream[i] IS CTRL_CODE) { - if (ESCAPE_CODE(stream, i) IS ESC_INDEX_END) { - auto end = escape_data(stream, i); - if (index->ID IS end->ID) { - NEXT_CHAR(stream, i); - break; - } - } - } - - NEXT_CHAR(stream, i); - } - - continue; // Needed to avoid the NEXT_CHAR at the end of the while - } - } - } - - NEXT_CHAR(stream, i); - } // while + auto &stream = Self->Stream; + auto name_hash = StrHash(Args->Name); + for (INDEX i=0; i < INDEX(stream.size()); i++) { + if (stream[i].code IS SCODE::INDEX_START) { + auto &index = Self->Stream.lookup(i); + if (name_hash != index.name_hash) continue; + if (index.visible) return ERR::Okay; // It's already visible! + + index.visible = true; + if (index.parent_visible) { // We are visible, but parents must also be visible to show content + // Show all objects and manage the ParentVisible status of any child indexes + + { + #ifndef RETAIN_LOG_LEVEL + pf::LogLevel level(2); + #endif + Self->UpdatingLayout = true; + layout_doc(Self); + } - DRAW_PAGE(Self); + for (++i; i < INDEX(stream.size()); i++) { + auto code = stream[i].code; + if (code IS SCODE::INDEX_END) { + if (index.id IS Self->Stream.lookup(i).id) break; } + else if (code IS SCODE::IMAGE) { + auto &img = Self->Stream.lookup(i); + if (!img.rect.empty()) acShow(*img.rect); - return ERR_Okay; + if (auto tab = find_tabfocus(Self, TT::VECTOR, img.rect->UID); tab >= 0) { + Self->Tabs[tab].active = true; + } + } + else if (code IS SCODE::LINK) { + if (auto tab = find_tabfocus(Self, TT::LINK, Self->Stream.lookup(i).uid); tab >= 0) { + Self->Tabs[tab].active = true; + } + } + else if (code IS SCODE::INDEX_START) { + auto &index = Self->Stream.lookup(i); + index.parent_visible = true; + + if (!index.visible) { + for (++i; i < INDEX(stream.size()); i++) { + if (stream[i].code IS SCODE::INDEX_END) { + if (index.id IS Self->Stream.lookup(i).id) break; + } + } + } + } } + + Self->Viewport->draw(); } - if (stream[i]) NEXT_CHAR(stream, i); + + return ERR::Okay; } - else NEXT_CHAR(stream, i); } - return ERR_Search; + return ERR::Search; } //******************************************************************************************************************** @@ -1649,42 +1360,28 @@ static ERROR DOCUMENT_ShowIndex(extDocument *Self, struct docShowIndex *Args) #include "document_def.c" static const FieldArray clFields[] = { - { "EventMask", FDF_LARGE|FDF_FLAGS|FDF_RW, NULL, NULL, &clDocumentEventMask }, { "Description", FDF_STRING|FDF_R }, - { "FontFace", FDF_STRING|FDF_RW, NULL, SET_FontFace }, - { "Title", FDF_STRING|FDF_RW, NULL, SET_Title }, - { "Author", FDF_STRING|FDF_RW, NULL, SET_Author }, - { "Copyright", FDF_STRING|FDF_RW, NULL, SET_Copyright }, - { "Keywords", FDF_STRING|FDF_RW, NULL, SET_Keywords }, + { "Title", FDF_STRING|FDF_R }, + { "Author", FDF_STRING|FDF_R }, + { "Copyright", FDF_STRING|FDF_R }, + { "Keywords", FDF_STRING|FDF_R }, + { "Viewport", FDF_OBJECT|FDF_RW, NULL, SET_Viewport, ID_VECTORVIEWPORT }, + { "Focus", FDF_OBJECT|FDF_RI, NULL, NULL, ID_VECTORVIEWPORT }, + { "View", FDF_OBJECT|FDF_R, NULL, NULL, ID_VECTORVIEWPORT }, + { "Page", FDF_OBJECT|FDF_R, NULL, NULL, ID_VECTORVIEWPORT }, { "TabFocus", FDF_OBJECTID|FDF_RW }, - { "Surface", FDF_OBJECTID|FDF_RW, NULL, SET_Surface, ID_SURFACE }, - { "Focus", FDF_OBJECTID|FDF_RI }, + { "EventMask", FDF_LONGFLAGS|FDF_FLAGS|FDF_RW, NULL, NULL, &clDocumentEventMask }, { "Flags", FDF_LONGFLAGS|FDF_RI, NULL, SET_Flags, &clDocumentFlags }, - { "LeftMargin", FDF_LONG|FDF_RI }, - { "TopMargin", FDF_LONG|FDF_RI }, - { "RightMargin", FDF_LONG|FDF_RI }, - { "BottomMargin", FDF_LONG|FDF_RI }, - { "FontSize", FDF_LONG|FDF_RW, NULL, SET_FontSize }, - { "PageHeight", FDF_LONG|FDF_R, NULL, NULL }, - { "BorderEdge", FDF_LONGFLAGS|FDF_RI, NULL, NULL, &clDocumentBorderEdge }, - { "LineHeight", FDF_LONG|FDF_R }, + { "PageHeight", FDF_LONG|FDF_R }, { "Error", FDF_LONG|FDF_R }, - { "FontColour", FDF_RGB|FDF_RW }, - { "Highlight", FDF_RGB|FDF_RW }, - { "Background", FDF_RGB|FDF_RW }, - { "CursorColour", FDF_RGB|FDF_RW }, - { "LinkColour", FDF_RGB|FDF_RW }, - { "VLinkColour", FDF_RGB|FDF_RW }, - { "SelectColour", FDF_RGB|FDF_RW }, - { "Border", FDF_RGB|FDF_RW }, // Virtual fields - { "DefaultScript", FDF_OBJECT|FDF_I, NULL, SET_DefaultScript }, - { "EventCallback", FDF_FUNCTIONPTR|FDF_RW, GET_EventCallback, SET_EventCallback }, - { "Path", FDF_STRING|FDF_RW, GET_Path, SET_Path }, - { "Origin", FDF_STRING|FDF_RW, GET_Path, SET_Origin }, - { "PageWidth", FDF_VARIABLE|FDF_LONG|FDF_PERCENTAGE|FDF_RW, GET_PageWidth, SET_PageWidth }, - { "Src", FDF_SYNONYM|FDF_STRING|FDF_RW, GET_Path, SET_Path }, - { "UpdateLayout", FDF_LONG|FDF_W, NULL, SET_UpdateLayout }, - { "WorkingPath", FDF_STRING|FDF_R, GET_WorkingPath, NULL }, + { "ClientScript", FDF_OBJECT|FDF_I, NULL, SET_ClientScript }, + { "EventCallback", FDF_FUNCTIONPTR|FDF_RW, GET_EventCallback, SET_EventCallback }, + { "Path", FDF_STRING|FDF_RW, GET_Path, SET_Path }, + { "Origin", FDF_STRING|FDF_RW, GET_Path, SET_Origin }, + { "PageWidth", FDF_VARIABLE|FDF_LONG|FDF_SCALED|FDF_RW, GET_PageWidth, SET_PageWidth }, + { "Pretext", FDF_STRING|FDF_W, NULL, SET_Pretext }, + { "Src", FDF_SYNONYM|FDF_STRING|FDF_RW, GET_Path, SET_Path }, + { "WorkingPath", FDF_STRING|FDF_R, GET_WorkingPath, NULL }, END_FIELD }; diff --git a/src/document/class/document_def.c b/src/document/class/document_def.c index 3ede76db0..5cca1f481 100644 --- a/src/document/class/document_def.c +++ b/src/document/class/document_def.c @@ -2,7 +2,12 @@ static const struct FieldDef clDocumentEventMask[] = { { "Path", 0x00000001 }, - { "LinkActivated", 0x00000002 }, + { "OnClick", 0x00000002 }, + { "OnMotion", 0x00000004 }, + { "OnCrossingIn", 0x00000008 }, + { "OnCrossingOut", 0x00000010 }, + { "OnCrossing", 0x00000018 }, + { "LinkActivated", 0x00000020 }, { NULL, 0 } }; @@ -11,27 +16,17 @@ static const struct FieldDef clDocumentFlags[] = { { "Overwrite", 0x00000002 }, { "NoSysKeys", 0x00000004 }, { "Disabled", 0x00000008 }, - { "NoScrollbars", 0x00000010 }, - { "NoLayoutMsg", 0x00000020 }, - { "Unrestricted", 0x00000040 }, - { NULL, 0 } -}; - -static const struct FieldDef clDocumentBorderEdge[] = { - { "Top", 0x00000001 }, - { "Left", 0x00000002 }, - { "Right", 0x00000004 }, - { "Bottom", 0x00000008 }, + { "NoLayoutMsg", 0x00000010 }, + { "Unrestricted", 0x00000020 }, { NULL, 0 } }; FDEF maFeedParser[] = { { "String", FD_STR }, { 0, 0 } }; FDEF maSelectLink[] = { { "Index", FD_LONG }, { "Name", FD_STR }, { 0, 0 } }; -FDEF maApplyFontStyle[] = { { "DocStyle:Style", FD_PTR|FD_STRUCT }, { "Font", FD_OBJECTPTR }, { 0, 0 } }; FDEF maFindIndex[] = { { "Name", FD_STR }, { "Start", FD_LONG|FD_RESULT }, { "End", FD_LONG|FD_RESULT }, { 0, 0 } }; FDEF maInsertXML[] = { { "XML", FD_STR }, { "Index", FD_LONG }, { 0, 0 } }; FDEF maRemoveContent[] = { { "Start", FD_LONG }, { "End", FD_LONG }, { 0, 0 } }; -FDEF maInsertText[] = { { "Text", FD_STR }, { "Index", FD_LONG }, { "Preformat", FD_LONG }, { 0, 0 } }; +FDEF maInsertText[] = { { "Text", FD_STR }, { "Index", FD_LONG }, { "Char", FD_LONG }, { "Preformat", FD_LONG }, { 0, 0 } }; FDEF maCallFunction[] = { { "Function", FD_STR }, { "ScriptArg:Args", FD_PTR|FD_STRUCT }, { "TotalArgs", FD_LONG }, { 0, 0 } }; FDEF maAddListener[] = { { "Trigger", FD_LONG }, { "Function", FD_FUNCTIONPTR }, { 0, 0 } }; FDEF maRemoveListener[] = { { "Trigger", FD_LONG }, { "Function", FD_FUNCTIONPTR }, { 0, 0 } }; @@ -43,7 +38,6 @@ FDEF maReadContent[] = { { "Format", FD_LONG }, { "Start", FD_LONG }, { "End", F static const struct MethodEntry clDocumentMethods[] = { { -1, (APTR)DOCUMENT_FeedParser, "FeedParser", maFeedParser, sizeof(struct docFeedParser) }, { -2, (APTR)DOCUMENT_SelectLink, "SelectLink", maSelectLink, sizeof(struct docSelectLink) }, - { -3, (APTR)DOCUMENT_ApplyFontStyle, "ApplyFontStyle", maApplyFontStyle, sizeof(struct docApplyFontStyle) }, { -4, (APTR)DOCUMENT_FindIndex, "FindIndex", maFindIndex, sizeof(struct docFindIndex) }, { -5, (APTR)DOCUMENT_InsertXML, "InsertXML", maInsertXML, sizeof(struct docInsertXML) }, { -6, (APTR)DOCUMENT_RemoveContent, "RemoveContent", maRemoveContent, sizeof(struct docRemoveContent) }, @@ -59,23 +53,22 @@ static const struct MethodEntry clDocumentMethods[] = { }; static const struct ActionArray clDocumentActions[] = { - { AC_Activate, (APTR)DOCUMENT_Activate }, - { AC_Clear, (APTR)DOCUMENT_Clear }, - { AC_Clipboard, (APTR)DOCUMENT_Clipboard }, - { AC_DataFeed, (APTR)DOCUMENT_DataFeed }, - { AC_Disable, (APTR)DOCUMENT_Disable }, - { AC_Draw, (APTR)DOCUMENT_Draw }, - { AC_Enable, (APTR)DOCUMENT_Enable }, - { AC_Focus, (APTR)DOCUMENT_Focus }, - { AC_Free, (APTR)DOCUMENT_Free }, - { AC_GetVar, (APTR)DOCUMENT_GetVar }, - { AC_Init, (APTR)DOCUMENT_Init }, - { AC_NewObject, (APTR)DOCUMENT_NewObject }, - { AC_NewOwner, (APTR)DOCUMENT_NewOwner }, - { AC_Refresh, (APTR)DOCUMENT_Refresh }, - { AC_SaveToObject, (APTR)DOCUMENT_SaveToObject }, - { AC_ScrollToPoint, (APTR)DOCUMENT_ScrollToPoint }, - { AC_SetVar, (APTR)DOCUMENT_SetVar }, - { 0, 0 } + { AC_Activate, DOCUMENT_Activate }, + { AC_Clear, DOCUMENT_Clear }, + { AC_Clipboard, DOCUMENT_Clipboard }, + { AC_DataFeed, DOCUMENT_DataFeed }, + { AC_Disable, DOCUMENT_Disable }, + { AC_Draw, DOCUMENT_Draw }, + { AC_Enable, DOCUMENT_Enable }, + { AC_Focus, DOCUMENT_Focus }, + { AC_Free, DOCUMENT_Free }, + { AC_GetVar, DOCUMENT_GetVar }, + { AC_Init, DOCUMENT_Init }, + { AC_NewObject, DOCUMENT_NewObject }, + { AC_Refresh, DOCUMENT_Refresh }, + { AC_SaveToObject, DOCUMENT_SaveToObject }, + { AC_ScrollToPoint, DOCUMENT_ScrollToPoint }, + { AC_SetVar, DOCUMENT_SetVar }, + { 0, NULL } }; diff --git a/src/document/class/fields.cpp b/src/document/class/fields.cpp index 05d2262bf..d15a42f02 100644 --- a/src/document/class/fields.cpp +++ b/src/document/class/fields.cpp @@ -7,84 +7,30 @@ Author: The author(s) of the document. If a document declares the names of its author(s) under a head tag, the author string will be readable from this field. This field is always NULL if a document does not declare an author string. -*********************************************************************************************************************/ - -static ERROR SET_Author(extDocument *Self, CSTRING Value) -{ - if (Self->Author) { FreeResource(Self->Author); Self->Author = NULL; } - if ((Value) and (*Value)) Self->Author = StrClone(Value); - return ERR_Okay; -} - -/********************************************************************************************************************* - --FIELD- -Background: Optional background colour for the document. - -Set the Background field to clear the document background to the colour specified. - --FIELD- -Border: Border colour around the document's surface. - -This field enables the drawing of a 1-pixel border around the document's surface. The edges that are drawn are -controlled by the #BorderEdge field. - --FIELD- -BorderEdge: Border edge flags. - -This field controls the border edge that is drawn around the document's surface. The colour of the border is defined -in the #Border field. - --FIELD- -BottomMargin: Defines the amount of whitespace to leave at the bottom of the document page. - -The BottomMargin value determines the amount of whitespace at the bottom of the page. The default margin can be -altered prior to initialisation of a document object, however the loaded content may declare its own margins and -overwrite this value during processing. - -This value can be set as a fixed pixel coordinate only. - -FIELD- Copyright: Copyright information for the document. If a document declares copyright information under a head tag, the copyright string will be readable from this field. This field is always NULL if a document does not declare a copyright string. -*********************************************************************************************************************/ - -static ERROR SET_Copyright(extDocument *Self, CSTRING Value) -{ - if (Self->Copyright) { FreeResource(Self->Copyright); Self->Copyright = NULL; } - if ((Value) and (*Value)) Self->Copyright = StrClone(Value); - return ERR_Okay; -} - -/**************************************************************************** - -FIELD- -CursorColour: The colour used for the document cursor. +ClientScript: Allows an external script object to be used by a document file. -The colour used for the document cursor may be changed by setting this field. This is relevant only when a document is -in edit mode. +Set ClientScript with a Script object to allow document content to 'breach the firewall' and access functionality +outside of its namespace. This feature is primarily intended for applications that need to interact with their own +embedded documents. --FIELD- -DefaultScript: Allows an external script object to be used by a document file. - -Setting the DefaultScript field with a reference to a Script object will allow a document file to have access to -functionality outside of its namespace. This feature is primarily intended for applications that need to embed -custom documents. - -If a loaded document defines its own custom script, it will have priority over the script referenced here. +If a document defines a default script in its content, it will have priority over the one referenced here. *********************************************************************************************************************/ -static ERROR SET_DefaultScript(extDocument *Self, OBJECTPTR Value) +static ERR SET_ClientScript(extDocument *Self, objScript *Value) { - Self->UserDefaultScript = Value; - return ERR_Okay; + Self->ClientScript = Value; + return ERR::Okay; } -/**************************************************************************** +/********************************************************************************************************************* -FIELD- Description: A description of the document, provided by its author. @@ -102,37 +48,36 @@ EventCallback: Provides callbacks for global state changes. Set this field with a function reference to receive event notifications. It must be set in conjunction with #EventMask so that notifications are limited to those of interest. -The callback function prototype is `ERROR Function(*Document, LARGE EventFlag)`. +The callback function prototype is `ERR Function(*Document, DEF EventFlag, KEYVALUE *EventData)`. The EventFlag value will indicate the event that occurred. Please see the #EventMask field for a list of supported events and additional details. -Error codes returned from the callback will normally be discarded, however in some cases ERR_Skip can be returned in +Error codes returned from the callback will normally be discarded, however in some cases ERR::Skip can be returned in order to prevent the event from being processed any further. *********************************************************************************************************************/ -static ERROR GET_EventCallback(extDocument *Self, FUNCTION **Value) +static ERR GET_EventCallback(extDocument *Self, FUNCTION **Value) { - if (Self->EventCallback.Type != CALL_NONE) { + if (Self->EventCallback.defined()) { *Value = &Self->EventCallback; - return ERR_Okay; + return ERR::Okay; } - else return ERR_FieldNotSet; + else return ERR::FieldNotSet; } -static ERROR SET_EventCallback(extDocument *Self, FUNCTION *Value) +static ERR SET_EventCallback(extDocument *Self, FUNCTION *Value) { if (Value) { - if (Self->EventCallback.Type IS CALL_SCRIPT) UnsubscribeAction(Self->EventCallback.Script.Script, AC_Free); + if (Self->EventCallback.isScript()) UnsubscribeAction(Self->EventCallback.Script.Script, AC_Free); Self->EventCallback = *Value; - if (Self->EventCallback.Type IS CALL_SCRIPT) { - auto callback = make_function_stdc(notify_free_event); - SubscribeAction(Self->EventCallback.Script.Script, AC_Free, &callback); + if (Self->EventCallback.isScript()) { + SubscribeAction(Self->EventCallback.Script.Script, AC_Free, FUNCTION(notify_free_event)); } } - else Self->EventCallback.Type = CALL_NONE; - return ERR_Okay; + else Self->EventCallback.clear(); + return ERR::Okay; } /********************************************************************************************************************* @@ -150,15 +95,15 @@ Flags: Optional flags that affect object behaviour. -****************************************************************************/ +*********************************************************************************************************************/ -static ERROR SET_Flags(extDocument *Self, LONG Value) +static ERR SET_Flags(extDocument *Self, DCF Value) { if (Self->initialised()) { - Self->Flags = Value & (~(DCF_NO_SCROLLBARS|DCF_UNRESTRICTED|DCF_DISABLED)); + Self->Flags = Value & (~(DCF::UNRESTRICTED|DCF::DISABLED)); } - else Self->Flags = Value & (~(DCF_DISABLED)); - return ERR_Okay; + else Self->Flags = Value & (~(DCF::DISABLED)); + return ERR::Okay; } /********************************************************************************************************************* @@ -170,67 +115,6 @@ By default, a document object will become active (i.e. capable of receiving keyb receives the focus. If you would like to change this so that a document becomes active when some other object receives the focus, refer to that object by writing its ID to this field. --FIELD- -FontColour: Default font colour. - -This field defines the default font colour if the source document does not specify one. - --FIELD- -FontFace: Defines the default font face. - -The default font face to use when processing a document is defined in this field. A document may override the default -font face by declaring a body tag containing a face attribute. If this occurs, the FontFace field will reflect the -default font face chosen by that document. - -*********************************************************************************************************************/ - -static ERROR SET_FontFace(extDocument *Self, CSTRING Value) -{ - if (Self->FontFace) FreeResource(Self->FontFace); - if (Value) { - Self->FontFace = StrClone(Value); - - // Check for facename:point usage - - auto str = Self->FontFace; - while (*str) { - if (*str IS ':') { - *str = 0; - Self->FontSize = StrToInt(str + 1); - break; - } - str++; - } - } - else Self->FontFace = NULL; - - return ERR_Okay; -} - -/********************************************************************************************************************* - --FIELD- -FontSize: The point-size of the default font. - -The point size of the default font is defined here. Valid values range between 6 and 128. - -*********************************************************************************************************************/ - -static ERROR SET_FontSize(extDocument *Self, LONG Value) -{ - if (Value < 6) Self->FontSize = 6; - else if (Value > 128) Self->FontSize = 128; - else Self->FontSize = Value; - return ERR_Okay; -} - -/********************************************************************************************************************* - --FIELD- -Highlight: Defines the colour used to highlight document. - -The Highlight field determines the colour that is used when highlighting selected document areas. - -FIELD- Keywords: Includes keywords declared by the source document. @@ -239,193 +123,114 @@ always NULL if a document does not declare any keywords. It is recommended that commas. It should not be assumed that the author of the document has adhered to the accepted standard for keyword separation. -*********************************************************************************************************************/ - -static ERROR SET_Keywords(extDocument *Self, STRING Value) -{ - if (Self->Keywords) FreeResource(Self->Keywords); - if ((Value) and (*Value)) Self->Keywords = StrClone(Value); - else Self->Keywords = NULL; - return ERR_Okay; -} - -/********************************************************************************************************************* - --FIELD- -LeftMargin: Defines the amount of whitespace to leave at the left of the page. - -The LeftMargin value determines the amount of whitespace at the left of the page. The default margin can be altered -prior to initialisation of a document object, however the loaded content may declare its own margins and overwrite this -value during processing. - -This value can be set as a fixed pixel coordinate only. - --FIELD- -LineHeight: Default line height (taken as an average) for all text on the page. - --FIELD- -LinkColour: Default font colour for hyperlinks. - -The default font colour for hyperlinks is defined here. If the alpha component is zero, this feature is disabled. - -FIELD- Path: Identifies the location of a document file to load. -To load a document file into a document object, set the Path field. If this field is set after initialisation, the -object will automatically clear its content and reload data from the location that you specify. It is also possible to -change the current page and parameters by setting the Path. +To load a document file into a document object, set the Path field. Valid string formats for setting the path are: -The string format for setting the path is `volume:folder/filename.rpl#Page?param1¶m2=value`. +`volume:folder/filename.rpl` -This example changes the current document by loading from a new file source: `documents:index.rpl`. +`#page_name?param1¶m2=value` -This example changes the current page if a document is already loaded (note: if the page does not exist in the -currently loaded document, a message is displayed to bring the error to the user's attention): `#introduction`. +`volume:folder/filename.rpl#page_name?param1¶m2=value` -This example changes the page and passes it new parameters: `#introduction?username=Paul`. +Setting this field post-initialisation will cause a complete reload unless the path begins with a hash to signal a +change to the current page and parameters. Note: if a requested page does not exist in the currently loaded document, +a dialog is displayed to bring the error to the user's attention). To leap to a bookmark in the page that has been specified with the <index> element, use the colon as a separator after the pagename, i.e. `#pagename:bookmark`. -Other means of opening a document include loading the data manually and feeding it through with the #DataFeed() action. - -The new document layout will be displayed when incoming messages are next processed by the running task. +Other means of opening a document include loading the data manually and passing it via the #DataFeed() action. -END- *********************************************************************************************************************/ -static ERROR GET_Path(extDocument *Self, STRING *Value) +static ERR GET_Path(extDocument *Self, CSTRING *Value) { - if (Self->Path) { - *Value = Self->Path; - return ERR_Okay; - } - else { - *Value = NULL; - return ERR_FieldNotSet; - } + *Value = Self->Path.c_str(); + return ERR::Okay; } -static ERROR SET_Path(extDocument *Self, CSTRING Value) +static ERR SET_Path(extDocument *Self, CSTRING Value) { pf::Log log; static BYTE recursion = 0; - LONG i, len; - if (recursion) return log.warning(ERR_Recursion); + if (recursion) return log.warning(ERR::Recursion); - if ((!Value) or (!*Value)) return ERR_NoData; + if ((!Value) or (!*Value)) return ERR::NoData; - Self->Error = ERR_Okay; + Self->Error = ERR::Okay; - STRING newpath = NULL; - UBYTE reload = TRUE; + std::string newpath; if ((Value[0] IS '#') or (Value[0] IS '?')) { - reload = FALSE; - - if (Self->Path) { - if (Value[0] IS '?') for (i=0; (Self->Path[i]) and (Self->Path[i] != '?'); i++); - else for (i=0; (Self->Path[i]) and (Self->Path[i] != '#'); i++); + if (!Self->Path.empty()) { + unsigned i; + if (Value[0] IS '?') for (i=0; (i < Self->Path.size()) and (Self->Path[i] != '?'); i++); + else for (i=0; (i < Self->Path.size()) and (Self->Path[i] != '#'); i++); - len = StrLength(Value); - - if (!AllocMemory(i + len + 1, MEM::STRING|MEM::NO_CLEAR, &newpath)) { - CopyMemory(Self->Path, newpath, i); - CopyMemory(Value, newpath+i, len+1); - } - else return ERR_AllocMemory; + newpath.assign(Self->Path, 0, i); + newpath.append(Value); } - else newpath = StrClone(Value); + else newpath.assign(Value); } - else if (Self->Path) { - // Work out if the location has actually been changed + else newpath = Value; - for (len=0; (Value[len]) and (Value[len] != '#') and (Value[len] != '?'); len++); - - for (i=0; (Self->Path[i]) and (Self->Path[i] != '#') and (Self->Path[i] != '?'); i++); - - if ((i IS len) and ((!i) or (!StrCompare(Value, Self->Path, len)))) { - // The location remains unchanged. A complete reload shouldn't be necessary. - - reload = FALSE; - //if ((Self->Path[i] IS '?') or (Value[len] IS '?')) { - // reload = TRUE; - //} - } - - newpath = StrClone(Value); - } - else newpath = StrClone(Value); - - log.branch("%s (vs %s) Reload: %d", newpath, Self->Path, reload); + log.branch("%s (vs %s)", newpath.c_str(), Self->Path.c_str()); // Signal that we are leaving the current page recursion++; - for (auto trigger=Self->Triggers[DRT_LEAVING_PAGE]; trigger; trigger=trigger->Next) { - if (trigger->Function.Type IS CALL_SCRIPT) { - OBJECTPTR script; - if ((script = trigger->Function.Script.Script)) { - ScriptArg args[] = { - { "OldURI", FD_STR, { .Address = Self->Path } }, - { "NewURI", FD_STR, { .Address = newpath } }, - }; - scCallback(script, trigger->Function.Script.ProcedureID, args, ARRAYSIZE(args), NULL); - } + for (auto &trigger : Self->Triggers[LONG(DRT::LEAVING_PAGE)]) { + if (trigger.isScript()) { + auto script = trigger.Script.Script; + ScriptArg args[] = { + { "OldURI", Self->Path }, + { "NewURI", newpath }, + }; + scCallback(script, trigger.Script.ProcedureID, args, std::ssize(args), NULL); } - else if (trigger->Function.Type IS CALL_STDC) { - auto routine = (void (*)(APTR, extDocument *, STRING, STRING))trigger->Function.StdC.Routine; - if (routine) { - pf::SwitchContext context(trigger->Function.StdC.Context); - routine(trigger->Function.StdC.Context, Self, Self->Path, newpath); - } + else if (trigger.isC()) { + auto routine = (void (*)(APTR, extDocument *, CSTRING, CSTRING, APTR))trigger.StdC.Routine; + pf::SwitchContext context(trigger.StdC.Context); + routine(trigger.StdC.Context, Self, Self->Path.c_str(), newpath.c_str(), trigger.StdC.Meta); } } recursion--; - if (Self->Path) { FreeResource(Self->Path); Self->Path = NULL; } - if (Self->PageName) { FreeResource(Self->PageName); Self->PageName = NULL; } - if (Self->Bookmark) { FreeResource(Self->Bookmark); Self->Bookmark = NULL; } + Self->Path.clear(); + Self->PageName.clear(); + Self->Bookmark.clear(); - if (newpath) { + if (!newpath.empty()) { Self->Path = newpath; recursion++; - unload_doc(Self, (reload IS FALSE) ? ULD_REFRESH : 0); if (Self->initialised()) { - if ((Self->XML) and (reload IS FALSE)) { - process_parameters(Self, Self->Path); - process_page(Self, Self->XML); - } - else { - load_doc(Self, Self->Path, FALSE, 0); - QueueAction(MT_DrwInvalidateRegion, Self->SurfaceID); - } + load_doc(Self, Self->Path, true); + Self->Viewport->draw(); } recursion--; // If an error occurred, remove the location & page strings to show that no document is loaded. - if (Self->Error) { - FreeResource(Self->Path); - Self->Path = NULL; - - if (Self->PageName) { FreeResource(Self->PageName); Self->PageName = NULL; } - if (Self->Bookmark) { FreeResource(Self->Bookmark); Self->Bookmark = NULL; } - if (Self->XML) { FreeResource(Self->XML); Self->XML = NULL; } - - QueueAction(MT_DrwInvalidateRegion, Self->SurfaceID); + if (Self->Error != ERR::Okay) { + Self->Path.clear(); + Self->PageName.clear(); + Self->Bookmark.clear(); + Self->Viewport->draw(); } } - else Self->Error = ERR_AllocMemory; + else Self->Error = ERR::AllocMemory; - report_event(Self, DEF_PATH, NULL, NULL); + report_event(Self, DEF::PATH, 0, NULL); return Self->Error; } -/**************************************************************************** +/********************************************************************************************************************* -FIELD- Origin: Similar to the Path field, but does not automatically load content if set. @@ -434,23 +239,13 @@ This field is identical to the #Path field, with the exception that it does not document object if it is set after initialisation. This may be useful if the location of a loaded document needs to be changed without causing a load operation. -****************************************************************************/ +*********************************************************************************************************************/ -static ERROR SET_Origin(extDocument *Self, STRING Value) +static ERR SET_Origin(extDocument *Self, CSTRING Value) { - if (Self->Path) { FreeResource(Self->Path); Self->Path = NULL; } - - if ((Value) and (*Value)) { - LONG i; - for (i=0; Value[i]; i++); - if (!AllocMemory(i+1, MEM::STRING|MEM::NO_CLEAR, &Self->Path)) { - for (i=0; Value[i]; i++) Self->Path[i] = Value[i]; - Self->Path[i] = 0; - } - else return ERR_AllocMemory; - } - - return ERR_Okay; + Self->Path.clear(); + if ((Value) and (*Value)) Self->Path.assign(Value); + return ERR::Okay; } /********************************************************************************************************************* @@ -469,7 +264,7 @@ margins. *********************************************************************************************************************/ -static ERROR GET_PageWidth(extDocument *Self, Variable *Value) +static ERR GET_PageWidth(extDocument *Self, Variable *Value) { DOUBLE value; @@ -478,80 +273,79 @@ static ERROR GET_PageWidth(extDocument *Self, Variable *Value) if (Self->initialised()) { value = Self->CalcWidth; - if (Value->Type & FD_PERCENTAGE) { - if (Self->SurfaceWidth <= 0) return ERR_GetField; - value = (DOUBLE)(value * Self->SurfaceWidth); + if (Value->Type & FD_SCALED) { + if (Self->VPWidth <= 0) return ERR::GetField; + value = (DOUBLE)(value * Self->VPWidth); } } else value = Self->PageWidth; if (Value->Type & FD_DOUBLE) Value->Double = value; else if (Value->Type & FD_LARGE) Value->Large = value; - else return ERR_FieldTypeMismatch; - return ERR_Okay; + else return ERR::FieldTypeMismatch; + return ERR::Okay; } -static ERROR SET_PageWidth(extDocument *Self, Variable *Value) +static ERR SET_PageWidth(extDocument *Self, Variable *Value) { pf::Log log; if (Value->Type & FD_DOUBLE) { if (Value->Double <= 0) { log.warning("A page width of %.2f is illegal.", Value->Double); - return ERR_OutOfRange; + return ERR::OutOfRange; } Self->PageWidth = Value->Double; } else if (Value->Type & FD_LARGE) { if (Value->Large <= 0) { log.warning("A page width of %" PF64 " is illegal.", Value->Large); - return ERR_OutOfRange; + return ERR::OutOfRange; } Self->PageWidth = Value->Large; } - else return ERR_FieldTypeMismatch; + else return ERR::FieldTypeMismatch; - if (Value->Type & FD_PERCENTAGE) Self->RelPageWidth = TRUE; - else Self->RelPageWidth = FALSE; + if (Value->Type & FD_SCALED) Self->RelPageWidth = true; + else Self->RelPageWidth = false; - return ERR_Okay; + return ERR::Okay; } /********************************************************************************************************************* -FIELD- -RightMargin: Defines the amount of white-space to leave at the right side of the document page. - -The RightMargin value determines the amount of white-space at the right of the page. The default margin can be altered -prior to initialisation of a document object, however the loaded content may declare its own margins and overwrite this -value during processing. +Pretext: Execute the XML defined here prior to loading new pages. -This value can be set as a fixed pixel coordinate only. +Use the Pretext field to execute document code prior to the loading of a new document. This feature is commonly used +to set configure a document in advance, such as setting default font values and background graphics. It is +functionally equivalent to embedding an `` statement at the top of a document, but with the benefit +of guaranteeing continued execution if the user navigates away from the first page. --FIELD- -SelectColour: Default font colour to use when hyperlinks are selected. - -This field defines the font colour for hyperlinks that are selected - for instance, when the user tabs to a link or -hovers over it. If the alpha component is zero, this field has no effect. - --FIELD- -Surface: Defines the surface area for document graphics. - -The Surface field refers to the object ID of the surface that will contain the document graphics. This field must be -set prior to initialisation to target the graphics correctly - if left unset then the document object will attempt to -determine the correct surface object based on object ownership. +A Pretext will always survive document unloading and resets. It can be removed only by setting this field with NULL. *********************************************************************************************************************/ -static ERROR SET_Surface(extDocument *Self, OBJECTID Value) +static ERR SET_Pretext(extDocument *Self, CSTRING Value) { - if (Self->initialised()) { - if (Self->SurfaceID IS Value) return ERR_Okay; - return ERR_NoSupport; + if (!Value) { + if (Self->PretextXML) { FreeResource(Self->PretextXML); Self->PretextXML = NULL; } + return ERR::Okay; + } + else if (Self->PretextXML) { + return Self->PretextXML->setStatement(Value); } - else Self->SurfaceID = Value; + else { + if ((Self->PretextXML = objXML::create::integral({ + fl::Flags(XMF::ALL_CONTENT|XMF::PARSE_HTML|XMF::STRIP_HEADERS|XMF::WELL_FORMED), + fl::Statement(Value), + fl::ReadOnly(true) + }))) { - return ERR_Okay; + return ERR::Okay; + } + else return ERR::CreateObject; + } } /********************************************************************************************************************* @@ -568,54 +362,26 @@ Title: The title of the document. If a document declares a title under a head tag, the title string will be readable from this field. This field is always NULL if a document does not declare a title. -*********************************************************************************************************************/ - -static ERROR SET_Title(extDocument *Self, STRING Value) -{ - if (Self->Title) { FreeResource(Self->Title); Self->Title = NULL; } - if ((Value) and (*Value)) Self->Title = StrClone(Value); - return ERR_Okay; -} - -/********************************************************************************************************************* - --FIELD- -TopMargin: Defines the amount of white-space to leave at the top of the document page. - -The TopMargin value determines the amount of white-space at the top of the page. The default margin can be altered -prior to initialisation of a document object, however the loaded content may declare its own margins and overwrite this -value during processing. - -This value can be set as a fixed pixel coordinate only. - -FIELD- -UpdateLayout: When TRUE, forces the layout to update on the next redraw. +Viewport: A client-specific viewport that will host the document graphics. -To force the document layout to be updated on the next redraw, set this field to TRUE. Redrawing can then be achieved -by calling the #Draw() action on the document. - -Forcing the document to recompute its layout is rarely necessary as this is automatically managed when inserting and -removing content. However, an action such as adjusting the size of graphical objects from a script would require this -field to be manually set. +The Viewport field must refer to a @VectorViewport that will host the document graphics. If undefined by the client, +the nearest viewport container will be determined based on object ownership. *********************************************************************************************************************/ -static ERROR SET_UpdateLayout(extDocument *Self, LONG Value) +static ERR SET_Viewport(extDocument *Self, objVectorViewport *Value) { - if (Value) Self->UpdateLayout = TRUE; - return ERR_Okay; -} - -/********************************************************************************************************************* + if (Value->CLASS_ID != ID_VECTORVIEWPORT) return ERR::InvalidObject; --FIELD- -VLinkColour: Default font colour for visited hyperlinks. - -The default font colour for visited hyperlinks is stored in this field. The source document can specify its own -colour for visited links if the author desires. --END- + if (Self->initialised()) { + if (Self->Viewport IS Value) return ERR::Okay; + return ERR::NoSupport; + } + else Self->Viewport = Value; -*********************************************************************************************************************/ + return ERR::Okay; +} /********************************************************************************************************************* @@ -634,25 +400,25 @@ You can manually change the working path by setting the #Origin field without af *********************************************************************************************************************/ -static ERROR GET_WorkingPath(extDocument *Self, CSTRING *Value) +static ERR GET_WorkingPath(extDocument *Self, CSTRING *Value) { pf::Log log; - if (!Self->Path) { + if (Self->Path.empty()) { log.warning("Document has no defined Path."); - return ERR_FieldNotSet; + return ERR::FieldNotSet; } - if (Self->WorkingPath) { FreeResource(Self->WorkingPath); Self->WorkingPath = NULL; } + Self->WorkingPath.clear(); // Determine if an absolute path has been indicated - BYTE path = FALSE; - if (Self->Path[0] IS '/') path = TRUE; + bool path = false; + if (Self->Path[0] IS '/') path = true; else { for (LONG j=0; (Self->Path[j]) and (Self->Path[j] != '/') and (Self->Path[j] != '\\'); j++) { if (Self->Path[j] IS ':') { - path = TRUE; + path = true; break; } } @@ -665,32 +431,23 @@ static ERROR GET_WorkingPath(extDocument *Self, CSTRING *Value) pf::SwitchContext context(Self); - STRING workingpath; + STRING working_path; if (path) { // Extract absolute path - auto save = Self->Path[j]; - Self->Path[j] = 0; - Self->WorkingPath = StrClone(Self->Path); - Self->Path[j] = save; + Self->WorkingPath.assign(Self->Path, 0, j); } - else if ((!CurrentTask()->get(FID_Path, &workingpath)) and (workingpath)) { - char buf[1024]; + else if ((CurrentTask()->get(FID_Path, &working_path) IS ERR::Okay) and (working_path)) { + std::string buf(working_path); // Using ResolvePath() can help to determine relative paths such as "../path/file" - if (j > 0) { - auto save = Self->Path[j]; - Self->Path[j] = 0; - snprintf(buf, sizeof(buf), "%s%s", workingpath, Self->Path); - Self->Path[j] = save; - } - else snprintf(buf, sizeof(buf), "%s", workingpath); + if (j > 0) buf += Self->Path.substr(0, j); - if (ResolvePath(buf, RSF::APPROXIMATE, &Self->WorkingPath) != ERR_Okay) { - Self->WorkingPath = StrClone(workingpath); + if (ResolvePath(buf.c_str(), RSF::APPROXIMATE, &working_path) IS ERR::Okay) { + Self->WorkingPath.assign(working_path); } } - else log.warning("No working path."); + else { *Value = NULL; return ERR::NoData; } - *Value = Self->WorkingPath; - return ERR_Okay; + *Value = Self->WorkingPath.c_str(); + return ERR::Okay; } diff --git a/src/document/debug.cpp b/src/document/debug.cpp new file mode 100644 index 000000000..a7d31dbfa --- /dev/null +++ b/src/document/debug.cpp @@ -0,0 +1,106 @@ + +//******************************************************************************************************************** + +static std::string printable(RSTREAM &, stream_char, ULONG = 60) __attribute__ ((unused)); + +static std::string printable(RSTREAM &Stream, stream_char Start, ULONG Length) +{ + std::string result; + result.reserve(Length); + stream_char i = Start; + while ((i.index < INDEX(Stream.size())) and (result.size() < Length)) { + if (Stream[i.index].code IS SCODE::TEXT) { + auto &text = Stream.lookup(i); + result += text.text.substr(i.offset, result.capacity() - result.size()); + } + else result += '%'; + i.next_code(); + } + return result; +} + +//******************************************************************************************************************** + +#ifdef DBG_STREAM + +static void print_stream(RSTREAM &Stream) +{ + if (Stream.data.empty()) return; + + pf::Log log; + std::ostringstream out; + out << "\nSTREAM: " << Stream.size() << " codes\n"; + out << "-------------------------------------------------------------------------------\n"; + + bool printpos = false; + for (INDEX i=0; i < INDEX(Stream.size()); i++) { + auto code = Stream[i].code; + if (code IS SCODE::FONT) { + auto &style = Stream.lookup(i); + out << "[Font"; + out << ":#" << style.font_index; + if ((style.options & FSO::ALIGN_RIGHT) != FSO::NIL) out << ":A/R"; + if ((style.options & FSO::ALIGN_CENTER) != FSO::NIL) out << ":A/C"; + if ((style.options & FSO::BOLD) != FSO::NIL) out << ":Bold"; + out << ":" << style.fill << "]"; + } + else if (code IS SCODE::PARAGRAPH_START) { + auto ¶ = Stream.lookup(i); + if (para.list_item) out << "[PS:LI]"; + else out << "[PS]"; + } + else if (code IS SCODE::PARAGRAPH_END) { + out << "[PE]\n"; + } + else out << "[" << strCodes[LONG(code)] << "]"; + + printpos = true; + } + + log.msg("%s", out.str().c_str()); +} + +#endif + +static void print_segments(extDocument *Self) +{ +#ifdef DBG_SEGMENTS + pf::Log log; + std::ostringstream out; + + out << "\nSEGMENTS\n--------\n"; + + for (unsigned si=0; si < Self->Segments.size(); si++) { + auto &seg = Self->Segments[si]; + auto i = seg.start; + + out << std::setw(3) << si << ": Span: " << seg.start.index << ':' << seg.start.offset << " - " << seg.stop.index << ':' << seg.stop.offset << ": "; + out << "(" << seg.area.X << "x" << seg.area.Y << ", " << seg.area.Width << "x" << seg.area.Height << ") "; + if (seg.edit) out << "{ "; + out << "\""; + while (i < seg.stop) { + auto code = seg.stream[0][i.index].code; + if (code IS SCODE::FONT) { + auto &style = seg.stream->lookup(i.index); + out << "[E:Font:#" << style.font_index << "]"; + } + else if (code IS SCODE::PARAGRAPH_START) { + auto ¶ = seg.stream->lookup(i.index); + if (para.list_item) out << "[E:LI]"; + else out << "[E:PS]"; + } + else if (code IS SCODE::PARAGRAPH_END) { + out << "[E:PE]\n"; + } + else out << "[E:" << strCodes[LONG(code)] << "]"; + i.next_code(); + } + + out << "\""; + if (seg.edit) out << " }"; + out << "\n"; + } + + log.msg("%s", out.str().c_str()); +#endif +} diff --git a/src/document/defs/document.fdl b/src/document/defs/document.fdl new file mode 100644 index 000000000..b72837e16 --- /dev/null +++ b/src/document/defs/document.fdl @@ -0,0 +1,103 @@ +--$FLUID:Include + +module({ name="Document", copyright="Paul Manias © 2005-2024", version=1.0 }, function() + restrict(function() + loadFile(glPath .. 'common-graphics.fdl') + end) + + c_include("", "", "", "") + + loadFile(glPath .. 'common.fdl') + + const("RIPL", { comment="Official version number (date format). Any changes to the handling of document content require that this number be updated." }, { + VERSION = "\"20240126\"" + }) + + enum("TT", { type="char", start=1 }, "VECTOR", "LINK", "EDIT") + + flags("DEF", { comment="Event flags for selectively receiving events from the Document object." }, + "PATH: The source file path has changed. Useful for detecting when the user has left the page.", + "ON_CLICK: The user has interacted with an element that has an on-click definition.", + "ON_MOTION: The user has triggered a motion event in an element that supports motion monitoring.", + "ON_CROSSING_IN: The mouse pointer has crossed into an element.", + "ON_CROSSING_OUT: The mouse pointer has crossed out of an element.", + "LINK_ACTIVATED: The user has interacted with a hyperlink. This event can be cancelled by returning ERR::Skip.", + { ON_CROSSING = "ON_CROSSING_IN|ON_CROSSING_OUT" } + ) + + enum("DRT", { type="int", start=0, comment="Internal trigger codes" }, + "BEFORE_LAYOUT", + "AFTER_LAYOUT", + "USER_CLICK", + "USER_CLICK_RELEASE", + "USER_MOVEMENT", + "REFRESH", + "GOT_FOCUS", + "LOST_FOCUS", + "LEAVING_PAGE", + "PAGE_PROCESSED", + "MAX") + + flags("DCF", { comment="Document flags" }, + "EDIT: Allow direct keyboard input and document editing.", + "OVERWRITE: This flag forces overwrite mode when the user enters information through the keyboard. If the flag is not set, then insert mode is used.", + "NO_SYS_KEYS: System-keys provide standard key support for Ctrl-C, Ctrl-X etc. Set this flag to turn them off.", + "DISABLED: This read-only flag is set if the UI has been disabled through the Disable action.", + "NO_LAYOUT_MSG: Turn off debug output produced during document layout and processing - useful on refresh for example.", + "UNRESTRICTED: Turn off all security measures - may only be set prior to initialisation.") + + flags("FSO", { comment="These are document style flags, as used in the DocStyle structure" }, + "BOLD: Enable bold styling.", + "ITALIC: Enable italic styling.", + "UNDERLINE: Draw a line under the text.", + "PREFORMAT: All white-space is taken into account.", + "ALIGN_RIGHT: Align to the right.", + "ALIGN_CENTER: Align to the left.", + "NO_WRAP: Do not wrap the text.", + { STYLES = "BOLD|UNDERLINE|ITALIC" }) + + methods("Document", "doc", { + { id=1, name="FeedParser" }, + { id=2, name="SelectLink" }, + { id=4, name="FindIndex" }, + { id=5, name="InsertXML" }, + { id=6, name="RemoveContent" }, + { id=7, name="InsertText" }, + { id=8, name="CallFunction" }, + { id=9, name="AddListener" }, + { id=10, name="RemoveListener" }, + { id=11, name="ShowIndex" }, + { id=12, name="HideIndex" }, + { id=13, name="Edit" }, + { id=14, name="ReadContent" } + }) + + class("Document", { src={ "../class/document_class.cpp", "../class/fields.cpp" }, output="../class/document_def.c" }, [[ + str Description # A description assigned by the author of the document + str Title # The title of the document + str Author # The author of the document + str Copyright # Copyright information for the document + str Keywords # Keywords for the document + obj(VectorViewport) Viewport # The viewport that will host the document + obj(VectorViewport) Focus # Monitor this viewport for focus events + obj(VectorViewport) View # An internally created viewport that hosts the Page + obj(VectorViewport) Page # The Page contains the document content and is hosted by the View + oid TabFocus # If the tab key is pressed, focus can be changed to this object + int(DEF) EventMask # Event mask for selectively receiving events from the Document object. + int(DCF) Flags # Optional flags + int PageHeight # Height of the document page + error Error # Most recent error code produced by the parser + ]]) + + c_insert([[ +namespace fl { + using namespace pf; + +constexpr FieldValue EventCallback(const FUNCTION &Value) { return FieldValue(FID_EventCallback, &Value); } +constexpr FieldValue EventCallback(APTR Value) { return FieldValue(FID_EventCallback, Value); } +constexpr FieldValue EventMask(DEF Value) { return FieldValue(FID_EventMask, LONG(Value)); } +constexpr FieldValue Flags(DCF Value) { return FieldValue(FID_Flags, LONG(Value)); } + +} +]]) +end) diff --git a/src/document/defs/document.h b/src/document/defs/document.h new file mode 100644 index 000000000..d6efcb02c --- /dev/null +++ b/src/document/defs/document.h @@ -0,0 +1,1150 @@ + +class extDocument; +struct bc_combobox; + +typedef int INDEX; +using SEGINDEX = int; + +enum class TE : char { + NIL = 0, + WRAP_TABLE, + REPASS_ROW_HEIGHT, + EXTEND_PAGE +}; + +enum class CB : UBYTE { // Cell border options + NIL = 0x00, + TOP = 0x01, + BOTTOM = 0x02, + LEFT = 0x04, + RIGHT = 0x08, + ALL = 0X0f +}; + +DEFINE_ENUM_FLAG_OPERATORS(CB) + +enum class CELL : UBYTE { + NIL = 0, + ABORT, + WRAP_TABLE_CELL, + REPASS_ROW_HEIGHT +}; + +enum class RTD : UBYTE { + NIL=0, + OBJECT_TEMP, // The object can be removed after parsing has finished + OBJECT_UNLOAD, // Default choice for object termination, terminates immediately + OBJECT_UNLOAD_DELAY, // Use SendMessage() to terminate the object + PERSISTENT_SCRIPT, // The script can survive refreshes + PERSISTENT_OBJECT // The object can survive refreshes +}; + +DEFINE_ENUM_FLAG_OPERATORS(RTD) + +enum class STYLE : UBYTE { + NIL = 0x00, + INHERIT_STYLE = 0x01, // Inherit whatever font style applies at the insertion point. + RESET_STYLE = 0x02 // Current font style will be reset rather than defaulting to the most recent style at the insertion point. +}; + +DEFINE_ENUM_FLAG_OPERATORS(STYLE) + +enum class PXF : WORD { + NIL = 0, + ARGS = 0x0001, + TRANSLATE = 0x0002 +}; + +DEFINE_ENUM_FLAG_OPERATORS(PXF) + +enum class LINK : UBYTE { + NIL = 0, + HREF, + FUNCTION +}; + +DEFINE_ENUM_FLAG_OPERATORS(LINK) + +enum { + COND_NOT_EQUAL=1, + COND_EQUAL, + COND_LESS_THAN, + COND_LESS_EQUAL, + COND_GREATER_THAN, + COND_GREATER_EQUAL +}; + +enum class SCODE : char { + NIL = 0, + TEXT, + FONT, + FONT_END, + LINK, + TABDEF, + PARAGRAPH_END, + PARAGRAPH_START, + LINK_END, + ADVANCE, + LIST_START, + LIST_END, + TABLE_START, + TABLE_END, + ROW, + CELL, + ROW_END, + INDEX_START, + INDEX_END, + XML, + IMAGE, + USE, + BUTTON, + CHECKBOX, + COMBOBOX, + INPUT, + // End of list. Functions affected by changing these codes are: + // BC_NAME() + // new_segment() + END +}; + +DEFINE_ENUM_FLAG_OPERATORS(SCODE) + +enum class ULD : UBYTE { + NIL = 0, + TERMINATE = 0x01, + KEEP_PARAMETERS = 0x02, + REFRESH = 0x04, + REDRAW = 0x08 +}; + +DEFINE_ENUM_FLAG_OPERATORS(ULD) + +enum class NL : char { + NONE = 0, + PARAGRAPH +}; + +DEFINE_ENUM_FLAG_OPERATORS(NL) + +enum class WRAP : char { + DO_NOTHING = 0, + EXTEND_PAGE, + WRAPPED +}; + +DEFINE_ENUM_FLAG_OPERATORS(WRAP) + +enum { + STATE_OUTSIDE=0, + STATE_ENTERED, + STATE_INSIDE +}; + +enum class IPF : ULONG { + NIL = 0, + NO_CONTENT = 0x0001, // XML content data will be ignored + FILTER_TABLE = 0x0008, // The tag is restricted to use within
    sections. + FILTER_ROW = 0X0010, // The tag is restricted to use within sections. + FILTER_ALL = (FILTER_TABLE|FILTER_ROW) +}; + +DEFINE_ENUM_FLAG_OPERATORS(IPF) + +enum class TRF : ULONG { + NIL = 0, + BREAK = 0x00000001, + CONTINUE = 0x00000002 +}; + +DEFINE_ENUM_FLAG_OPERATORS(TRF) + +class RSTREAM; + +#include "dunit.h" + +//******************************************************************************************************************** +// UI hooks for the client + +struct ui_hooks { + std::string on_click; // Function to call after a button event in the UI + std::string on_motion; // Function to call after a motion event in the UI + std::string on_crossing; // Function to call after a crossing event in the UI (enter/leave) + JTYPE events = JTYPE::NIL; // Input events that the client is interested in. +}; + +//******************************************************************************************************************** + +struct padding { + DOUBLE left = 0, top = 0, right = 0, bottom = 0; + bool left_scl = false, right_scl = false, top_scl = false, bottom_scl = false; + bool configured = false; + + padding() = default; + + padding(DOUBLE pLeft, DOUBLE pTop, DOUBLE pRight, DOUBLE pBottom) : + left(pLeft), top(pTop), right(pRight), bottom(pBottom), configured(true) { } + + void parse(const std::string &Value); + + void scale_all() { left_scl = right_scl = top_scl = bottom_scl = true; } +}; + +//******************************************************************************************************************** + +struct scroll_mgr { + struct scroll_slider { + DOUBLE offset = 0; + DOUBLE length = 20; + }; + + struct scroll_bar { + scroll_mgr *m_mgr = NULL; + objVectorViewport *m_bar_vp = NULL; // Main viewport for managing the scrollbar + objVectorViewport *m_slider_host = NULL; + objVectorViewport *m_slider_vp = NULL; + objVectorRectangle *m_slider_rect = NULL; + scroll_slider m_slider_pos; + char m_direction = 0; // 'V' or 'H' + DOUBLE m_breadth = 10; + + scroll_slider calc_slider(DOUBLE, DOUBLE, DOUBLE, DOUBLE); + void init(scroll_mgr *, char, objVectorViewport *); + void clear(); + }; + + extDocument *m_doc = NULL; + objVectorViewport *m_page = NULL; // Monitored page + objVectorViewport *m_view = NULL; // Monitored owner of the page + DOUBLE m_min_width = 0; // For dynamic width mode, this is the minimum required width + bool m_fixed_mode = false; + bool m_auto_adjust_view_size = true; // Automatically adjust the view to accomodate the visibility of the scrollbars + + scroll_bar m_vbar; + scroll_bar m_hbar; + + scroll_mgr() {} + + void init(extDocument *, objVectorViewport *, objVectorViewport *); + void scroll_page(DOUBLE, DOUBLE); + void recalc_sliders_from_view(); + void fix_page_size(DOUBLE, DOUBLE); + void dynamic_page_size(DOUBLE, DOUBLE, DOUBLE); +}; + +//******************************************************************************************************************** +// Tab is used to represent interactive entities within the document that can be tabbed to. + +struct tab { + // The ref is a UID for the Type, so you can use it to find the tab in the document stream + std::variant ref; // For TT::VECTOR: VectorID; TT::LINK: LinkID + TT type; + bool active; // true if the tabbable entity is active/visible + + tab(TT pType, BYTECODE pReference, bool pActive) : ref(pReference), type(pType), active(pActive) { } +}; + +//******************************************************************************************************************** + +struct edit_cell { + CELL_ID cell_id; + DOUBLE x, y, width, height; +}; + +//******************************************************************************************************************** + +struct link_activated { + std::map Values; // All key-values associated with the link. +}; + +//******************************************************************************************************************** +// Every instruction in the document stream is represented by a stream_code entity. The code refers to what the thing +// is, while the UID hash refers to further information in the Codes table. + +struct stream_code { + SCODE code; // Type + BYTECODE uid; // Lookup for the Codes table + + stream_code() : code(SCODE::NIL), uid(0) { } + stream_code(SCODE pCode, BYTECODE pID) : code(pCode), uid(pID) { } +}; + +//******************************************************************************************************************** + +class entity { +public: + BYTECODE uid; // Unique identifier for lookup + SCODE code = SCODE::NIL; // Byte code + + entity() { uid = glByteCodeID++; } + entity(SCODE pCode) : code(pCode) { uid = glByteCodeID++; } +}; + +//******************************************************************************************************************** + +class docresource { +public: + OBJECTID object_id; + CLASSID class_id; + RTD type; + bool terminate = false; // If true, can be freed immediately and not on a delay + + docresource(OBJECTID pID, RTD pType, CLASSID pClassID = 0) : + object_id(pID), class_id(pClassID), type(pType) { } + + ~docresource() { + if ((type IS RTD::PERSISTENT_SCRIPT) or (type IS RTD::PERSISTENT_OBJECT)) { + if (terminate) FreeResource(object_id); + else SendMessage(MSGID_FREE, MSF::NIL, &object_id, sizeof(OBJECTID)); + } + else if (type IS RTD::OBJECT_UNLOAD_DELAY) { + if (terminate) FreeResource(object_id); + else SendMessage(MSGID_FREE, MSF::NIL, &object_id, sizeof(OBJECTID)); + } + else if (type != RTD::NIL) FreeResource(object_id); + } + + docresource(docresource &&other) noexcept { // Move constructor + object_id = other.object_id; + class_id = other.class_id; + type = other.type; + terminate = other.terminate; + other.type = RTD::NIL; + } + + docresource(const docresource &other) { // Copy constructor + object_id = other.object_id; + class_id = other.class_id; + type = other.type; + terminate = other.terminate; + } + + docresource& operator=(docresource &&other) noexcept { // Move assignment + if (this == &other) return *this; + object_id = other.object_id; + class_id = other.class_id; + type = other.type; + terminate = other.terminate; + other.type = RTD::NIL; + return *this; + } + + docresource& operator=(const docresource& other) { // Copy assignment + if (this == &other) return *this; + object_id = other.object_id; + class_id = other.class_id; + type = other.type; + terminate = other.terminate; + return *this; + } +}; + +//******************************************************************************************************************** + +struct case_insensitive_map { + bool operator() (const std::string &lhs, const std::string &rhs) const { + return ::strcasecmp(lhs.c_str(), rhs.c_str()) < 0; + } +}; + +//******************************************************************************************************************** +// Basic font caching on an index basis. + +struct font_entry { + APTR handle; + std::string face; + std::string style; + FontMetrics metrics; + DOUBLE font_size; // 72 DPI pixel size + ALIGN align; + + font_entry(APTR pHandle, const std::string_view pFace, const std::string_view pStyle, DOUBLE pSize) : + handle(pHandle), face(pFace), style(pStyle), font_size(pSize), align(ALIGN::NIL) { + vecGetFontMetrics(pHandle, &metrics); + } + + ~font_entry() { } + + font_entry(font_entry &&other) noexcept { // Move constructor + handle = other.handle; + metrics = other.metrics; + font_size = other.font_size; + face = other.face; + style = other.style; + align = other.align; + other.handle = NULL; + } + + font_entry(const font_entry &other) { // Copy constructor + handle = other.handle; + font_size = other.font_size; + metrics = other.metrics; + face = other.face; + style = other.style; + align = other.align; + } + + font_entry& operator=(font_entry &&other) noexcept { // Move assignment + if (this == &other) return *this; + handle = other.handle; + font_size = other.font_size; + metrics = other.metrics; + face = other.face; + style = other.style; + align = other.align; + other.handle = NULL; + return *this; + } + + font_entry& operator=(const font_entry& other) { // Copy assignment + if (this == &other) return *this; + handle = other.handle; + font_size = other.font_size; + metrics = other.metrics; + face = other.face; + style = other.style; + align = other.align; + return *this; + } +}; + +//******************************************************************************************************************** +// bc_font has a dual purpose - it can maintain current font style information during parsing as well as being embedded +// in the document stream. + +struct bc_font : public entity { + WORD font_index; // Font lookup (will reflect the true font face, point size, style) + FSO options; // Style options, like underline and italics + ALIGN valign; // Vertical alignment of text within the available line height + std::string fill; // Font fill instruction + std::string face; // The font face as requested by the client. Might not match the font we actually use. + DOUBLE font_size; // The 72 DPI pixel size as requested by the client. Might not match the font we actually use. + + bc_font(): font_index(-1), options(FSO::NIL), valign(ALIGN::BOTTOM), fill("rgb(0,0,0)"), font_size(0) { code = SCODE::FONT; } + + font_entry * get_font(); + + bc_font(const bc_font &Other) { + // Copy another style and reset the index to -1 so that changes can refreshed + *this = Other; + font_index = -1; + } +}; + +struct bc_font_end : public entity { + bc_font_end() : entity(SCODE::FONT_END) { } +}; + +//******************************************************************************************************************** +// stream_char provides indexing to specific characters in the stream. It is designed to handle positional changes so +// that text string boundaries can be crossed without incident. +// +// The index and offset are set to -1 if the stream_char is invalidated. + +struct stream_char { + INDEX index; // Byte code position within the stream + size_t offset; // Specific character offset within the bc_text.text string + + stream_char() : index(-1), offset(-1) { } + stream_char(INDEX pIndex, ULONG pOffset) : index(pIndex), offset(pOffset) { } + stream_char(INDEX pIndex) : index(pIndex), offset(0) { } + + bool operator==(const stream_char &Other) const { + return (this->index == Other.index) and (this->offset == Other.offset); + } + + bool operator<(const stream_char &Other) const { + if (this->index < Other.index) return true; + else if ((this->index IS Other.index) and (this->offset < Other.offset)) return true; + else return false; + } + + bool operator>(const stream_char &Other) const { + if (this->index > Other.index) return true; + else if ((this->index IS Other.index) and (this->offset > Other.offset)) return true; + else return false; + } + + bool operator<=(const stream_char &Other) const { + if (this->index < Other.index) return true; + else if ((this->index IS Other.index) and (this->offset <= Other.offset)) return true; + else return false; + } + + bool operator>=(const stream_char &Other) const { + if (this->index > Other.index) return true; + else if ((this->index IS Other.index) and (this->offset >= Other.offset)) return true; + else return false; + } + + void operator+=(const LONG Value) { + offset += Value; + } + + inline void reset() { index = -1; offset = -1; } + inline bool valid() { return index != -1; } + + inline void set(INDEX pIndex, ULONG pOffset = 0) { + index = pIndex; + offset = pOffset; + } + + inline INDEX prev_code() { + index--; + if (index < 0) { index = -1; offset = -1; } + else offset = 0; + return index; + } + + inline INDEX next_code() { + offset = 0; + index++; + return index; + } + + // NB: None of these support unicode. + + UBYTE get_char(RSTREAM &); + UBYTE get_char(RSTREAM &, LONG Seek); + UBYTE get_prev_char(RSTREAM &); + UBYTE get_prev_char_or_inline(RSTREAM &); + void erase_char(RSTREAM &); // Erase a character OR an escape code. + void next_char(RSTREAM &); + void prev_char(RSTREAM &); +}; + +//******************************************************************************************************************** +// Refer to layout::new_segment(). A segment represents graphical content, which can be in the form of text, +// graphics or both. A segment can consist of one line only - so if the layout process encounters a boundary causing +// wordwrap then a new segment must be created. + +struct doc_segment { + stream_char start; // Starting index (including character if text) + stream_char stop; // Stop at this index/character + stream_char trim_stop; // The stopping point when whitespace is removed + FloatRect area; // Dimensions of the segment. + DOUBLE descent; // The largest descent value after taking into account all fonts used on the line. + DOUBLE align_width; // Full width of this segment if it were non-breaking + RSTREAM *stream; // The stream that this segment refers to + bool edit; // true if this segment represents content that can be edited + bool allow_merge; // true if this segment can be merged with siblings that have allow_merge set to true + + inline DOUBLE x(DOUBLE Advance, FSO StyleOptions) { + if ((StyleOptions & FSO::ALIGN_CENTER) != FSO::NIL) return Advance + ((align_width - area.Width) * 0.5); + else if ((StyleOptions & FSO::ALIGN_RIGHT) != FSO::NIL) return Advance + (align_width - area.Width); + else return Advance; + } + + inline DOUBLE y(ALIGN VAlign, font_entry *Font) { + if ((VAlign & ALIGN::TOP) != ALIGN::NIL) return area.Y + Font->metrics.Ascent; + else if ((VAlign & ALIGN::VERTICAL) != ALIGN::NIL) { + const DOUBLE avail_space = area.Height - descent; + return area.Y + avail_space - ((avail_space - Font->metrics.Height) * 0.5); + } + else return area.Y + area.Height - descent; + } +}; + +struct doc_clip { + DOUBLE left = 0, top = 0, right = 0, bottom = 0; + INDEX index = 0; // The stream index of the object/table/item that is creating the clip. + bool transparent = false; // If true, wrapping will not be performed around the clip region. + std::string name; + + doc_clip() = default; + + doc_clip(DOUBLE pLeft, DOUBLE pTop, DOUBLE pRight, DOUBLE pBottom, LONG pIndex, bool pTransparent, const std::string &pName) : + left(pLeft), top(pTop), right(pRight), bottom(pBottom), index(pIndex), transparent(pTransparent), name(pName) { + + if ((right - left > 20000) or (bottom - top > 20000)) { + pf::Log log; + log.warning("%s set invalid clip dimensions: %.0f,%.0f,%.0f,%.0f", name.c_str(), left, top, right, bottom); + right = left; + bottom = top; + } + } +}; + +struct doc_edit { + LONG max_chars; + std::string name; + std::string on_enter, on_exit, on_change; + std::vector> args; + bool line_breaks; + + doc_edit() : max_chars(-1), args(0), line_breaks(false) { } +}; + +struct bc_link; +struct bc_cell; + +struct mouse_over { + std::string function; // name of function to call. + DOUBLE top, left, bottom, right; + LONG element_id; +}; + +struct tablecol { + DOUBLE preset_width = 0; + DOUBLE min_width = 0; // For assisting layout + DOUBLE width = 0; + bool preset_width_rel = false; +}; + +//******************************************************************************************************************** + +struct bc_advance : public entity { + DUNIT x, y; + + bc_advance() : x(0.0), y(0.0) { code = SCODE::ADVANCE; } +}; + +struct bc_index : public entity { + ULONG name_hash = 0; // The name of the index is held here as a hash + LONG id = 0; // UID for matching to the correct bc_index_end + DOUBLE y = 0; // The cursor's vertical position of when the index was encountered during layout + bool visible = false; // true if the content inside the index is visible (this is the default) + bool parent_visible = false; // true if the nearest parent index(es) will allow index content to be visible. true is the default. This allows Hide/ShowIndex() to manage themselves correctly + + bc_index(ULONG pName, LONG pID, LONG pY, bool pVisible, bool pParentVisible) : + name_hash(pName), id(pID), y(pY), visible(pVisible), parent_visible(pParentVisible) { + code = SCODE::INDEX_START; + } +}; + +struct bc_index_end : public entity { + LONG id; // UID matching to the correct bc_index + bc_index_end(LONG pID) : id(pID) { code = SCODE::INDEX_END; } +}; + +struct bc_link : public entity { + GuardedObject path; + LINK type; // Link type (either a function or hyperlink) + ui_hooks hooks; // UI hooks defined by the client + std::string ref; // Function name or a path, depending on the Type + std::string hint; // Hint/title to display when hovering + std::vector> args; + std::string fill; // Fill instruction from the client + bc_font font; // Font style from the parser + + bc_link() : type(LINK::NIL) + { code = SCODE::LINK; } +}; + +struct bc_link_end : public entity { + bc_link_end() { code = SCODE::LINK_END; } +}; + +struct bc_list : public entity { + enum { + ORDERED=0, + BULLET, + CUSTOM + }; + + std::string fill; // Fill to use for bullet points (valid for BULLET only). + std::vector buffer; // Temp buffer, used for ordered lists + LONG start = 1; // Starting value for ordered lists (default: 1) + DUNIT item_indent = DUNIT(1.0, DU::LINE_HEIGHT); // Minimum indentation for text printed for each item + DUNIT block_indent = DUNIT(1.0, DU::LINE_HEIGHT); // Indentation for each set of items + LONG item_num = 0; + LONG order_insert = 0; + DUNIT v_spacing = DUNIT(0.5, DU::LINE_HEIGHT); // Spacing between list items, equivalent to paragraph leading, expressed as a ratio + UBYTE type = BULLET; + bool repass = false; + + bc_list() { code = SCODE::LIST_START; } +}; + +struct bc_list_end : public entity { + bc_list_end() { code = SCODE::LIST_END; } +}; + +struct bc_table : public entity { + GuardedObject path; + GuardedObject viewport; + std::vector seq; + std::vector columns; // Table column management + std::string fill, stroke; // SVG stroke and fill instructions + padding cell_padding; // Spacing inside each cell (margins) + DUNIT cell_v_spacing, cell_h_spacing; // Spacing between each cell + DOUBLE row_width = 0; // Assists in the computation of row width + DOUBLE x = 0, y = 0, width = 0, height = 0; // Run-time dimensions calculated during layout + DUNIT min_width, min_height; // Client-defined minimum table width/height + DOUBLE cursor_x = 0, cursor_y = 0; // Cursor coordinates + DUNIT stroke_width; // Stroke width + size_t total_clips = 0; // Temporary record of Document->Clips.size() + LONG rows = 0; // Total number of rows in table + LONG row_index = 0; // Current row being processed, generally for debugging + UBYTE compute_columns = 0; + ALIGN align = ALIGN::NIL; // Horizontal alignment. If defined, the table will be floating. + bool cells_expanded = false; // false if the table cells have not been expanded to match the inside table width + bool reset_row_height = false; // true if the height of all rows needs to be reset in the current pass + bool wrap = false; + bool collapsed = false; // Equivalent to HTML collapsing, eliminates whitespace between rows and cells + + // Entry followed by the minimum width of each column + + bc_table() { code = SCODE::TABLE_START; } + + inline bool floating_x() { + return (align & (ALIGN::LEFT|ALIGN::RIGHT|ALIGN::HORIZONTAL)) != ALIGN::NIL; + } + + void computeColumns() { // Compute the default column widths + if (!compute_columns) return; + + compute_columns = 0; + cells_expanded = false; + + if (!columns.empty()) { + for (unsigned j=0; j < columns.size(); j++) { + //if (ComputeColumns IS 1) { + // Columns[j].width = 0; + // Columns[j].min_width = 0; + //} + + if (columns[j].preset_width_rel) { // Percentage width value + columns[j].width = columns[j].preset_width * width; + } + else if (columns[j].preset_width) { // Fixed width value + columns[j].width = columns[j].preset_width; + } + else columns[j].width = 0; + + if (columns[j].min_width > columns[j].width) columns[j].width = columns[j].min_width; + } + } + else columns.clear(); + } +}; + +struct bc_table_end : public entity { + bc_table_end() { code = SCODE::TABLE_END; } +}; + +// It is recommended that font styling for paragraphs take advantage of the embedded font object. Using a separate +// FONT code raises the chance of confusion for the user, because features like leading are calculated using the +// style registered in the paragraph. + +class bc_paragraph : public entity { + public: + GuardedObject icon; // Icon representation if this is an item + bc_font font; // Default font that applies to this paragraph. Embedding the font style in this way ensures that vertical placement can be computed immediately without looking for a FONT code. + std::string value = ""; + DOUBLE x, y, height; // Layout dimensions, manipulated at run-time + DUNIT block_indent; // Indentation; also equivalent to setting a left margin value + DUNIT item_indent; // For list items only. This value is carried directly from bc_list.item_indent + DUNIT indent; // Client specified indent value + DUNIT line_height; // Spacing between paragraph lines on word-wrap, affects the cursor's vertical advance. Expressed as a ratio of the m_line.line_height + DUNIT leading; // Leading whitespace (minimum amount of space from the end of the last paragraph). Expressed as a ratio of the default line height + //DOUBLE trailing; // Not implemented: Trailing whitespace + // Options + bool list_item; // True if this paragraph represents a list item + bool trim; + bool aggregate; + + bc_paragraph() : entity(SCODE::PARAGRAPH_START), x(0), y(0), height(0), + block_indent(0.0, DU::PIXEL), item_indent(0.0, DU::PIXEL), indent(0.0, DU::PIXEL), + line_height(1.0, DU::TRUE_LINE_HEIGHT), leading(1.0, DU::LINE_HEIGHT), + list_item(false), trim(false), aggregate(false) { } + + bc_paragraph(const bc_font &Style) : bc_paragraph() { + font = Style; + font.font_index = -1; + } +}; + +struct bc_paragraph_end : public entity { + bc_paragraph_end() : entity(SCODE::PARAGRAPH_END) { } +}; + +struct bc_row : public entity { + GuardedObject rect_fill; + DOUBLE y = 0; + DOUBLE row_height = 0; // height of all cells on this row, used when drawing the cells + DOUBLE min_height = 0; + std::string stroke, fill; + bool vertical_repass = false; + + bc_row() : entity(SCODE::ROW) { } +}; + +struct bc_row_end : public entity { + bc_row_end() : entity(SCODE::ROW_END) { } +}; + +struct bc_cell : public entity { + GuardedObject viewport; + GuardedObject rect_fill; + KEYVALUE args; // Cell attributes, intended for event hooks + std::vector segments; + RSTREAM *stream; // Internally managed byte code content for the cell + CELL_ID cell_id = 0; // UID for the cell + LONG column = 0; // Column number that the cell starts in + LONG col_span = 1; // Number of columns spanned by this cell (normally set to 1) + LONG row_span = 1; // Number of rows spanned by this cell + CB border = CB::NIL; // Border options + DOUBLE x = 0, y = 0; // Cell coordinates, relative to their container + DOUBLE width = 0, height = 0; // Width and height of the cell + DUNIT stroke_width; + ui_hooks hooks; // UI hooks defined by the client + std::string edit_def; // The edit definition that this cell is linked to (if any) + std::string stroke; + std::string fill; + bool modified = false; // Set to true when content in the cell has been modified + // NOTE: Update the copy constructor if modifying the field list. + + void set_fill(const std::string); + + bc_cell(LONG pCellID, LONG pColumn); + ~bc_cell(); + bc_cell(const bc_cell &Other); +}; + +struct bc_text : public entity { + std::string text; + std::vector vector_text; + bool formatted = false; + SEGINDEX segment = -1; // Reference to the first segment that manages this text string. + + bc_text() { code = SCODE::TEXT; } + bc_text(std::string_view pText) : text(pText) { code = SCODE::TEXT; } + bc_text(std::string_view pText, bool pFormatted) : text(pText), formatted(pFormatted) { code = SCODE::TEXT; } +}; + +struct bc_use : public entity { + std::string id; // Reference to a symbol registered in the Document's SVG object + bool processed = false; + + bc_use() { code = SCODE::USE; } + bc_use(std::string pID) : id(pID) { code = SCODE::USE; } +}; + +struct bc_xml : public entity { + OBJECTID object_id = 0; // Reference to the object + bool owned = false; // true if the object is owned by a parent (not subject to normal document layout) + bc_xml() { code = SCODE::XML; } +}; + +//******************************************************************************************************************** +// Common widget management structure + +struct widget_mgr { + std::string name; // Client provided name identifier + std::string label; + std::string fill; // Default fill instruction + std::string alt_fill; // Alternative fill instruction for state changes + std::string font_fill; // Default fill instruction for user input text + GuardedObject viewport; + GuardedObject rect; // A vector will host the widget and define a clipping mask for it + padding pad, final_pad; // Padding defines external whitespace around the widget + DUNIT width, height; // Client can define a fixed width/height, or leave at 0 for auto-sizing + DUNIT def_size = DUNIT(1.0, DU::FONT_SIZE); // Default height or width if not otherwise specified. + DOUBLE final_width, final_height; // Final dimensions computed during layout + DOUBLE label_width = 0, label_pad = 0; // If a label is specified, the label_width & pad is in addition to final_width + DOUBLE x = 0; // For floating widgets only, horizontal position calculated during layout + ALIGN align = ALIGN::NIL; // NB: If horizontal alignment is defined then the widget is treated as floating. + bool alt_state = false, internal_page = false; + bool align_to_text = false; // Widgets with internal text (buttons, input, combobox) can look best if their internal text aligns with the baseline. + UBYTE label_pos = 1; // 0 = left, 1 = right + + inline bool floating_y() { + return false; + } + + inline bool floating_x() { + return (align & (ALIGN::LEFT|ALIGN::RIGHT|ALIGN::HORIZONTAL)) != ALIGN::NIL; + } + + constexpr DOUBLE full_width() const { + if (internal_page) return final_width + final_pad.left + final_pad.right; + else return final_width + label_width + label_pad + final_pad.left + final_pad.right; + } + + constexpr DOUBLE full_height() const { return final_height + final_pad.top + final_pad.bottom; } +}; + +//******************************************************************************************************************** + +struct dropdown_item { + std::string id, value, content, icon; + dropdown_item(std::string pContent) : content(pContent) { } +}; + +struct doc_menu { + GuardedObject m_surface; // Surface container for the menu UI + objVectorScene * m_scene; + objDocument * m_doc; // Independent document for managing the menu layout + objVectorViewport * m_view; + std::vector m_items; // List of items to appear in the menu + std::function m_callback; // Callback for item selection + std::variant m_ref; // User customisable reference. + std::string m_style; // Optional style override + scroll_mgr m_scroll; + + // Font options for items in the list + + std::string m_font_face; + std::string m_font_style; + DOUBLE m_font_size; + + LARGE m_show_time = 0; // Time of last acShow() + LARGE m_hide_time = 0; // Time of last acHide() + + objSurface * create(DOUBLE); + objSurface * get(); + void define_font(font_entry *); + void toggle(objVectorViewport *); + void reposition(objVectorViewport *); + void refresh(); + + doc_menu() { } + + doc_menu(std::function pCallback) : m_callback(pCallback) { } + + void show() { + acShow(*m_surface); + m_show_time = PreciseTime(); + } + + void hide() { + acHide(*m_surface); + } +}; + +//******************************************************************************************************************** + +struct bc_button : public entity, widget_mgr { + padding inner_padding; // Defines padding around the button's content. Not to be confused with the widget_mgr outer padding + RSTREAM *stream; + std::vector segments; + + bc_button(); + ~bc_button(); +}; + +struct bc_checkbox : public entity, widget_mgr { + bc_checkbox() { code = SCODE::CHECKBOX; } + GuardedObject label_text; + bool processed = false; +}; + +struct bc_combobox : public entity, widget_mgr { + GuardedObject label_text; + GuardedObject clip_vp; + objVectorText *input; + doc_menu menu; + std::string style; + std::string value; + std::string last_good_input; + + static void callback(struct doc_menu &, struct dropdown_item &); + + bc_combobox() : menu(&callback) { code = SCODE::COMBOBOX; align_to_text = true; } +}; + +struct bc_input : public entity, widget_mgr { + std::string value; + GuardedObject label_text; + GuardedObject clip_vp; + bool secret = false; + + bc_input() { code = SCODE::INPUT; align_to_text = true; } +}; + +struct bc_image : public entity, widget_mgr { + // Images inherit from widget graphics management since the rules are identical + bc_image() { code = SCODE::IMAGE; } +}; + +//******************************************************************************************************************** + +struct vp_to_entity { + std::variant widget; + bool hover = false; // True if the mouse pointer is hovering over the entity +}; + +//******************************************************************************************************************** + +struct ui_link { + bc_link origin; // A copy of the original link information (stable pointers are unavailable) + FloatRect area; // Occupied area in the UI + stream_char cursor_start, cursor_end; // Starting position and end of the link's segment + std::vector path; + RSTREAM *stream; + bool hover = false; // True if the mouse pointer is hovering over the link + + void exec(extDocument *); + + void append_link() { + path.push_back({ .Type = PE::Move, .X = area.X, .Y = area.Y }); + path.push_back({ .Type = PE::HLineRel, .X = area.Width, }); + path.push_back({ .Type = PE::VLineRel, .Y = area.Height }); + path.push_back({ .Type = PE::HLineRel, .X = -area.Width, }); + path.push_back({ .Type = PE::ClosePath }); + } +}; + +//******************************************************************************************************************** + +using CODEVAR = std::variant; + +using CODEMAP = std::unordered_map; // Pointer stability is required and guaranteed by unordered_map + +class RSTREAM { +public: + std::vector data; + CODEMAP codes; + + RSTREAM() { data.reserve(8 * 1024); } + + RSTREAM(RSTREAM &Other) { + data = Other.data; + codes = Other.codes; + } + + void clear() { + data.clear(); + codes.clear(); + } + + std::size_t size() const { return data.size(); } + + // Overloading [] operator to access elements in array style + + stream_code& operator[](const int Index) { return data[Index]; } + + const stream_code& operator[](const int Index) const { return data[Index]; } + + template T & lookup(const stream_char Index); + template T & lookup(const INDEX Index); + + template T & insert(stream_char &, T &); + template T & emplace(stream_char &, T &); + template T & emplace(stream_char &); + + inline INDEX find_cell(CELL_ID); + inline INDEX find_editable_cell(std::string_view); +}; + +//******************************************************************************************************************** + +class sorted_segment { // Efficient lookup to the doc_segment array, sorted by vertical position +public: + SEGINDEX segment; + DOUBLE y; +}; + +//******************************************************************************************************************** + +class extDocument : public objDocument { + public: + FUNCTION EventCallback; + std::unordered_map Vars; // Variables as defined by the client program. Transparently accessible like URI params. Names have priority over params. + std::unordered_map Params; // Incoming parameters provided via the URI + std::map TemplateIndex; + std::vector UIObjects; // List of temporary objects in the UI + std::vector Segments; + std::vector SortSegments; // Used for UI interactivity when determining who is front-most + std::vector Links; + std::unordered_map VPToEntity; // Lookup table for VP -> StreamCode. + std::vector MouseOverChain; + std::vector Resources; // Tracks resources that are page related. Terminated on page unload. + std::vector Tabs; + std::vector EditCells; + std::unordered_map EditDefs; + std::array, size_t(DRT::MAX)> Triggers; + std::vector TemplateArgs; // If a template is called, the tag is referred here so that args can be pulled from it + std::string FontFace; // Default font face + RSTREAM Stream; // Internal stream buffer + stream_char SelectStart, SelectEnd; // Selection start & end (stream index) + stream_char CursorIndex; // Position of the cursor if text is selected, or edit mode is active. It reflects the position at which entered text will be inserted. + stream_char SelectIndex; // The end of the selected text area, if text is selected. + std::string Path; // Optional file to load on Init() + std::string PageName; // Page name to load from the Path + std::string Bookmark; // Bookmark name processed from the Path + std::string WorkingPath; // String storage for the WorkingPath field + std::string LinkFill, VisitedLinkFill, LinkSelectFill, FontFill, Highlight; + std::string Background; // Background fill instruction + std::string CursorStroke; // Stroke instruction for the text cursor + objXML *Templates; // All templates for the current document are stored here + objXML *PretextXML; // Execute this XML prior to loading a new page. + objSVG *SVG; // Allocated by the tag + XMLTag *PageTag; // Refers to a specific page that is being processed for the layout + objScript *ClientScript; // Allows the developer to define a custom default script. + objScript *DefaultScript; + doc_edit *ActiveEditDef; // As for ActiveEditCell, but refers to the active editing definition + objVectorScene *Scene; // A document specific scene is required to keep our resources away from the host + DOUBLE VPWidth, VPHeight; // Dimensions of the host Viewport + DOUBLE FontSize; // The default font-size, measured in 72 DPI pixels + DOUBLE MinPageWidth; // Internal value for managing the page width, speeds up layout processing + DOUBLE PageWidth; // width of the widest section of the document page. Can be pre-defined for a fixed width. + DOUBLE LeftMargin, TopMargin, RightMargin, BottomMargin; + DOUBLE CalcWidth; // Final page width calculated from the layout process + DOUBLE XPosition, YPosition; // Scrolling offset + DOUBLE ClickX, ClickY; + DOUBLE SelectCharX; // The x coordinate of the SelectIndex character + DOUBLE CursorCharX; // The x coordinate of the CursorIndex character + DOUBLE PointerX, PointerY; // Current pointer coordinates on the document surface + LONG TemplatesModified; // For tracking modifications to Self->Templates (compared to Self->Templates->Modified) + SEGINDEX ClickSegment; // The index of the segment that the user clicked on + SEGINDEX MouseOverSegment; // The index of the segment that the mouse is currently positioned over + TIMER FlashTimer; // For flashing the cursor + CELL_ID ActiveEditCellID; // If editing is active, this refers to the ID of the cell being edited + ULONG ActiveEditCRC; // CRC for cell editing area, used for managing onchange notifications + WORD FocusIndex; // Tab focus index + WORD Invisible; // Incremented for sections within a hidden index + UBYTE Processing; // If > 0, the page layout is being altered + bool RefreshTemplates; // True if the template index requires refreshing. + bool RelPageWidth; // Relative page width + bool UpdatingLayout; // True if the page layout is in the process of being updated + bool PageProcessed; // True if the parsing of page content has been completed + bool NoWhitespace; // True if the parser should stop injecting whitespace characters + bool HasFocus; // True if the main viewport has the focus + bool CursorState; // True if the edit cursor is on, false if off. Used for flashing of the cursor + + std::vector & get_sorted_segments(); +}; + +bc_button::bc_button() { + code = SCODE::BUTTON; + stream = new RSTREAM(); + align_to_text = true; +} + +bc_button::~bc_button() { + delete stream; +} + +bc_cell::~bc_cell() { + delete stream; +} + +bc_cell::bc_cell(LONG pCellID, LONG pColumn) +{ + code = SCODE::CELL; + cell_id = pCellID; + column = pColumn; + stream = new RSTREAM(); +} + +bc_cell::bc_cell(const bc_cell &Other) { + if (Other.stream) stream = new RSTREAM(Other.stream[0]); + cell_id = Other.cell_id; + column = Other.column; + col_span = Other.col_span; + row_span = Other.row_span; + border = Other.border; + x = Other.x, y = Other.y; + width = Other.width, height = Other.height; + stroke_width = Other.stroke_width; + hooks = Other.hooks; + edit_def = Other.edit_def; + args = Other.args; + segments = Other.segments; + stroke = Other.stroke; + fill = Other.fill; + modified = Other.modified; +} diff --git a/src/document/defs/dunit.h b/src/document/defs/dunit.h new file mode 100644 index 000000000..1365c83d9 --- /dev/null +++ b/src/document/defs/dunit.h @@ -0,0 +1,35 @@ +//******************************************************************************************************************** +// Display Unit class. Reads CSS metric values during parsing and returns them as pixel values during the layout +// process. + +enum class DU : UBYTE { + NIL = 0, + PIXEL, // px + SCALED, // %: Scale to fill empty space + FONT_SIZE, // em + CHAR, // ch: The advance (width) of the '0' character + LINE_HEIGHT, // lh: Current line height + TRUE_LINE_HEIGHT, // lh: Current line height + ROOT_FONT_SIZE, // rem: Font size of the root element + ROOT_LINE_HEIGHT, // rlh: Line height of the root element + VP_WIDTH, // vw: 1% of the viewport's width + VP_HEIGHT, // vh: 1% of the viewport's height + VP_MIN, // vmin: 1% of the viewport's smallest axis + VP_MAX // vmax: 1% of the viewport's largest axis +}; + +struct DUNIT { + DOUBLE value; + DU type; + + DUNIT() : value(0), type(DU::NIL) { } + + DUNIT(DOUBLE pValue, DU pType = DU::PIXEL) : value(pValue), type(pType) { } + + DUNIT(const std::string_view pValue, DU pDefaultType = DU::PIXEL, DOUBLE pMin = std::numeric_limits::min()); + + DOUBLE px(class layout &Layout); + + constexpr bool empty() { return (type IS DU::NIL) or (!value); } + constexpr void clear() { value = 0; type = DU::PIXEL; } +}; diff --git a/src/document/hashes.fdl b/src/document/defs/hashes.fdl similarity index 50% rename from src/document/hashes.fdl rename to src/document/defs/hashes.fdl index 9a9e60da3..34a677942 100644 --- a/src/document/hashes.fdl +++ b/src/document/defs/hashes.fdl @@ -1,110 +1,164 @@ --$FLUID:Include -header({ copyright="Paul Manias © 1996-2023" }, function() +header({ copyright="Paul Manias © 2023-2024" }, function() hash("HASH", "0x%sUL", + "a", + "action", + "advance", "AfterLayout", + "align", + "alt-fill", + "anchor", + "b", + "background", "BeforeLayout", - "UserClick", - "UserClickRelease", - "UserMovement", - "Refresh", - "GotFocus", - "LostFocus", - "LeavingPage", - "a", - "link", "blockquote", - "b", - "caps", - "div", - "editdef", - "p", - "font", - "i", - "li", - "pre", - "indent", - "shrink", - "u", - "list", - "advance", + "body", + "border", + "bottom", "br", - "else", - "elseif", - "repeat", - "action", + "break", + "button", "cache", "call", - "debug", - "dml", - "include", - "print", - "parse", - "set", - "trigger", - "page", - "background", + "caps", + "cell", + "cell-padding", + "center", + "checkbox", + "clip-path", + "collapsed", + "colour", + "colour", + "colour", + "col-span", + "columns", + "combobox", + "continue", + "cursor-stroke", "data", + "debug", + "defs", + "div", + "edit", + "edit-all", + "edit-def", + "edit-fonts", + "edit-images", + "edit-tables", + "else", + "elseif", + "event", + "face", + "face", + "fill", + "float", + "focus", + "font", + "font-colour", + "font-face", + "font-fill", + "font-size", + "font-style", "footer", + "function", + "GotFocus", "head", "header", + "height", + "hint", + "href", + "h-spacing", + "i", + "icon", + "if", + "image", + "include", + "indent", + "index", "info", "inject", - "row", - "cell", - "table", - "td", - "tr", - "body", - "index", - "setmargins", - "setfont", + "inline", + "input", + "kerning", + "label", + "label-pos", + "leading", + "LeavingPage", + "left", + "li", + "line-breaks", + "line-height", + "link", + "list", + "LostFocus", + "margins", + "maxchars", + "middle", + "name", + "no-wrap", + "on-crossing", + "on-change", + "on-click", + "on-enter", + "on-exit", + "on-motion", + "p", + "padding", + "page", + "PageProcessed", + "page-width", + "parse", + "pre", + "preformat", + "print", + "Refresh", + "repeat", "restorestyle", + "right", + "row", + "row-span", "savestyle", "script", + "select", + "select-fill", + "set", + "setfont", + "setmargins", + "shrink", + "size", + "spacing", + "src", + "stroke", + "stroke-width", + "style", + "svg", + "table", + "td", "template", + "thickness", + "thin", + "title", + "top", + "tr", + "trigger", + "trim", + "u", + "unicode", + "use", + "UserClick", + "UserClickRelease", + "UserMovement", + "v-align", + "value", + "v-link", + "v-spacing", + "while", + "width", + "width", + "x", "xml", "xml-raw", "xml-translate", - "PageProcessed", - "focus", - "vlink", - "selectcolour", - "leftmargin", - "rightmargin", - "topmargin", - "bottommargin", - "margins", - "lineheight", - "pagewidth", - "width", - "colour", - "face", - "colour", - "face", - "size", - "style", - "preformat", - "columns", - "width", - "height", - "colour", - "border", - "highlight", - "shadow", - "spacing", - "thin", - "vspacing", - "colspan", - "rowspan", - "nowrap", - "onclick", - "edit", - "hspacing", - "fontface", - "fontsize", - "fontcolour", - "padding", - "thickness", - "select") + "y") end) diff --git a/src/document/hashes.h b/src/document/defs/hashes.h similarity index 51% rename from src/document/hashes.h rename to src/document/defs/hashes.h index dc2a44491..6b06a8c10 100644 --- a/src/document/hashes.h +++ b/src/document/defs/hashes.h @@ -1,111 +1,165 @@ #pragma once -// Copyright: Paul Manias © 1996-2023 +// Copyright: Paul Manias © 2023-2024 // Generator: idl-c +#define HASH_a 0x0002b606UL +#define HASH_action 0xf1644d03UL +#define HASH_advance 0x2062deb7UL #define HASH_AfterLayout 0x58983635UL +#define HASH_align 0x0f174e50UL +#define HASH_alt_fill 0x8c3507faUL +#define HASH_anchor 0xf22203e0UL +#define HASH_b 0x0002b607UL +#define HASH_background 0x677e1785UL #define HASH_BeforeLayout 0x68a24b96UL -#define HASH_UserClick 0xc0715faaUL -#define HASH_UserClickRelease 0x43eb566bUL -#define HASH_UserMovement 0x2b4154afUL -#define HASH_Refresh 0x3e3db654UL -#define HASH_GotFocus 0x00bb074fUL -#define HASH_LostFocus 0x319b8e67UL -#define HASH_LeavingPage 0x6af1c368UL -#define HASH_a 0x0002b606UL -#define HASH_link 0x7c9a15b3UL #define HASH_blockquote 0x1d60c29eUL -#define HASH_b 0x0002b607UL -#define HASH_caps 0x7c95048cUL -#define HASH_div 0x0b886a48UL -#define HASH_editdef 0x536ad41aUL -#define HASH_p 0x0002b615UL -#define HASH_font 0x7c96e4fcUL -#define HASH_i 0x0002b60eUL -#define HASH_li 0x0059789aUL -#define HASH_pre 0x0b889e6cUL -#define HASH_indent 0x04cbc867UL -#define HASH_shrink 0x1bba89f4UL -#define HASH_u 0x0002b61aUL -#define HASH_list 0x7c9a1661UL -#define HASH_advance 0x2062deb7UL +#define HASH_body 0x7c94b233UL +#define HASH_border 0xf4916c63UL +#define HASH_bottom 0xf492ca7aUL #define HASH_br 0x00597759UL -#define HASH_else 0x7c964c6eUL -#define HASH_elseif 0xfb5b2dddUL -#define HASH_repeat 0x192dec66UL -#define HASH_action 0xf1644d03UL +#define HASH_break 0x0f2c9f4aUL +#define HASH_button 0xf4ff5d81UL #define HASH_cache 0x0f355db9UL #define HASH_call 0x7c950401UL -#define HASH_debug 0x0f49a52cUL -#define HASH_dml 0x0b886ac2UL -#define HASH_include 0x9e36af89UL -#define HASH_print 0x102a0912UL -#define HASH_parse 0x1020dd80UL -#define HASH_set 0x0b88a991UL -#define HASH_trigger 0xf6b58819UL -#define HASH_page 0x7c9c2442UL -#define HASH_background 0x677e1785UL +#define HASH_caps 0x7c95048cUL +#define HASH_cell 0x7c951505UL +#define HASH_cell_padding 0xdbe3e489UL +#define HASH_center 0xf62fb286UL +#define HASH_checkbox 0x11a6290cUL +#define HASH_clip_path 0x455423a7UL +#define HASH_collapsed 0xeb60fadcUL +#define HASH_colour 0xf6e37b99UL +#define HASH_colour 0xf6e37b99UL +#define HASH_colour 0xf6e37b99UL +#define HASH_col_span 0x39056042UL +#define HASH_columns 0xd35616e6UL +#define HASH_combobox 0x3f17305eUL +#define HASH_continue 0x42aefb8aUL +#define HASH_cursor_stroke 0x05f4d608UL #define HASH_data 0x7c95915fUL +#define HASH_debug 0x0f49a52cUL +#define HASH_defs 0x7c95a0a7UL +#define HASH_div 0x0b886a48UL +#define HASH_edit 0x7c96292bUL +#define HASH_edit_all 0xc0a71eb1UL +#define HASH_edit_def 0xc0a72a87UL +#define HASH_edit_fonts 0x8745c682UL +#define HASH_edit_images 0x76d2860eUL +#define HASH_edit_tables 0x8fa2c093UL +#define HASH_else 0x7c964c6eUL +#define HASH_elseif 0xfb5b2dddUL +#define HASH_event 0x0f651c07UL +#define HASH_face 0x7c96a7f4UL +#define HASH_face 0x7c96a7f4UL +#define HASH_fill 0x7c96cb2cUL +#define HASH_float 0x0f71e19bUL +#define HASH_focus 0x0f735645UL +#define HASH_font 0x7c96e4fcUL +#define HASH_font_colour 0x613d163dUL +#define HASH_font_face 0xf1c14998UL +#define HASH_font_fill 0xf1c16cd0UL +#define HASH_font_size 0xf1c88f84UL +#define HASH_font_style 0x2ae0853aUL #define HASH_footer 0xfde4add4UL +#define HASH_function 0xd424384bUL +#define HASH_GotFocus 0x00bb074fUL #define HASH_head 0x7c97d177UL #define HASH_header 0x01d218aeUL +#define HASH_height 0x01d688deUL +#define HASH_hint 0x7c97e438UL +#define HASH_href 0x7c98094aUL +#define HASH_h_spacing 0x6cfb4f5fUL +#define HASH_i 0x0002b60eUL +#define HASH_icon 0x7c98572eUL +#define HASH_if 0x00597834UL +#define HASH_image 0x0fa87ca8UL +#define HASH_include 0x9e36af89UL +#define HASH_indent 0x04cbc867UL +#define HASH_index 0x0fa9159dUL #define HASH_info 0x7c9884d1UL #define HASH_inject 0x04cf1142UL -#define HASH_row 0x0b88a69dUL -#define HASH_cell 0x7c951505UL -#define HASH_table 0x1068fa8dUL -#define HASH_td 0x0059799dUL -#define HASH_tr 0x005979abUL -#define HASH_body 0x7c94b233UL -#define HASH_index 0x0fa9159dUL -#define HASH_setmargins 0xba739162UL -#define HASH_setfont 0x8c2edf88UL +#define HASH_inline 0x04d03c64UL +#define HASH_input 0x0fa94ab5UL +#define HASH_kerning 0x243d11f3UL +#define HASH_label 0x0fd835a5UL +#define HASH_label_pos 0x06af1864UL +#define HASH_leading 0x6ffe3259UL +#define HASH_LeavingPage 0x6af1c368UL +#define HASH_left 0x7c9a03b0UL +#define HASH_li 0x0059789aUL +#define HASH_line_breaks 0x8f2b8332UL +#define HASH_line_height 0x9c418313UL +#define HASH_link 0x7c9a15b3UL +#define HASH_list 0x7c9a1661UL +#define HASH_LostFocus 0x319b8e67UL +#define HASH_margins 0xb4d91256UL +#define HASH_maxchars 0x5db12b7cUL +#define HASH_middle 0x0dc5ebd4UL +#define HASH_name 0x7c9b0c46UL +#define HASH_no_wrap 0x1da3d7c9UL +#define HASH_on_crossing 0xa53975f7UL +#define HASH_on_change 0x6ed76db5UL +#define HASH_on_click 0x6ff95575UL +#define HASH_on_enter 0x701ece4dUL +#define HASH_on_exit 0x683f27a9UL +#define HASH_on_motion 0x86b40685UL +#define HASH_p 0x0002b615UL +#define HASH_padding 0x9ac8cc5cUL +#define HASH_page 0x7c9c2442UL +#define HASH_PageProcessed 0x6dd40a2aUL +#define HASH_page_width 0xfc47a28fUL +#define HASH_parse 0x1020dd80UL +#define HASH_pre 0x0b889e6cUL +#define HASH_preformat 0x729fef55UL +#define HASH_print 0x102a0912UL +#define HASH_Refresh 0x3e3db654UL +#define HASH_repeat 0x192dec66UL #define HASH_restorestyle 0x07ae549aUL +#define HASH_right 0x10494163UL +#define HASH_row 0x0b88a69dUL +#define HASH_row_span 0x2a89985cUL #define HASH_savestyle 0x3a48aec5UL #define HASH_script 0x1b600fbaUL +#define HASH_select 0x1b80e3c5UL +#define HASH_select_fill 0x9d771139UL +#define HASH_set 0x0b88a991UL +#define HASH_setfont 0x8c2edf88UL +#define HASH_setmargins 0xba739162UL +#define HASH_shrink 0x1bba89f4UL +#define HASH_size 0x7c9dede0UL +#define HASH_spacing 0xa47e0e2aUL +#define HASH_src 0x0b88ab2dUL +#define HASH_stroke 0x1c93c91dUL +#define HASH_stroke_width 0xa27c3faaUL +#define HASH_style 0x1061af16UL +#define HASH_svg 0x0b88abb5UL +#define HASH_table 0x1068fa8dUL +#define HASH_td 0x0059799dUL #define HASH_template 0xeeaba201UL +#define HASH_thickness 0x369e2871UL +#define HASH_thin 0x7c9e73d8UL +#define HASH_title 0x106daa27UL +#define HASH_top 0x0b88af18UL +#define HASH_tr 0x005979abUL +#define HASH_trigger 0xf6b58819UL +#define HASH_trim 0x7c9e9e61UL +#define HASH_u 0x0002b61aUL +#define HASH_unicode 0x3a5912acUL +#define HASH_use 0x0b88b3d2UL +#define HASH_UserClick 0xc0715faaUL +#define HASH_UserClickRelease 0x43eb566bUL +#define HASH_UserMovement 0x2b4154afUL +#define HASH_v_align 0xef2810d3UL +#define HASH_value 0x108d5742UL +#define HASH_v_link 0x1e8b13d6UL +#define HASH_v_spacing 0xcbc97d6dUL +#define HASH_while 0x10a3387eUL +#define HASH_width 0x10a3b0a5UL +#define HASH_width 0x10a3b0a5UL +#define HASH_x 0x0002b61dUL #define HASH_xml 0x0b88bfd6UL #define HASH_xml_raw 0x1f0b59cdUL #define HASH_xml_translate 0xa398e7f1UL -#define HASH_PageProcessed 0x6dd40a2aUL -#define HASH_focus 0x0f735645UL -#define HASH_vlink 0x109351c9UL -#define HASH_selectcolour 0xcaf45a59UL -#define HASH_leftmargin 0xe837e46eUL -#define HASH_rightmargin 0xb6995c61UL -#define HASH_topmargin 0xdde37dd6UL -#define HASH_bottommargin 0xc2a11ab8UL -#define HASH_margins 0xb4d91256UL -#define HASH_lineheight 0x8e286786UL -#define HASH_pagewidth 0x5a6bce02UL -#define HASH_width 0x10a3b0a5UL -#define HASH_colour 0xf6e37b99UL -#define HASH_face 0x7c96a7f4UL -#define HASH_colour 0xf6e37b99UL -#define HASH_face 0x7c96a7f4UL -#define HASH_size 0x7c9dede0UL -#define HASH_style 0x1061af16UL -#define HASH_preformat 0x729fef55UL -#define HASH_columns 0xd35616e6UL -#define HASH_width 0x10a3b0a5UL -#define HASH_height 0x01d688deUL -#define HASH_colour 0xf6e37b99UL -#define HASH_border 0xf4916c63UL -#define HASH_highlight 0x1ecf649dUL -#define HASH_shadow 0x1bb1226bUL -#define HASH_spacing 0xa47e0e2aUL -#define HASH_thin 0x7c9e73d8UL -#define HASH_vspacing 0x02c9da80UL -#define HASH_colspan 0xd3550935UL -#define HASH_rowspan 0x56c5a60fUL -#define HASH_nowrap 0x10924cdcUL -#define HASH_onclick 0x6c13e8e8UL -#define HASH_edit 0x7c96292bUL -#define HASH_hspacing 0x17303632UL -#define HASH_fontface 0x07729b6bUL -#define HASH_fontsize 0x0779e157UL -#define HASH_fontcolour 0xa88a28d0UL -#define HASH_padding 0x9ac8cc5cUL -#define HASH_thickness 0x369e2871UL -#define HASH_select 0x1b80e3c5UL +#define HASH_y 0x0002b61eUL diff --git a/src/document/defs/module_def.c b/src/document/defs/module_def.c new file mode 100644 index 000000000..f17493bd3 --- /dev/null +++ b/src/document/defs/module_def.c @@ -0,0 +1,4 @@ +// Auto-generated by idl-c.fluid + +#undef MOD_IDL +#define MOD_IDL "c.DCF:DISABLED=0x8,EDIT=0x1,NO_LAYOUT_MSG=0x10,NO_SYS_KEYS=0x4,OVERWRITE=0x2,UNRESTRICTED=0x20\nc.DEF:LINK_ACTIVATED=0x20,ON_CLICK=0x2,ON_CROSSING=0x18,ON_CROSSING_IN=0x8,ON_CROSSING_OUT=0x10,ON_MOTION=0x4,PATH=0x1\nc.DRT:AFTER_LAYOUT=0x1,BEFORE_LAYOUT=0x0,GOT_FOCUS=0x6,LEAVING_PAGE=0x8,LOST_FOCUS=0x7,MAX=0xa,PAGE_PROCESSED=0x9,REFRESH=0x5,USER_CLICK=0x2,USER_CLICK_RELEASE=0x3,USER_MOVEMENT=0x4\nc.FSO:ALIGN_CENTER=0x20,ALIGN_RIGHT=0x10,BOLD=0x1,ITALIC=0x2,NO_WRAP=0x40,PREFORMAT=0x8,STYLES=0x7,UNDERLINE=0x4\nc.RIPL:VERSION=""20240126""\nc.TT:EDIT=0x3,LINK=0x2,VECTOR=0x1\n" diff --git a/src/document/document.cpp b/src/document/document.cpp index 08aab05a4..4f9016a00 100644 --- a/src/document/document.cpp +++ b/src/document/document.cpp @@ -1,944 +1,326 @@ /********************************************************************************************************************* -The source code of the Parasol project is made publicly available under the -terms described in the LICENSE.TXT file that is distributed with this package. -Please refer to it for further information on licensing. - -********************************************************************************************************************** - --MODULE- -Document: Provides document display and editing facilities. - -The Document module exports a small number of functions in support of the @Document class. --END- - -PARAGRAPH MANAGEMENT --------------------- -Text is managed as a stream of text interspersed with escaped areas that contain byte codes. When the document text is -drawn, we maintain a 'line list' where the index of each line is recorded (see font_wrap()). This allows us to do -things like Ctrl-K to delete a 'line'. It also allows us to remember the pixel width and height of each line, which is -important for highlighting selected text. - -THE BYTE CODE -------------- -The text stream is a sequence of UTF-8 text with special escape codes inserted at points where we want to perform -certain actions, such as changing the font style, indicating hyperlinks etc. The escape code value is the standard -0x1b. Following that is a 16-bit number that indicates the length of the data (starting from 0x1b to the end of the -escape sequence). A single byte indicates the instruction, e.g. ESC_FONT, ESC_OBJECT, ESC_HYPERLINK. Following that -is the data related to that instruction. Another escape code is placed at the end to terminate the sequence (often -useful when a routine needs to backtrack through the text stream). - -GRAPHICAL OBJECT LAYOUT RULES ------------------------------ -RIPPLE allows for extremely complex document layouts. This chapter clarifies the layout rules that must be observed by -classes that provide support for RIPPLE page layouts. - -LAYOUT INTERPRETATION: Information about the available layout space will be passed in the Clip argument of the Layout -action. Note that if the object is inside a table cell, the amount of space available will be smaller than the actual -page size. Multiple iterations of the page layout will typically result in expanded coordinates in the Clip argument -each time the page layout is recalculated. - -FIXED PLACEMENT: If the class accepts dimension values for X, Y, Width and/or height, fixed placement is enabled if any -of those values are set by the user. Fixed placement can occur on the horizontal axis, vertical axis or both depending -on the number of dimension values that have been set. When fixed placement occurs, positioning relative to the -document cursor is disabled and the values supplied by the user are used for placement of the graphical object. Where -fixed placement is enabled, the object should still return a clipping region unless it is in background mode. Document -margins are honoured when in fixed placement mode. - -LAYOUT OPTIONS: All classes should support layout options by declaring a Layout field that supports the following -flags: SQUARE, WIDE, RIGHT, LEFT, BOTTOM, BACKGROUND, FOREGROUND, FIXED, VFIXED, HFIXED - -BACKGROUND MODE: The user can place graphical objects in the background by specifying the BACKGROUND layout option. -All text will be overlayed on top of the graphics and no text clipping will be performed against the object. The -layout support routine must return ERR_NothingDone to indicate that no clipping zone is defined. - -FOREGROUND MODE: The user can force an object into the foreground so that it will be drawn over the document's text -stream. This is achieved by setting the FOREGROUND layout option. - -EXTENDED CLIPPING: By default, clipping is to the graphical area occupied by an object. In some cases, the user may -wish to extend the clipping to the edges of the available layout space. This can be achieved by requesting an object -layout of RIGHT (extend clip to the right), LEFT (extend clip to the left), WIDE (extend both left and right). The -default layout clipping is SQUARE, which does not extend the clipping region. - -ALIGNMENT: Graphics Alignment can be requested by the document when calling the layout support action. The class can -also support alignment by providing an Align field. The formula that is used for alignment depends on whether or not -the dimensions are fixed in place. Alignment options will always override dimension settings where appropriate. Thus -if horizontal alignment is selected, any predefined X value set by the user can be ignored in favour of calculating the -alignment from the left-most side of the cell. The alignment formula must honour the margins of the available cell -space. When an object is not in background mode, all alignment values are calculated with respect to the height of the -current line and not the height of the cell space that is occupied. If horizontal centering is opted, the left-most -side used in the calculation must be taken from the current CursorX position. - -MARGINS: In standard layout mode, cell margins must be honoured. In fixed placement mode, cell margins are honoured -when calculating offsets, relative values and alignment. In background mode, cell margins are ignored. - -WHITESPACE: Gaps of whitespace at the top, left, right or bottom sides of a graphics object may be supported by some -class types, usually to prevent text from getting too close to the sides of an object. This feature can only be -applied to objects that are are not in fixed placement or background mode. - -TIGHT CLIPPING: Tight clipping is used where a complex clip region is required that is smaller than the rectangular -region occupied by a graphical object. A graphic with a circular or triangular shape could be an example of a graphic -that could use tight clipping. Support for this feature is currently undefined in the RIPPLE standard. In future it -is likely that it will be possible for the user to create customised tight-clipping zones by declaring polygonal areas -that should be avoided. There are no plans to implement this feature at the level of object layouts. - -TABLES ------- -Internally, the layout of tables is managed as follows: - -Border-Thickness, Cell-Spacing, Cell-Padding, Content, Cell-Padding, Cell-Spacing, ..., Border-Thickness - -Table attributes are: - -Columns: The minimum width of each column in the table. -Width/Height: Minimum width and height of the table. -Colour: Background colour for the table. -Border: Border colour for the table (see thickness). -Thickness: Thickness of the border colour. -Highlight Highlight colour for border. -Shadow: Shadow colour for border. -Padding: Padding inside each cell (syn. Margins) -Spacing: Spacing between cells. - -For complex tables with different coloured borders between cells, allocate single-pixel sized cells with the background -colour set to the desired value in order to create the illusion of multi-coloured cell borders. - -The page area owned by a table is given a clipping zone by the page layout engine, in the same way that objects are -given clipping zones. This allows text to be laid out around the table with no effort on the part of the developer. - - -CELLS ------ -Borders: Borders are drawn within the cell, so the cell-padding value need to at least be the same value as the border -thickness, or text inside the cell will mix with the border. +The source code of the Parasol project is made publicly available under the terms described in the LICENSE.TXT file +that is distributed with this package. Please refer to it for further information on licensing. *********************************************************************************************************************/ -//#define DEBUG +//#define _DEBUG //#define DBG_LAYOUT -//#define DBG_LAYOUT_ESCAPE // Do not use unless you want a lot of detail -//#define DBG_WORDWRAP //#define DBG_STREAM -//#define DBG_LINES // Print list of lines (segments) +//#define DBG_SEGMENTS // Print list of segments +//#define DBG_WORDWRAP //#define GUIDELINES // Clipping guidelines //#define GUIDELINES_CONTENT // Segment guidelines +#if (defined(_DEBUG) || defined(DBG_LAYOUT) || defined(DBG_STREAM) || defined(DBG_SEGMENTS)) + #define RETAIN_LOG_LEVEL TRUE +#endif + #ifdef DBG_LAYOUT - #define LAYOUT(...) LogF(__VA_ARGS__) - #define LAYOUT_LOGRETURN() LogReturn() + #define DLAYOUT(...) log.msg(__VA_ARGS__) #else - #define LAYOUT(...) - #define LAYOUT_LOGRETURN() + #define DLAYOUT(...) #endif #ifdef DBG_WORDWRAP - #define WRAP(...) LogF(__VA_ARGS__) - #define WRAP_LOGRETURN() LogReturn() + #define DWRAP(...) log.msg(__VA_ARGS__) #else - #define WRAP(...) - #define WRAP_LOGRETURN() + #define DWRAP(...) #endif -#define PRV_DOCUMENT #define PRV_DOCUMENT_MODULE -#define PRV_MODDOCUMENT #define PRV_SURFACE -#define COLOUR_LENGTH 16 -#define CURSOR_RATE 1400 -#define MAX_PAGEWIDTH 200000 -#define MAX_PAGEHEIGHT 200000 -#define MIN_PAGE_WIDTH 20 -#define MAX_ARGS 80 -#define MAX_DEPTH 1000 // Limits the number of tables-within-tables -#define MAX_DRAWBKGD 30 -#define BULLET_WIDTH 14 // Minimum column width for bullet point lists -#define BORDER_SIZE 1 -#define WIDTH_LIMIT 4000 -#define LINE_HEIGHT 16 // Default line height (measured as an average) for the page -#define DEFAULT_INDENT 30 -#define DEFAULT_FONTSIZE 10 -#define MIN_LINEHEIGHT 0.001 -#define MIN_VSPACING 0.001 -#define MAX_VSPACING 20 -#define MIN_LEADING 0.001 -#define MAX_LEADING 20 -#define NOTSPLIT -1 -#define BUFFER_BLOCK 8192 -#define CTRL_CODE '\E' // The escape code, 0x1b. NOTE: This must be between 1 and 0x20 so that it can be treated as whitespace for certain routines and also to avoid UTF8 interference -#define CLIP_BLOCK 30 - -#define DRAW_PAGE(a) QueueAction(MT_DrwInvalidateRegion, (a)->SurfaceID); - -#define ULD_TERMINATE 0x01 -#define ULD_KEEP_PARAMETERS 0x02 -#define ULD_REFRESH 0x04 -#define ULD_REDRAW 0x08 - -#define SEF_STRICT 0x00000001 -#define SEF_IGNORE_QUOTES 0x00000002 -#define SEF_KEEP_ESCAPE 0x00000004 -#define SEF_NO_SCRIPT 0x00000008 - -enum { - COND_NOT_EQUAL=1, - COND_EQUAL, - COND_LESS_THAN, - COND_LESS_EQUAL, - COND_GREATER_THAN, - COND_GREATER_EQUAL -}; #include #include #include #include #include +#include #include - -#include "hashes.h" +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include "defs/hashes.h" + +static const LONG MAX_PAGE_WIDTH = 30000; +static const LONG MAX_PAGE_HEIGHT = 100000; +static const LONG MIN_PAGE_WIDTH = 20; +static const LONG MAX_DEPTH = 40; // Limits recursion from tables-within-tables +static const LONG WIDTH_LIMIT = 4000; +static const LONG DEFAULT_FONTSIZE = 16; // 72DPI pixel size + +using BYTECODE = ULONG; +using CELL_ID = ULONG; + +static BYTECODE glByteCodeID = 1; +static ULONG glUID = 1000; // Use for generating unique/incrementing ID's, e.g. cell ID using namespace pf; -struct CoreBase *CoreBase; -struct FontBase *FontBase; -struct DisplayBase *DisplayBase; -struct VectorBase *VectorBase; +JUMPTABLE_CORE +JUMPTABLE_FONT +JUMPTABLE_DISPLAY +JUMPTABLE_VECTOR + +#include "defs/document.h" + +//******************************************************************************************************************** + +static std::string glHighlight = "rgb(219,219,255,255)"; + static OBJECTPTR clDocument = NULL; -static RGB8 glHighlight = { 220, 220, 255, 255 }; static OBJECTPTR modDisplay = NULL, modFont = NULL, modDocument = NULL, modVector = NULL; //******************************************************************************************************************** -class extDocument : public objDocument { - public: - FUNCTION EventCallback; - objXML *XML; // Source XML document - objXML *InsertXML; // For temporary XML parsing by the InsertXML method - objXML *Templates; // All templates for the current document are stored here - objXML *InjectXML; - std::unordered_map Vars; - std::unordered_map Params; - struct escCell *CurrentCell; // Used to assist drawing, reflects the cell we are currently drawing within (if any) - STRING ParamBuffer; - STRING Temp; - STRING Buffer; - STRING Path; // Optional file to load on Init() - STRING PageName; // Page name to load from the Path - STRING Bookmark; // Bookmark name processed from the Path - UBYTE *Stream; // Internal stream buffer - STRING WorkingPath; // String storage for the WorkingPath field - APTR prvKeyEvent; - OBJECTPTR CurrentObject; - OBJECTPTR UserDefaultScript; // Allows the developer to define a custom default script. - OBJECTPTR DefaultScript; - struct DocSegment *Segments; // Pointer to an array of segments - struct SortSegment *SortSegments; - struct style_status Style; - struct style_status RestoreStyle; - struct XMLTag *InjectTag; - struct XMLTag *HeaderTag; - struct XMLTag *FooterTag; - struct XMLTag *PageTag; - struct XMLTag *BodyTag; - struct DocClip *Clips; - LONG SurfaceWidth, SurfaceHeight; - struct DocLink *Links; - struct DocEdit *EditDefs; - struct MouseOver *MouseOverChain; - struct docresource *Resources; - struct DocEdit *ActiveEditDef; // As for ActiveEditCell, but refers to the active editing definition - struct { - STRING *Attrib; - STRING String; - } *VArg; - struct { - // The Ref is a unique ID for the Type, so you can use it to find the tab in the document stream - LONG Ref; // For TT_OBJECT: ObjectID; TT_LINK: LinkID - LONG XRef; // For TT_OBJECT: SurfaceID (if found) - UBYTE Type; // TT_LINK, TT_OBJECT - UBYTE Active:1; // TRUE if the tabbable link is active/visible - } *Tabs; - struct DocTrigger * Triggers[DRT_MAX]; - struct XMLTag * ArgNest[64]; - struct EditCell *EditCells; - STRING TBuffer; // Translation buffer - LONG TBufferSize; - LONG ArgNestIndex; - LONG TabIndex; - LONG MaxTabs; - LONG UniqueID; // Use for generating unique/incrementing ID's, e.g. cell ID - OBJECTID UserFocusID; - OBJECTID ViewID; // View surface - this contains the page and serves as the page's scrolling area - OBJECTID PageID; // Page surface - this holds the graphics content - LONG MinPageWidth; // Internal value for managing the page width, speeds up layout processing - FLOAT PageWidth; // Width of the widest section of the document page. Can be pre-defined for a fixed width. - LONG InputHandle; - LONG MaxClips; - LONG TotalClips; - LONG TotalLinks; // Current total of assigned links - LONG MaxLinks; // Current size limit of the link array - LONG LinkIndex; // Currently selected link (mouse over) - LONG ScrollWidth; - LONG StreamLen; // The length of the stream string (up to the termination character) - LONG StreamSize; // Allocated size of the stream buffer - LONG SelectStart; // Selection start (stream index) - LONG SelectEnd; // Selection end (stream index) - LONG MaxSegments; // Total number of segments available in the line array - LONG SegCount; // Total number of entries in the segments array - LONG SortCount; // Total number of entries in the sorted segments array - LONG XPosition; // Horizontal scrolling offset - LONG YPosition; // Vertical scrolling offset - LONG AreaX, AreaY; - LONG AreaWidth, AreaHeight; - LONG TempSize; - LONG BufferSize; - LONG BufferIndex; - LONG CalcWidth; - LONG LoopIndex; - LONG ElementCounter; // Counter for element ID's - LONG ClickX, ClickY; - LONG ECIndex; // EditCells table index - LONG ECMax; // Maximum number of entries currently available in the EditCells array - LONG ObjectCache; - LONG TemplatesModified; // Track modifications to Self->Templates - LONG BreakLoop; - LONG GeneratedID; // Unique ID that is regenerated on each load/refresh - LONG ClickSegment; // The index of the segment that the user clicked on - LONG MouseOverSegment; // The index of the segment that the mouse is currently positioned over - LONG CursorIndex; // Position of the cursor if text is selected, or edit mode is active. It reflects the position at which entered text will be inserted. -1 if not in use - LONG SelectIndex; // The end of the selected text area, if text is selected. Otherwise -1 - LONG SelectCharX; // The X coordinate of the SelectIndex character - LONG CursorCharX; // The X coordinate of the CursorIndex character - LONG PointerX; // Current pointer X coordinate on the document surface - LONG PointerY; - TIMER FlashTimer; - LONG ActiveEditCellID; // If editing is active, this refers to the ID of the cell being edited - ULONG ActiveEditCRC; // CRC for cell editing area, used for managing onchange notifications - UWORD Depth; // Section depth - increases when layout_section() recurses, e.g. into tables - UWORD ParagraphDepth; - UWORD LinkID; - WORD ArgIndex; - WORD FocusIndex; // Tab focus index - WORD Invisible; // This variable is incremented for sections within a hidden index - ULONG RelPageWidth:1; // Relative page width - ULONG PointerLocked:1; - ULONG ClickHeld:1; - ULONG UpdateLayout:1; - ULONG State:3; - ULONG VScrollVisible:1; - ULONG MouseOver:1; - ULONG PageProcessed:1; - ULONG NoWhitespace:1; - ULONG HasFocus:1; - ULONG CursorSet:1; - ULONG LMB:1; - ULONG EditMode:1; - ULONG CursorState:1; // TRUE if the edit cursor is on, FALSE if off. Used for flashing of the cursor - UBYTE Processing; - UBYTE DrawIntercept; - UBYTE InTemplate; - UBYTE BkgdGfx; -}; +std::vector & extDocument::get_sorted_segments() +{ + if ((!SortSegments.empty()) or (Segments.empty())) return SortSegments; + + auto sortseg_compare = [&] (sorted_segment &Left, sorted_segment &Right) { + if (Left.y < Right.y) return 1; + else if (Left.y > Right.y) return -1; + else { + if (Segments[Left.segment].area.X < Segments[Right.segment].area.X) return 1; + else if (Segments[Left.segment].area.X > Segments[Right.segment].area.X) return -1; + else return 0; + } + }; -enum { - RT_OBJECT_TEMP=1, - RT_OBJECT_UNLOAD, - RT_OBJECT_UNLOAD_DELAY, - RT_MEMORY, - RT_PERSISTENT_SCRIPT, - RT_PERSISTENT_OBJECT -}; + // Build the SortSegments array (unsorted) -struct docresource { - struct docresource *Next; - struct docresource *Prev; - union { - APTR Memory; - APTR Address; - OBJECTID ObjectID; - }; - LONG ClassID; - BYTE Type; -}; + SortSegments.resize(Segments.size()); + unsigned i; + SEGINDEX seg; + for (i=0, seg=0; seg < SEGINDEX(Segments.size()); seg++) { + if ((Segments[seg].area.Height > 0) and (Segments[seg].area.Width > 0)) { + SortSegments[i].segment = seg; + SortSegments[i].y = Segments[seg].area.Y; + i++; + } + } -struct tagroutine { - ULONG TagHash; - void (*Routine)(extDocument *, objXML *, XMLTag *, XMLTag *, LONG *, LONG); - ULONG Flags; -}; + // Shell sort -struct DocSegment { - LONG Index; // Line's byte index within the document text stream - LONG Stop; // The stopping index for the line - LONG TrimStop; // The stopping index for the line, with any whitespace removed - LONG X; // Horizontal coordinate of this line on the display - LONG Y; // Vertical coordinate of this line on the display - UWORD Height; // Pixel height of the line, including all anchored objects. When drawing, this is used for vertical alignment of graphics within the line - UWORD BaseLine; // Base-line - this is the height of the largest font down to the base line - UWORD Width; // Width of the characters in this line segment - UWORD AlignWidth; // Full-width of this line-segment if it were non-breaking - UWORD Depth; // Section depth that this segment belongs to - helps to differentiate between inner and outer tables - UBYTE Edit:1; // TRUE if this segment represents content that can be edited - UBYTE TextContent:1; // TRUE if there are text characters in this segment - UBYTE ControlContent:1; // TRUE if there are control codes in this segment - UBYTE ObjectContent:1; // TRUE if there are objects in this segment - UBYTE AllowMerge:1; // TRUE if this segment can be merged with sibling segments that have AllowMerge set to TRUE -}; + unsigned j, h = 1; + while (h < SortSegments.size() / 9) h = 3 * h + 1; -struct SortSegment { - LONG Segment; - LONG Y; -}; + for (; h > 0; h /= 3) { + for (auto i=h; i < SortSegments.size(); i++) { + sorted_segment temp = SortSegments[i]; + for (j=i; (j >= h) and (sortseg_compare(SortSegments[j - h], temp) < 0); j -= h) { + SortSegments[j] = SortSegments[j - h]; + } + SortSegments[j] = temp; + } + } -struct MouseOver { - struct MouseOver *Next; - LONG Top, Left, Bottom, Right; - LONG ElementID; -}; + return SortSegments; +} -struct DocLink { - union { - struct escLink *Link; - struct escCell *Cell; - APTR Escape; - }; - LONG X, Y; - UWORD Width, Height; - LONG Segment; - UBYTE EscapeCode; -}; +//******************************************************************************************************************** +// Function prototypes. -struct DocEdit { - struct DocEdit *Next; - ULONG NameHash; // The name of the edit area is held here as a hash. Zero if the area has no name. - LONG MaxChars; - LONG OnEnter; // Offset to the name of the OnEnter function - LONG OnExit; // Offset to the name of the OnExit function - LONG OnChange; // Offset to the name of the OnChange function - LONG Args; - LONG TotalArgs; - UBYTE LineBreaks:1; -}; +#include "defs/module_def.c" -struct DocClip { - struct SurfaceClip Clip; - LONG Index; - BYTE Transparent:1; -#ifdef DBG_WORDWRAP - UBYTE Name[32]; -#endif -}; +struct layout; // Pre-def -enum { - STATE_OUTSIDE=0, - STATE_ENTERED, - STATE_INSIDE -}; +static ERR activate_cell_edit(extDocument *, LONG, stream_char); +static ERR add_document_class(void); +static LONG add_tabfocus(extDocument *, TT, BYTECODE); +static void advance_tabfocus(extDocument *, BYTE); +static void deactivate_edit(extDocument *, bool); +static ERR extract_script(extDocument *, const std::string &, objScript **, std::string &, std::string &); +static void error_dialog(const std::string, const std::string); +static void error_dialog(const std::string, ERR); +static const Field * find_field(OBJECTPTR, CSTRING, OBJECTPTR *); +static SEGINDEX find_segment(std::vector &, stream_char, bool); +static LONG find_tabfocus(extDocument *, TT, BYTECODE); +static ERR flash_cursor(extDocument *, LARGE, LARGE); +inline std::string get_font_style(const FSO); +static LONG getutf8(CSTRING, LONG *); +static ERR insert_text(extDocument *, RSTREAM *, stream_char &, const std::string_view, bool); +static ERR insert_xml(extDocument *, RSTREAM *, objXML *, objXML::TAGS &, LONG, STYLE = STYLE::NIL, IPF = IPF::NIL); +static ERR key_event(objVectorViewport *, KQ, KEY, LONG); +static void layout_doc(extDocument *); +static ERR load_doc(extDocument *, std::string, bool, ULD = ULD::NIL); +static void notify_disable_viewport(OBJECTPTR, ACTIONID, ERR, APTR); +static void notify_enable_viewport(OBJECTPTR, ACTIONID, ERR, APTR); +static void notify_focus_viewport(OBJECTPTR, ACTIONID, ERR, APTR); +static void notify_free_event(OBJECTPTR, ACTIONID, ERR, APTR); +static void notify_lostfocus_viewport(OBJECTPTR, ACTIONID, ERR, APTR); +static ERR feedback_view(objVectorViewport *, FM); +static void process_parameters(extDocument *, const std::string_view); +static bool read_rgb8(CSTRING, RGB8 *); +static CSTRING read_unit(CSTRING, DOUBLE &, bool &); +static void redraw(extDocument *, bool); +static ERR report_event(extDocument *, DEF, entity *, KEYVALUE *); +static void reset_cursor(extDocument *); +static ERR resolve_fontx_by_index(extDocument *, stream_char, DOUBLE &); +static LONG safe_file_path(extDocument *, const std::string &); +static void set_focus(extDocument *, LONG, CSTRING); +static void show_bookmark(extDocument *, const std::string &); +static std::string stream_to_string(RSTREAM &, stream_char, stream_char); +static ERR unload_doc(extDocument *, ULD = ULD::NIL); +static bool valid_objectid(extDocument *, OBJECTID); +static bool view_area(extDocument *, DOUBLE, DOUBLE, DOUBLE, DOUBLE); +static std::string write_calc(DOUBLE, WORD); + +static ERR GET_WorkingPath(extDocument *, CSTRING *); + +inline bool read_rgb8(const std::string Value, RGB8 *RGB) { + return read_rgb8(Value.c_str(), RGB); +} -#define IPF_NOCONTENT 0x0001 -#define IPF_STRIPFEEDS 0x0002 - -#define TAG_CHILDREN 0x00000001 // Children are compulsory for the tag to have an effect -#define TAG_CONTENT 0x00000002 // Tag has a direct impact on text content or the page layout -#define TAG_CONDITIONAL 0x00000004 // Tag is a conditional statement -#define TAG_INSTRUCTION 0x00000008 // Tag is an executable instruction -#define TAG_ROOT 0x00000010 // Tag is limited to use at the root of the document -#define TAG_PARAGRAPH 0x00000020 // Tag results in paragraph formatting (will force some type of line break) -#define TAG_OBJECTOK 0x00000040 // It is OK for this tag to be used within any object - -// These flag values are in the upper word so that we can or them with IPF and TAG constants. - -#define FILTER_TABLE 0x80000000 // FILTER: Table -#define FILTER_ROW 0x40000000 // FILTER: Row -#define FILTER_ALL (FILTER_TABLE|FILTER_ROW) - -#define IXF_SIBLINGS 0x01 -#define IXF_HOLDSTYLE 0x02 -#define IXF_RESETSTYLE 0x04 -#define IXF_CLOSESTYLE 0x08 - -#define TRF_BREAK 0x00000001 -#define TRF_CONTINUE 0x00000002 - -#define PXF_ARGS 0x0001 -#define PXF_TRANSLATE 0x0002 - -// This PTR macros are used in tags.cpp - -#define PTR_SAVE_ARGS(tag) \ - *b_revert = Self->BufferIndex; \ - *s_revert = Self->ArgIndex; \ - *e_revert = 0; \ - if (convert_xml_args(Self, (tag)->Attrib, (tag)->TotalAttrib) != ERR_Okay) goto next; \ - *e_revert = Self->ArgIndex; - -#define PTR_RESTORE_ARGS() \ - if (*e_revert > *s_revert) { \ - while (*e_revert > *s_revert) { \ - *e_revert -= 1; \ - Self->VArg[*e_revert].Attrib[0] = Self->VArg[*e_revert].String; \ - } \ - } \ - Self->BufferIndex = *b_revert; \ - Self->ArgIndex = *s_revert; - -enum { - LINK_HREF=1, - LINK_FUNCTION -}; +#ifdef DBG_STREAM +static void print_stream(RSTREAM &); +#endif -struct tablecol { - UWORD PresetWidth; - UWORD MinWidth; // For assisting layout - UWORD Width; -}; +//******************************************************************************************************************** +// Fonts are shared in a global cache (multiple documents can have access to the cache) -typedef struct escAdvance { LONG X, Y; } escAdvance; - -typedef struct escIndex { - ULONG NameHash; // The name of the index is held here as a hash - LONG ID; // Unique ID for matching to the correct escIndexEnd - LONG Y; // The cursor's vertical position of when the index was encountered during layout - UBYTE Visible:1; // TRUE if the content inside the index is visible (this is the default) - UBYTE ParentVisible:1; // TRUE if the nearest parent index(es) will allow index content to be visible. TRUE is the default. This allows Hide/ShowIndex() to manage themselves correctly -} escIndex; - -typedef struct escIndexEnd { - LONG ID; // Unique ID matching to the correct escIndex -} escIndexEnd; - -typedef struct escLink { - UBYTE Type; // Link type (either a function or hyperlink) - UBYTE Args; // Total number of args being sent, if a function - UWORD ID; - LONG Align; - LONG PointerMotion; - // Please update tag_link() if you add fields to this structure -} escLink; - -typedef struct escList { - struct escList *Stack; // Stack management pointer during layout - RGB8 Colour; // Colour to use for bullet points (valid for LT_BULLET only). - STRING Buffer; // Temp buffer, used for ordered lists - LONG Start; // Starting value for ordered lists (default: 1) - LONG ItemIndent; // Minimum indentation for text printed for each item - LONG BlockIndent; // Indentation for each set of items - LONG ItemNum; - LONG OrderInsert; - FLOAT VSpacing; // Spacing between list items, expressed as a ratio - UBYTE Type; - UBYTE Repass:1; -} escList; - -typedef struct escSetMargins { WORD Left; WORD Top; WORD Bottom; WORD Right; } escSetMargins; - -typedef struct escObject { - OBJECTID ObjectID; // Reference to the object - LONG ClassID; // Class that the object belongs to, mostly for informative/debugging purposes - UBYTE Embedded:1; // TRUE if object is embedded as part of the text stream (treated as if it were a character) - UBYTE Owned:1; // TRUE if the object is owned by a parent (not subject to normal document layout) - UBYTE Graphical:1; // TRUE if the object has graphical representation or contains graphical objects -} escObject; - -typedef struct escTable { - struct escTable *Stack; - struct tablecol *Columns; // Table column management, allocated as an independent memory array - RGB8 Colour; // Background colour - RGB8 Highlight; // Border highlight - RGB8 Shadow; // Border shadow - WORD CellVSpacing; // Spacing between each cell, vertically - WORD CellHSpacing; // Spacing between each cell, horizontally - WORD CellPadding; // Spacing inside each cell (margins) - LONG RowWidth; // Assists in the computation of row width - LONG X, Y; // Calculated X/Y coordinate of the table - LONG Width, Height; // Calculated table width/height - LONG MinWidth, MinHeight; // User-determined minimum table width/height - LONG TotalColumns; // Total number of columns in table - LONG Rows; // Total number of rows in table - LONG RowIndex; // Current row being processed, generally for debugging - LONG CursorX, CursorY; // Cursor coordinates - LONG TotalClips; - UWORD Thickness; // Border thickness - UBYTE ComputeColumns; - UBYTE WidthPercent:1; // TRUE if width is a percentage - UBYTE HeightPercent:1; // TRUE if height is a percentage - UBYTE CellsExpanded:1; // FALSE if the table cells have not been expanded to match the inside table width - UBYTE ResetRowHeight:1; // TRUE if the height of all rows needs to be reset in the current pass - UBYTE Wrap:1; - UBYTE Thin:1; - // Entry followed by the minimum width of each column -} escTable; - -typedef struct escParagraph { - struct escParagraph *Stack; - LONG X, Y; - LONG Height; - LONG BlockIndent; - LONG ItemIndent; - DOUBLE Indent; - DOUBLE VSpacing; // Trailing whitespace, expressed as a ratio of the default line height - DOUBLE LeadingRatio; // Leading whitespace (minimum amount of space from the end of the last paragraph). Expressed as a ratio of the default line height - // Options - UBYTE Relative:1; - UBYTE CustomString:1; - UBYTE ListItem:1; - UBYTE Trim:1; -} escParagraph; - -typedef struct escRow { - struct escRow *Stack; - LONG Y; - LONG RowHeight; // Height of all cells on this row, used when drawing the cells - LONG MinHeight; - RGB8 Highlight; - RGB8 Shadow; - RGB8 Colour; - UBYTE VerticalRepass:1; -} escRow; - -typedef struct escCell { - // PLEASE REFER TO THE DEFAULTS IN TAG_CELL() IN TAGS.C IF YOU CHANGE THIS STRUCTURE - struct escCell *Stack; - LONG CellID; // Identifier for the matching escCellEnd - LONG Column; // Column number that the cell starts in - LONG ColSpan; // Number of columns spanned by this cell (normally set to 1) - LONG RowSpan; // Number of rows spanned by this cell - LONG AbsX, AbsY; // Cell coordinates, these are absolute - LONG Width, Height; // Width and height of the cell - LONG OnClick; // Offset to the name of an onclick function - LONG Args; // Offset to the argument list, if any are specified. Otherwise zero - ULONG EditHash; // Hash-name of the edit definition that this cell is linked to (if any, otherwise zero) - WORD TotalArgs; // Total number of arguments for function execution - RGB8 Highlight; - RGB8 Shadow; - RGB8 Colour; -} escCell; - -typedef struct escCellEnd { - LONG CellID; // Matching identifier from escCell -} escCellEnd; - -struct process_table { - struct escTable *escTable; - LONG RowCol; -}; +static std::deque glFonts; // font_entry pointers must be kept stable +static std::mutex glFontsMutex; -struct EditCell { - LONG CellID; - LONG X, Y, Width, Height; -}; +font_entry * bc_font::get_font() +{ + pf::Log log(__FUNCTION__); -enum { - ESC_FONT=1, - ESC_FONTCOLOUR, - ESC_UNDERLINE, - ESC_BACKGROUND, - ESC_INVERSE, - ESC_OBJECT, - ESC_LINK, - ESC_TABDEF, - ESC_PARAGRAPH_END, - ESC_PARAGRAPH_START, // 10 - ESC_LINK_END, - ESC_ADVANCE, - ESC_SHRINK, // Deprecated - ESC_LIST_START, - ESC_LIST_END, // 15 - ESC_TABLE_START, - ESC_TABLE_END, - ESC_ROW, - ESC_CELL, - ESC_CELL_END, // 20 - ESC_ROW_END, - ESC_SETMARGINS, - ESC_INDEX_START, - ESC_INDEX_END, - // End of list - NB: PLEASE UPDATE strCodes[] IF YOU ADD NEW CODES - ESC_END -}; + if (font_index IS -2) { + if (!glFonts.empty()) return &glFonts[0]; // Always try to return a font rather than NULL + return NULL; + } -enum { - LT_ORDERED=0, - LT_BULLET, - LT_CUSTOM -}; + if ((font_index < std::ssize(glFonts)) and (font_index >= 0)) return &glFonts[font_index]; -enum { - NL_NONE=0, - NL_PARAGRAPH -}; + // Sanity check the face and point values -static const CSTRING strCodes[] = { - "-", - "Font", - "FontCol", - "Uline", - "Bkgd", - "Inv", - "Obj", - "Link", - "TabDef", - "PE", - "P", - "EndLnk", - "Advance", - "Shrink", - "List", - "ListEnd", - "Table", - "TableEnd", - "Row", - "Cell", - "CellEnd", - "RowEnd", - "SetMargins", - "Index", - "IndexEnd" -}; + if (face.empty()) face = ((extDocument *)CurrentContext())->FontFace; -/********************************************************************************************************************* -** Function prototypes. -*/ + if (font_size < 3) { + font_size = ((extDocument *)CurrentContext())->FontSize; + if (font_size < 3) font_size = DEFAULT_FONTSIZE; + } -#include "module_def.c" + // Check the cache for this font -struct layout; // Pre-def + auto style_name = get_font_style(options); + APTR new_handle; + CSTRING resolved_face; + if (fntResolveFamilyName(face.c_str(), &resolved_face) IS ERR::Okay) { + face.assign(resolved_face); -static ERROR activate_edit(extDocument *, LONG, LONG); -static ERROR add_clip(extDocument *, SurfaceClip *, LONG, CSTRING, BYTE); -static ERROR add_document_class(void); -static LONG add_drawsegment(extDocument *, LONG, LONG Stop, layout *, LONG, LONG, LONG, CSTRING); -static void add_link(extDocument *, UBYTE, APTR, LONG, LONG, LONG, LONG, CSTRING); -static docresource * add_resource_id(extDocument *, LONG, LONG); -static docresource * add_resource_ptr(extDocument *, APTR, LONG); -static LONG add_tabfocus(extDocument *, UBYTE, LONG); -static void add_template(extDocument *, objXML *, XMLTag *); -static void advance_tabfocus(extDocument *, BYTE); -static LONG calc_page_height(extDocument *, LONG, LONG, LONG); -static void check_mouse_click(extDocument *, DOUBLE X, DOUBLE Y); -static void check_mouse_pos(extDocument *, DOUBLE, DOUBLE); -static void check_mouse_release(extDocument *, DOUBLE X, DOUBLE Y); -static ERROR consume_input_events(const InputEvent *, LONG); -static ERROR convert_xml_args(extDocument *, XMLAttrib *, LONG); -static LONG create_font(CSTRING, CSTRING, LONG); -static void deactivate_edit(extDocument *, BYTE); -static void deselect_text(extDocument *); -static void draw_background(extDocument *, objSurface *, objBitmap *); -static void draw_document(extDocument *, objSurface *, objBitmap *); -static void draw_border(extDocument *, objSurface *, objBitmap *); -static void exec_link(extDocument *, LONG); -static ERROR extract_script(extDocument *, CSTRING, OBJECTPTR *, CSTRING *, CSTRING *); -static void error_dialog(CSTRING, CSTRING, ERROR); -static ERROR eval(extDocument *, STRING, LONG, LONG); -static LONG find_segment(extDocument *, LONG, LONG); -static LONG find_tabfocus(extDocument *, UBYTE, LONG); -static ERROR flash_cursor(extDocument *, LARGE, LARGE); -static void free_links(extDocument *); -static CSTRING get_font_style(LONG); -//static LONG get_line_from_index(extDocument *, LONG Index); -static LONG getutf8(CSTRING, LONG *); -static ERROR insert_escape(extDocument *, LONG *, WORD, APTR, LONG); -static void insert_paragraph_end(extDocument *, LONG *); -static void insert_paragraph_start(extDocument *, LONG *, escParagraph *); -static ERROR insert_string(CSTRING, STRING, LONG, LONG, LONG); -static ERROR insert_text(extDocument *, LONG *, CSTRING, LONG, BYTE); -static ERROR insert_xml(extDocument *, objXML *, XMLTag *, LONG, UBYTE); -static void key_event(extDocument *, evKey *, LONG); -static ERROR keypress(extDocument *, LONG, LONG, LONG); -static void layout_doc(extDocument *); -static LONG layout_section(extDocument *, LONG, objFont **, LONG, LONG, LONG *, LONG *, LONG, LONG, LONG, LONG, BYTE *); -static ERROR load_doc(extDocument *, CSTRING, BYTE, BYTE); -static objFont * lookup_font(LONG, CSTRING); -static void notify_disable_surface(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, APTR Args); -static void notify_enable_surface(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, APTR Args); -static void notify_focus_surface(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, APTR Args); -static void notify_free_event(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, APTR Args); -static void notify_lostfocus_surface(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, APTR Args); -static void notify_redimension_surface(OBJECTPTR Object, ACTIONID ActionID, ERROR Result, struct acRedimension *Args); -static LONG parse_tag(extDocument *, objXML *, XMLTag *, LONG *, LONG); -#ifdef _DEBUG -static void print_xmltree(XMLTag *, LONG *) __attribute__ ((unused)); -#endif -#ifdef DBG_LINES -static void print_sorted_lines(extDocument *) __attribute__ ((unused)); -#endif -static ERROR process_page(extDocument *, objXML *); -static void process_parameters(extDocument *, CSTRING); -static bool read_rgb8(CSTRING, RGB8 *); -static void redraw(extDocument *, BYTE); -static ERROR report_event(extDocument *, LARGE, APTR, CSTRING); -static void reset_cursor(extDocument *); -static ERROR resolve_fontx_by_index(extDocument *, LONG, LONG *); -static ERROR resolve_font_pos(extDocument *, LONG, LONG X, LONG *, LONG *); -static LONG safe_file_path(extDocument *, CSTRING); -static void set_focus(extDocument *, LONG, CSTRING); -static void set_object_style(extDocument *, OBJECTPTR); -static void show_bookmark(extDocument *, CSTRING); -static void style_check(extDocument *, LONG *); -static void tag_object(extDocument *, CSTRING, CLASSID, XMLTag *, objXML *, XMLTag *, XMLTag *, LONG *, LONG, UBYTE *, UBYTE *, LONG *); -static void tag_xml_content(extDocument *, objXML *, XMLTag *, WORD); -static ERROR unload_doc(extDocument *, BYTE); -static BYTE valid_object(extDocument *, OBJECTPTR); -static BYTE valid_objectid(extDocument *, OBJECTID); -static BYTE view_area(extDocument *, LONG Left, LONG Top, LONG Right, LONG Bottom); -static LONG xml_content_len(XMLTag *) __attribute__ ((unused)); -static void xml_extract_content(XMLTag *, char *, LONG *, BYTE) __attribute__ ((unused)); + if (vecGetFontHandle(face.c_str(), style_name.c_str(), 400, font_size, &new_handle) IS ERR::Okay) { + for (unsigned i=0; i < glFonts.size(); i++) { + if (new_handle IS glFonts[i].handle) { + font_index = i; + break; + } + } + } -#ifdef DBG_STREAM -static void print_stream(extDocument *Self, STRING Stream) __attribute__ ((unused)); -#endif + if (font_index IS -1) { // Font not in cache + std::lock_guard lk(glFontsMutex); -struct FontEntry { - objFont *Font; - LONG Point; -}; + log.branch("Index: %d, %s, %s, %g", LONG(std::ssize(glFonts)), face.c_str(), style_name.c_str(), font_size); -static STRING exsbuffer = NULL; -static LONG exsbuffer_size = 0; -static FontEntry *glFonts = NULL; -static LONG glTotalFonts = 0; -static LONG glMaxFonts = 0; + if (font_index IS -1) { // Add the font to the cache + font_index = std::ssize(glFonts); + glFonts.emplace_back(new_handle, face, style_name, font_size); + } + } -// Control code format: ESC,Code,Length[2],ElementID[4]...Data...,Length[2],ESC + if (font_index >= 0) return &glFonts[font_index]; + } -#define ESC_LEN_START 8 -#define ESC_LEN_END 3 -#define ESC_LEN (ESC_LEN_START + ESC_LEN_END) + log.warning("Failed to create font %s:%g", face.c_str(), font_size); -template -T * escape_data(BYTE *Stream, LONG Index) { - return (T *)(Stream + Index + ESC_LEN_START); + if (!glFonts.empty()) return &glFonts[0]; // Always try to return a font rather than NULL + else return NULL; } -template -T * escape_data(UBYTE *Stream, LONG Index) { - return (T *)(Stream + Index + ESC_LEN_START); -} +//******************************************************************************************************************** -#define remove_cursor(a) draw_cursor((a),FALSE) -// Calculate the length of an escape sequence -#define ESC_ELEMENTID(a) (((LONG *)(a))[1]) -#define ESCAPE_CODE(stream, index) ((stream)[(index)+1]) // Escape codes are only 1 byte long -#define ESCAPE_LEN(a) ((((a)[2])<<8) | ((a)[3])) -// Move to the next character - handles UTF8 only, no escape sequence handling -#define NEXT_CHAR(s,i) { if ((s)[(i)] IS CTRL_CODE) i += ESCAPE_LEN(s+i); else { i++; while (((s)[(i)] & 0xc0) IS 0x80) (i)++; } } -#define PREV_CHAR(s,i) { if ((s)[(i)-1] IS CTRL_CODE) (i) -= ((s)[(i)-3]<<8) | ((s)[(i)-2]); else i--; } - -#define START_TEMPLATE(TAG,XML,ARGS) \ - XMLTag *savetag; \ - objXML *savexml; \ - savetag = Self->InjectTag; \ - savexml = Self->InjectXML; \ - Self->InjectTag = (TAG); \ - Self->InjectXML = (XML); \ - Self->InTemplate++; - -#define END_TEMPLATE() \ - Self->InTemplate--; \ - Self->InjectTag = savetag; \ - Self->InjectXML = savexml; - -static FIELD FID_LayoutSurface; +template inline void remove_cursor(T a) { draw_cursor(a, false); } //******************************************************************************************************************** -ERROR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) +static const std::array strCodes = { + "?", "Text", "Font", "FontEnd", "Link", "TabDef", "PE", "P", "EndLink", "Advance", "List", "ListEnd", + "Table", "TableEnd", "Row", "Cell", "RowEnd", "Index", "IndexEnd", "XML", "Image", "Use", "Button", "Checkbox", + "Combobox", "Input" +}; + +template inline const std::string_view & BC_NAME(RSTREAM &Stream, T Index) { + return strCodes[LONG(Stream[Index].code)]; +} + +//******************************************************************************************************************** + +static ERR CMDInit(OBJECTPTR argModule, struct CoreBase *argCoreBase) { CoreBase = argCoreBase; argModule->getPtr(FID_Root, &modDocument); - if (objModule::load("display", &modDisplay, &DisplayBase) != ERR_Okay) return ERR_InitModule; - if (objModule::load("font", &modFont, &FontBase) != ERR_Okay) return ERR_InitModule; - if (objModule::load("vector", &modVector, &VectorBase) != ERR_Okay) return ERR_InitModule; - - FID_LayoutSurface = StrHash("LayoutSurface", 0); + if (objModule::load("display", &modDisplay, &DisplayBase) != ERR::Okay) return ERR::InitModule; + if (objModule::load("font", &modFont, &FontBase) != ERR::Okay) return ERR::InitModule; + if (objModule::load("vector", &modVector, &VectorBase) != ERR::Okay) return ERR::InitModule; OBJECTID style_id; - if (!FindObject("glStyle", ID_XML, FOF::NIL, &style_id)) { + if (FindObject("glStyle", ID_XML, FOF::NIL, &style_id) IS ERR::Okay) { char buffer[32]; - if (!acGetVar(GetObjectPtr(style_id), "/colours/@DocumentHighlight", buffer, sizeof(buffer))) { - read_rgb8(buffer, &glHighlight); + if (acGetVar(GetObjectPtr(style_id), "/colours/@DocumentHighlight", buffer, sizeof(buffer)) IS ERR::Okay) { + glHighlight.assign(buffer); } } return add_document_class(); } -ERROR CMDExpunge(void) +static ERR CMDExpunge(void) { - { - pf::Log log; - log.msg("Freeing %d internally allocated fonts.", glTotalFonts); - for (LONG i=0; i < glTotalFonts; i++) FreeResource(glFonts[i].Font); - } - - if (exsbuffer) { FreeResource(exsbuffer); exsbuffer = NULL; } - if (glFonts) { FreeResource(glFonts); glFonts = NULL; } + glFonts.clear(); - if (modVector) { FreeResource(modVector); modVector = NULL; } - if (modDisplay) { FreeResource(modDisplay); modDisplay = NULL; } - if (modFont) { FreeResource(modFont); modFont = NULL; } + if (modVector) { FreeResource(modVector); modVector = NULL; } + if (modDisplay) { FreeResource(modDisplay); modDisplay = NULL; } + if (modFont) { FreeResource(modFont); modFont = NULL; } - if (clDocument) { FreeResource(clDocument); clDocument = NULL; } - return ERR_Okay; + if (clDocument) { FreeResource(clDocument); clDocument = NULL; } + return ERR::Okay; } -static ERROR CMDOpen(OBJECTPTR Module) -{ - Module->set(FID_FunctionList, glFunctions); - return ERR_Okay; -} - -/********************************************************************************************************************* - --FUNCTION- -CharLength: Returns the length of any character or escape code in a document data stream. - -This function will compute the byte-length of any UTF-8 character sequence or escape code in a document's data stream. - --INPUT- -ext(Document) Document: The document to query. -int Index: The byte index of the character to inspect. - --RESULT- -int: The length of the character is returned, or 0 if an error occurs. - --END- - -*********************************************************************************************************************/ +//******************************************************************************************************************** -static LONG docCharLength(extDocument *Self, LONG Index) +inline INDEX RSTREAM::find_cell(CELL_ID ID) { - if (!Self) return 0; - - if (Self->Stream[Index] IS CTRL_CODE) { - return ESCAPE_LEN(Self->Stream + Index); - } - else { - LONG len = 1; - while (((Self->Stream)[len] & 0xc0) IS 0x80) len++; - return len; + for (INDEX i=0; i < std::ssize(data); i++) { + if (data[i].code IS SCODE::CELL) { + auto &cell = std::get(codes[data[i].uid]); + if ((ID) and (ID IS cell.cell_id)) return i; + } } -} -//******************************************************************************************************************** + return -1; +} -INLINE LONG find_cell(extDocument *Self, LONG ID, ULONG EditHash) +inline INDEX RSTREAM::find_editable_cell(std::string_view EditDef) { - UBYTE *stream; - if (!(stream = (UBYTE *)Self->Stream)) return -1; - - LONG i = 0; - while (stream[i]) { - if (stream[i] IS CTRL_CODE) { - if (ESCAPE_CODE(stream, i) IS ESC_CELL) { - auto cell = escape_data(stream, i); - if ((ID) and (ID IS cell->CellID)) return i; - else if ((EditHash) and (EditHash IS cell->EditHash)) return i; - } + for (INDEX i=0; i < std::ssize(data); i++) { + if (data[i].code IS SCODE::CELL) { + auto &cell = lookup(i); + if (EditDef == cell.edit_def) return i; } - NEXT_CHAR(stream, i); } return -1; @@ -946,32 +328,44 @@ INLINE LONG find_cell(extDocument *Self, LONG ID, ULONG EditHash) //******************************************************************************************************************** -INLINE DocEdit * find_editdef(extDocument *Self, ULONG Hash) +inline doc_edit * find_editdef(extDocument *Self, std::string_view Name) { - for (auto edit=Self->EditDefs; edit; edit=edit->Next) { - if (edit->NameHash IS Hash) return edit; - } - - return NULL; + auto it = Self->EditDefs.find(Name); + if (it != Self->EditDefs.end()) return &it->second; + else return NULL; } //******************************************************************************************************************** +// Layout the document with a lower log level to cut back on noise. -INLINE void layout_doc_fast(extDocument *Self) +inline void layout_doc_fast(extDocument *Self) { - AdjustLogLevel(2); +#ifndef RETAIN_LOG_LEVEL + pf::LogLevel level(2); +#endif + layout_doc(Self); - AdjustLogLevel(-2); } -#include "tags.cpp" +//******************************************************************************************************************** + +#include "scrollbar.cpp" +#include "streamchar.cpp" +#include "parsing.cpp" #include "class/fields.cpp" #include "class/document_class.cpp" +#include "debug.cpp" #include "functions.cpp" +#include "ui.cpp" +#include "layout.cpp" +#include "menu.cpp" +#include "draw.cpp" +#include "entities.cpp" +#include "dunit.cpp" //******************************************************************************************************************** -static ERROR add_document_class(void) +static ERR add_document_class(void) { clDocument = objMetaClass::create::global( fl::BaseClassID(ID_DOCUMENT), @@ -984,12 +378,12 @@ static ERROR add_document_class(void) fl::Fields(clFields), fl::Size(sizeof(extDocument)), fl::Path(MOD_PATH), - fl::FileExtension("*.rpl|*.ripple|*.rple")); + fl::FileExtension("*.rpl|*.ripple|*.ripl")); - return clDocument ? ERR_Okay : ERR_AddClass; + return clDocument ? ERR::Okay : ERR::AddClass; } //******************************************************************************************************************** -PARASOL_MOD(CMDInit, NULL, CMDOpen, CMDExpunge, MOD_IDL, NULL) +PARASOL_MOD(CMDInit, NULL, NULL, CMDExpunge, MOD_IDL, NULL) extern "C" struct ModHeader * register_document_module() { return &ModHeader; } diff --git a/src/document/document.fdl b/src/document/document.fdl deleted file mode 100644 index 17c5474c5..000000000 --- a/src/document/document.fdl +++ /dev/null @@ -1,162 +0,0 @@ ---$FLUID:Include - -module({ name="Document", copyright="Paul Manias © 2005-2023", version=1.0 }, function() - restrict(function() - loadFile(glPath .. 'common-graphics.fdl') - end) - - c_include("", "", "") - - const("RIPPLE", { comment="Official version number (date format). Any changes to the handling of document content require that this number be updated." }, { - VERSION = "\"20160601\"" - }) - - enum("TT", { start=1 }, "OBJECT", "LINK", "EDIT") - - flags("DEF", { comment="Event flags for selectively receiving events from the Document object." }, - "PATH: The source file path has changed. Useful for detecting when the user has left the page.", - "LINK_ACTIVATED: The user has interacted with a hyperlink. This event can be cancelled by returning ERR_Skip.") - - enum("DRT", { start=0, comment="Internal trigger codes" }, - "BEFORE_LAYOUT", - "AFTER_LAYOUT", - "USER_CLICK", - "USER_CLICK_RELEASE", - "USER_MOVEMENT", - "REFRESH", - "GOT_FOCUS", - "LOST_FOCUS", - "LEAVING_PAGE", - "PAGE_PROCESSED", - "MAX") - - flags("DCF", { comment="Document flags" }, - "EDIT: Allow direct keyboard input and document editing.", - "OVERWRITE: This flag forces overwrite mode when the user enters information through the keyboard. If the flag is not set, then insert mode is used.", - "NO_SYS_KEYS: System-keys provide standard key support for Ctrl-C, Ctrl-X etc. Set this flag to turn them off.", - "DISABLED: This read-only flag is set if the object has been disabled through the Disable action.", - "NO_SCROLLBARS: Do not display scrollbars if the page exceeds the size of the view.", - "NO_LAYOUT_MSG: Turn off debug output produced during document layout and processing - useful on refresh for example.", - "UNRESTRICTED: Turn off all security measures - may only be set prior to initialisation.") - - flags("DBE", { comment="Border edge flags." }, - "TOP: Top border edge.", - "LEFT: Left border edge.", - "RIGHT: Right border edge.", - "BOTTOM: Bottom border edge.") - - flags("FSO", { comment="These are document style flags, as used in the DocStyle structure" }, - "BOLD", - "ITALIC", - "UNDERLINE", - "PREFORMAT: All white-space is taken into account.", - "CAPS: Print all text in caps.", - "ALIGN_RIGHT", - "ALIGN_CENTER", - "ANCHOR: Anchor objects to the text.", - "NO_WRAP: Do not wrap the text.", - { STYLES = "BOLD|UNDERLINE|ITALIC|CAPS" }) - - struct("DocStyle", { version=1, type="docstyle", comment="This structure is passed to objects that support the LayoutStyle field" }, [[ - int Version # Version of this DocStyle structure - obj(Document) Document # The document object that this style originates from - obj(Font) Font # Pointer to the current font object. Indicates face, style etc, but not simple attributes like colour - struct(RGB8) FontColour # Foreground colour (colour of the font) - struct(RGB8) FontUnderline # Underline colour for the font, if active - int StyleFlags # Font style flags (FSO) - ]]) - - struct ("deLinkActivated", { }, [[ - struct(*KeyStore) Parameters # All key-values associated with the link. - ]]) - - struct("escFont", { }, [[ - short Index # Font lookup - short Options # FSO flags - struct(RGB8) Colour # Font colour - ]]) - - c_insert([[ -typedef struct escFont escFont; - ]]) - - struct("SurfaceClip", { }, [[ - struct(*SurfaceClip) Next - int Left - int Top - int Right - int Bottom - ]]) - - struct("style_status", { }, [[ - struct(escFont) FontStyle - struct(*process_table) Table - struct(*escList) List - char(36) Face - short Point - bit(uchar) FontChange # A major font change has occurred (e.g. face, point size) - bit(uchar) StyleChange # A minor style change has occurred (e.g. font colour) - ]]) - - struct("docdraw", { }, [[ - ptr Object - oid ID - ]]) - - struct("DocTrigger", { }, [[ - struct(*DocTrigger) Next - struct(*DocTrigger) Prev - func Function - ]]) - - methods("Document", "doc", { - { id=1, name="FeedParser" }, - { id=2, name="SelectLink" }, - { id=3, name="ApplyFontStyle" }, - { id=4, name="FindIndex" }, - { id=5, name="InsertXML" }, - { id=6, name="RemoveContent" }, - { id=7, name="InsertText" }, - { id=8, name="CallFunction" }, - { id=9, name="AddListener" }, - { id=10, name="RemoveListener" }, - { id=11, name="ShowIndex" }, - { id=12, name="HideIndex" }, - { id=13, name="Edit" }, - { id=14, name="ReadContent" } - }) - - class("Document", { src={ "class/document_class.cpp", "class/fields.cpp" }, output="class/document_def.c" }, [[ - large(DEF) EventMask # Event mask for selectively receiving events from the Document object. - str Description # A description assigned by the author of the document - str FontFace # The user's default font face - str Title # The title of the document - str Author # The author of the document - str Copyright # Copyright information for the document - str Keywords # Keywords for the document - oid TabFocus # If the tab key is pressed, focus can be changed to this object - oid Surface # The surface that the document will be rendered to - oid Focus - int(DCF) Flags # Optional flags - int LeftMargin # Size of the left margin - int TopMargin # Size of the top margin - int RightMargin # Size of the right margin - int BottomMargin # Size of the bottom margin - int FontSize # The user's default font size - int PageHeight # Height of the document page - int(DBE) BorderEdge - int LineHeight # Default line height (assumed to be an average) for all text the loaded page - error Error # Processing error code - struct(RGB8) FontColour # Default font colour - struct(RGB8) Highlight # Default colour for document highlighting - struct(RGB8) Background # Colour for document background - struct(RGB8) CursorColour # The colour of the cursor - struct(RGB8) LinkColour # Colour to use for hyperlinks - struct(RGB8) VLinkColour # Colour to use for visited hyperlinks - struct(RGB8) SelectColour # Default colour to use when links are selected (e.g. when the user tabs to a link) - struct(RGB8) Border - ]]) - - functionNames("doc", - "CharLength") -end) diff --git a/src/document/draw.cpp b/src/document/draw.cpp new file mode 100644 index 000000000..64a0f93a3 --- /dev/null +++ b/src/document/draw.cpp @@ -0,0 +1,824 @@ + +//******************************************************************************************************************** +// If the layout needs to be recalculated, set the UpdatingLayout field before calling this function. + +static void redraw(extDocument *Self, bool Focus) +{ + pf::Log log(__FUNCTION__); + + log.traceBranch(""); + + { + #ifndef RETAIN_LOG_LEVEL + pf::LogLevel level(3); + #endif + + layout_doc(Self); // Does nothing if UpdatingLayout is false + } + + if (Self->Viewport->Scene->SurfaceID) Self->Viewport->draw(); + + if ((Focus) and (Self->FocusIndex != -1)) set_focus(Self, -1, "redraw()"); +} + +//******************************************************************************************************************** +// Determine the position of the widget and return the coordinates in (X, Y) +// +// Use AsViewport if the Widget.viewport represents the widget in the UI. A viewport will be created automatically +// if the client has not already done so, and it will be assumed that patterns defined in alt_state/alt_fill are to be +// used as fills. +// +// Alternatively, a VectorRectangle will be created automatically and reference the patterns defined in +// alt_state/alt_fill. This is the fastest means of rendering widget graphics at the cost of additional bitmap +// caching. +// +// Irrespective of the drawing method, the X/Y/W/H dimensions of the widget are updated before returning. + +ERR layout::position_widget(widget_mgr &Widget, doc_segment &Segment, objVectorViewport *ParentVP, bc_font *Style, + DOUBLE &XAdvance, DOUBLE LabelWidth, bool AsViewport, DOUBLE &X, DOUBLE &Y) +{ + if (Widget.floating_x()) { + // If the widget is floating then the X coordinate will be pre-calculated during layout + X = Widget.x + Widget.final_pad.left; + } + else { + // For inline widgets, alignment is calculated from the active style. + if ((Style->options & FSO::ALIGN_CENTER) != FSO::NIL) X = XAdvance + ((Segment.align_width - Segment.area.Width) * 0.5); + else if ((Style->options & FSO::ALIGN_RIGHT) != FSO::NIL) X = XAdvance + Segment.align_width - Segment.area.Width; + else X = XAdvance; + } + + // TODO: Is the use of floating_x() correct? + if (Widget.floating_x()) Y = Segment.area.Y + Widget.final_pad.top; + else { + if ((Style->valign & ALIGN::TOP) != ALIGN::NIL) { + Y = Widget.final_pad.top; + } + else if ((Style->valign & ALIGN::VERTICAL) != ALIGN::NIL) { + Y = (Segment.area.Height - Widget.full_height()) * 0.5; + } + else { + // Bottom alignment. Aligning to the base-line is preferable, but if the widget is tall then we take up the descent space too. + auto h = Widget.final_height - Widget.final_pad.bottom; + if (h > Segment.area.Height - Segment.descent) { + if (Widget.align_to_text) Y = Segment.area.Height - h + Segment.descent; + else Y = Segment.area.Height - h; + } + else Y = Segment.area.Height - Segment.descent - h; + } + + Y += Segment.area.Y; + } + + const DOUBLE width = Widget.final_width + LabelWidth; + + if (AsViewport) { + // Using a viewport means that the vector paths will be recomputed on each draw cycle. + if (Widget.viewport.empty()) { + auto vp = objVectorViewport::create::global({ + fl::Name("vp_widget"), + fl::Owner(ParentVP->UID), + fl::Fill(Widget.alt_state ? Widget.alt_fill : Widget.fill) + }); + + if (!vp) return ERR::CreateObject; + else Widget.viewport.set(vp); + } + + Widget.viewport->setFields(fl::X(F2T(X)), fl::Y(F2T(Y)), fl::Width(width), fl::Height(Widget.final_height)); + } + else { + // Using a rectangle with a pattern reference will keep the pattern bitmap cached. + if (Widget.rect.empty()) { + auto rect = objVectorRectangle::create::global({ + fl::Name("rect_widget"), + fl::Owner(ParentVP->UID), + fl::Fill(Widget.alt_state ? Widget.alt_fill : Widget.fill) + }); + + if (!rect) return ERR::CreateObject; + else Widget.rect = rect; + } + + Widget.rect->setFields(fl::X(F2T(X)), fl::Y(F2T(Y)), fl::Width(width), fl::Height(Widget.final_height)); + } + + if (!Widget.floating_x()) XAdvance += Widget.final_pad.left + Widget.final_pad.right + width; + + return ERR::Okay; +} + +//******************************************************************************************************************** +// Convert the layout information to a vector scene. This is the final step in the layout process. The advantage in +// performing this step separately to the layout process is that the graphics resources are managed last, which is +// sensible for keeping them out of the layout loop. +// +// It is intended that the layout process generates the document's entire scene graph every time. Optimisations +// relating to things like obscuration of graphics elements are considered to be the job of the VectorScene's drawing +// functionality. + +ERR layout::gen_scene_init(objVectorViewport *Viewport) +{ + pf::Log log(__FUNCTION__); + + log.branch(); + + // Remove former objects from the viewport + + for (auto it=Self->UIObjects.rbegin(); it != Self->UIObjects.rend(); it++) { + FreeResource(*it); + } + Self->UIObjects.clear(); + + m_cursor_drawn = false; + + Self->Links.clear(); + Self->VPToEntity.clear(); // NB: Widgets are cleared and re-added because they use direct pointers to the std::vector stream + + if (Self->UpdatingLayout) return ERR::NothingDone; // Drawing is disabled if the layout is being updated + + if (glFonts.empty()) { // Sanity check + log.traceWarning("Failed to load a default font."); + return ERR::Failed; + } + + #ifdef GUIDELINES // Make clip regions visible + for (unsigned i=0; i < m_clips.size(); i++) { + auto rect = objVectorRectangle::create::global({ + fl::Owner(Viewport->UID), + fl::X(m_clips[i].Clip.left), fl::Y(m_clips[i].Clip.top), + fl::Width(m_clips[i].Clip.right - m_clips[i].Clip.left), + fl::Height(m_clips[i].Clip.bottom - m_clips[i].Clip.top), + fl::Fill("rgb(255,200,200,64)") }); + } + #endif + + return ERR::Okay; +} + +void layout::gen_scene_graph(objVectorViewport *Viewport, std::vector &Segments) +{ + pf::Log log(__FUNCTION__); + + std::stack stack_list; + std::stack stack_row; + std::stack stack_para; + std::stack stack_table; + std::stack stack_ui_link; + std::stack stack_style; + std::stack stack_vp; + +#ifndef RETAIN_LOG_LEVEL + pf::LogLevel level(2); +#endif + +/* + stream_char select_start, select_end; + DOUBLE select_start_x, select_end_x; + + if ((Self->ActiveEditDef) and (!Self->SelectIndex.valid())) { + select_start = Self->CursorIndex; + select_end = Self->CursorIndex; + select_start_x = Self->CursorCharX; + select_end_x = Self->CursorCharX; + } + else if ((Self->CursorIndex.valid()) and (Self->SelectIndex.valid())) { + if (Self->SelectIndex < Self->CursorIndex) { + select_start = Self->SelectIndex; + select_end = Self->CursorIndex; + select_start_x = Self->SelectCharX; + select_end_x = Self->CursorCharX; + } + else { + select_start = Self->CursorIndex; + select_end = Self->SelectIndex; + select_start_x = Self->CursorCharX; + select_end_x = Self->SelectCharX; + } + } +*/ + for (SEGINDEX seg=0; seg < SEGINDEX(Segments.size()); seg++) { + auto &segment = Segments[seg]; + + if (!stack_ui_link.empty()) { + stack_ui_link.top().area = segment.area; + } + + // Highlighting of selected text + /* + if ((select_start <= segment.stop) and (select_end > segment.start)) { + if (select_start != select_end) { + alpha = 80.0/255.0; + if ((select_start > segment.start) and (select_start < segment.stop)) { + if (select_end < segment.stop) { + gfxDrawRectangle(Bitmap, segment.x + select_start_x, segment.y, + select_end_x - select_start_x, segment.height, Bitmap->packPixel(0, 128, 0), BAF::FILL); + } + else { + gfxDrawRectangle(Bitmap, segment.x + select_start_x, segment.y, + segment.width - select_start_x, segment.height, Bitmap->packPixel(0, 128, 0), BAF::FILL); + } + } + else if (select_end < segment.stop) { + gfxDrawRectangle(Bitmap, segment.x, segment.y, select_end_x, segment.height, + Bitmap->packPixel(0, 128, 0), BAF::FILL); + } + else { + gfxDrawRectangle(Bitmap, segment.x, segment.y, segment.width, segment.height, + Bitmap->packPixel(0, 128, 0), BAF::FILL); + } + alpha = 1.0; + } + } + */ + if ((Self->ActiveEditDef) and (Self->CursorState) and (!m_cursor_drawn)) { + if ((Self->CursorIndex >= segment.start) and (Self->CursorIndex <= segment.stop)) { + if ((Self->CursorIndex IS segment.stop) and + (Self->CursorIndex.get_prev_char_or_inline(segment.stream[0]) IS '\n')); + else if ((Self->Page->Flags & VF::HAS_FOCUS) != VF::NIL) { // Standard text cursor + std::vector seq = { + { .Type = PE::Move, .X = segment.area.X + Self->CursorCharX, .Y = segment.area.Y }, + { .Type = PE::VLineRel, .Y = segment.area.Height - segment.descent } + }; + + auto vp = objVectorPath::create::global({ + fl::Owner(Viewport->UID), fl::Stroke("rgb(255,0,0,255)"), fl::StrokeWidth(2) + }); + + vpSetCommand(vp, seq.size(), seq.data(), seq.size() * sizeof(PathCommand)); + m_cursor_drawn = true; + } + } + } + + auto x_advance = segment.area.X; + for (auto cursor = segment.start; cursor < segment.stop; cursor.next_code()) { + switch (segment.stream[0][cursor.index].code) { + case SCODE::FONT: + stack_style.push(&segment.stream->lookup(cursor)); + break; + + case SCODE::FONT_END: + stack_style.pop(); + break; + + case SCODE::LIST_START: + stack_list.push(&segment.stream->lookup(cursor)); + break; + + case SCODE::LIST_END: + stack_list.pop(); + break; + + case SCODE::PARAGRAPH_START: { + auto ¶ = segment.stream->lookup(cursor); + stack_para.push(¶); + + stack_style.push(&segment.stream->lookup(cursor).font); + auto font = stack_style.top()->get_font(); + + DOUBLE x = segment.x(x_advance, stack_style.top()->options); + DOUBLE y = segment.y(stack_style.top()->valign, font); + + if ((!stack_list.empty()) and (para.list_item)) { + // Handling for paragraphs that form part of a list + + if ((stack_list.top()->type IS bc_list::CUSTOM) or + (stack_list.top()->type IS bc_list::ORDERED)) { + if (!para.icon.empty()) { + para.icon->setFields( + fl::X(F2T(x - para.item_indent.px(*this))), + fl::Y(F2T(y)) + ); + } + } + else if (stack_list.top()->type IS bc_list::BULLET) { + if (!para.icon.empty()) { + const DOUBLE radius = segment.area.Height * 0.2; + const DOUBLE cy = y - (font->metrics.Ascent * 0.5); + + para.icon->setFields( + fl::CenterX(x - para.item_indent.px(*this) + radius), + fl::CenterY(cy), + fl::Radius(radius)); + } + } + } + break; + } + + case SCODE::PARAGRAPH_END: + stack_style.pop(); + stack_para.pop(); + break; + + case SCODE::TABLE_START: { + stack_table.push(&segment.stream->lookup(cursor)); + auto table = stack_table.top(); + + if (table->floating_x()); // If floating, X coordinate is calculated during layout + else { + // Otherwise the X coordinate is dependent on the style's alignment + // NB: Currently the TABLE code is defined as non-graphical and positioning is declared in the + // table structure, not the segment.area. + if ((stack_style.top()->options & FSO::ALIGN_CENTER) != FSO::NIL) table->x = table->x + ((segment.align_width - segment.area.Width) * 0.5); + else if ((stack_style.top()->options & FSO::ALIGN_RIGHT) != FSO::NIL) table->x = table->x + segment.align_width - segment.area.Width; + } + + stack_vp.push(Viewport); + if (!(Viewport = *table->viewport)) return; + + Viewport->setFields(fl::X(table->x), fl::Y(table->y), fl::Width(table->width), fl::Height(table->height)); + + // To build sophisticated table grids, we allocate a single VectorPath that + // the table, rows and cells contribute to. This ensures efficiency and consistency + // in the final result. + + if ((!table->fill.empty()) or (!table->stroke.empty())) { + table->seq.push_back({ .Type = PE::Move, .X = 0, .Y = 0 }); + table->seq.push_back({ .Type = PE::HLineRel, .X = table->width, }); + table->seq.push_back({ .Type = PE::VLineRel, .Y = table->height }); + table->seq.push_back({ .Type = PE::HLineRel, .X = -table->width, }); + table->seq.push_back({ .Type = PE::ClosePath }); + } + break; + } + + case SCODE::TABLE_END: { + auto &table = stack_table.top(); + vpSetCommand(*table->path, table->seq.size(), table->seq.data(), + table->seq.size() * sizeof(PathCommand)); + table->seq.clear(); + + Viewport = stack_vp.top(); + stack_vp.pop(); + + stack_table.pop(); + break; + } + + case SCODE::ROW: { + stack_row.push(&segment.stream->lookup(cursor)); + auto row = stack_row.top(); + if (!row->rect_fill.empty()) { + row->rect_fill->setFields(fl::X(0), + fl::Y(row->y - stack_table.top()->y), + fl::Width(stack_table.top()->width), + fl::Height(row->row_height)); + } + break; + } + + case SCODE::ROW_END: + stack_row.pop(); + break; + + case SCODE::CELL: { + // If a cell defines fill/stroke values then it gets an independent rectangle to achieve that. + // + // If it defines a border then it can instead make use of the table's VectorPath object, which is + // more efficient and creates consistent looking output. + + auto &cell = segment.stream->lookup(cursor); + auto table = stack_table.top(); + + if ((!cell.fill.empty()) or (!cell.stroke.empty())) { + if (!cell.stroke.empty()) { + cell.rect_fill->setFields(fl::Stroke(cell.stroke), fl::StrokeWidth(cell.stroke_width.px(*this))); + } + if (!cell.fill.empty()) cell.rect_fill->setFields(fl::Fill(cell.fill)); + } + else if (!cell.rect_fill.empty()) cell.rect_fill->setFields(fl::Fill(NULL), fl::Stroke(NULL)); + + if ((cell.width >= 1) and (cell.height >= 1)) { + cell.viewport->setFields(fl::X(cell.x), fl::Y(cell.y), + fl::Width(cell.width), fl::Height(cell.height)); + + if ((cell.border != CB::NIL) and (cell.stroke.empty())) { + // When a cell defines a border value, it piggy-backs the table's stroke definition + if (cell.border IS CB::ALL) { + table->seq.push_back({ .Type = PE::Move, .X = cell.x, .Y = cell.y }); + table->seq.push_back({ .Type = PE::HLineRel, .X = cell.width }); + table->seq.push_back({ .Type = PE::VLineRel, .Y = cell.height }); + table->seq.push_back({ .Type = PE::HLineRel, .X = -cell.width }); + table->seq.push_back({ .Type = PE::ClosePath }); + } + else { + if ((cell.border & CB::LEFT) != CB::NIL) { + table->seq.push_back({ .Type = PE::Move, .X = cell.x, .Y = cell.y }); + table->seq.push_back({ .Type = PE::VLineRel, .Y = cell.height }); + table->seq.push_back({ .Type = PE::ClosePath }); + } + + if ((cell.border & CB::TOP) != CB::NIL) { + table->seq.push_back({ .Type = PE::Move, .X = cell.x, .Y = cell.y }); + table->seq.push_back({ .Type = PE::HLineRel, .X = cell.width }); + table->seq.push_back({ .Type = PE::ClosePath }); + } + + if ((cell.border & CB::RIGHT) != CB::NIL) { + table->seq.push_back({ .Type = PE::Move, .X = cell.x + cell.width, .Y = cell.y }); + table->seq.push_back({ .Type = PE::VLineRel, .Y = cell.height }); + table->seq.push_back({ .Type = PE::ClosePath }); + } + + if ((cell.border & CB::BOTTOM) != CB::NIL) { + table->seq.push_back({ .Type = PE::Move, .X = cell.x, .Y = cell.y + cell.height }); + table->seq.push_back({ .Type = PE::HLineRel, .X = cell.width }); + table->seq.push_back({ .Type = PE::ClosePath }); + } + } + } + + gen_scene_graph(*cell.viewport, cell.segments); + + Self->VPToEntity.emplace(cell.viewport.id, vp_to_entity { &cell }); + } + + break; + } + + case SCODE::LINK: { + auto link = &segment.stream->lookup(cursor); + + stack_ui_link.push(ui_link { + .origin = *link, + .area = { x_advance, segment.area.Y, segment.area.Width - x_advance, segment.area.Height }, + .cursor_start = cursor, + .stream = segment.stream + }); + + // Font management + + link->font.fill = link->fill; // Reset the fill instruction to the default + stack_style.push(&link->font); + if (Self->HasFocus) { + // Override the default link colour if the link has the tab key's focus + if ((Self->Tabs[Self->FocusIndex].type IS TT::LINK) and + (std::get(Self->Tabs[Self->FocusIndex].ref) IS link->uid) and + (Self->Tabs[Self->FocusIndex].active)) { + link->font.fill = Self->LinkSelectFill; + } + else if (stack_ui_link.top().hover) { + link->font.fill = Self->LinkSelectFill; + } + } + + break; + } + + case SCODE::LINK_END: { + auto &ui_link = stack_ui_link.top(); + ui_link.cursor_end = cursor; + ui_link.area.Width = x_advance - ui_link.area.X; + if (ui_link.area.Width >= 1) ui_link.append_link(); + + // Define the path that represents the clickable area. + + vpSetCommand(*ui_link.origin.path, ui_link.path.size(), ui_link.path.data(), + ui_link.path.size() * sizeof(PathCommand)); + + acMoveToFront(*ui_link.origin.path); + + ui_link.path.clear(); // Return the memory + + Self->Links.emplace_back(ui_link); + + stack_ui_link.pop(); + stack_style.pop(); + break; + } + + case SCODE::BUTTON: { + auto &button = segment.stream->lookup(cursor); + + gen_scene_graph(*button.viewport, button.segments); + + DOUBLE wx, wy; + if (position_widget(button, segment, Viewport, stack_style.top(), x_advance, 0, true, wx, wy) IS ERR::Okay) { + Self->VPToEntity.emplace(button.viewport.id, vp_to_entity { &button }); + } + break; + } + + case SCODE::CHECKBOX: { + auto &checkbox = segment.stream->lookup(cursor); + + DOUBLE wx, wy; + if (!checkbox.label.empty()) { + if (checkbox.label_pos) { + // Right-sided labels can be integrated with the widget so that clicking affects state. + if (position_widget(checkbox, segment, Viewport, stack_style.top(), x_advance, checkbox.label_width + checkbox.label_pad, true, wx, wy) IS ERR::Okay) { + DOUBLE x, y; + auto font = stack_style.top()->get_font(); + const DOUBLE avail_space = checkbox.final_height - font->metrics.Descent; + y = avail_space - ((avail_space - font->metrics.Height) * 0.5); + + x = checkbox.final_width + checkbox.label_pad; + + if (checkbox.label_text.empty()) { + checkbox.label_text.set(objVectorText::create::global({ + fl::Name("checkbox_label"), + fl::Owner(checkbox.viewport->UID), + fl::String(checkbox.label), + fl::Face(font->face), + fl::FontSize(font->font_size), + fl::FontStyle(font->style), + fl::Fill(stack_style.top()->fill) + })); + } + + if (!checkbox.label_text.empty()) { + checkbox.label_text->setFields(fl::X(F2T(x)), fl::Y(F2T(y))); + } + } + } + else { + // Left-sided labels aren't included in the scope of the widget's viewport + // TODO: Interactivity is feasible but we'll need to add an input feedback mechanism for that + auto font = stack_style.top()->get_font(); + auto x_label = x_advance; + x_advance += checkbox.label_width + checkbox.label_pos; + if (position_widget(checkbox, segment, Viewport, stack_style.top(), x_advance, 0, true, wx, wy) IS ERR::Okay) { + const DOUBLE avail_space = checkbox.final_height - font->metrics.Descent; + DOUBLE y = wy + avail_space - ((avail_space - font->metrics.Height) * 0.5); + + if (checkbox.label_text.empty()) { + checkbox.label_text.set(objVectorText::create::global({ + fl::Name("checkbox_label"), + fl::Owner(Viewport->UID), + fl::String(checkbox.label), + fl::Face(font->face), + fl::FontSize(font->font_size), + fl::FontStyle(font->style), + fl::Fill(stack_style.top()->fill) + })); + } + + if (!checkbox.label_text.empty()) { + checkbox.label_text->setFields(fl::X(F2T(x_label)), fl::Y(F2T(y))); + } + } + } + } + else position_widget(checkbox, segment, Viewport, stack_style.top(), x_advance, 0, true, wx, wy); + + if (!checkbox.processed) { + checkbox.processed = true; + if ((!checkbox.viewport.empty()) and (checkbox.viewport->Scene->SurfaceID)) { + vecSubscribeInput(*checkbox.viewport, JTYPE::BUTTON|JTYPE::CROSSING, FUNCTION(inputevent_checkbox)); + } + } + + if (!checkbox.viewport.empty()) Self->VPToEntity.emplace(checkbox.viewport.id, vp_to_entity { &checkbox }); + break; + } + + case SCODE::COMBOBOX: { + auto &combo = segment.stream->lookup(cursor); + auto font = stack_style.top()->get_font(); + + DOUBLE wx, wy; + const DOUBLE avail_space = combo.final_height - font->metrics.Descent; + + if (!combo.label.empty()) { + if (combo.label_pos) { + position_widget(combo, segment, Viewport, stack_style.top(), x_advance, 0, true, wx, wy); + + DOUBLE y = wy + avail_space - ((avail_space - font->metrics.Height) * 0.5); + + if (combo.label_text.empty()) { + combo.label_text = objVectorText::create::global({ + fl::Name("combo_label"), + fl::Owner(Viewport->UID), + fl::String(combo.label), + fl::Face(font->face), + fl::FontSize(font->font_size), + fl::FontStyle(font->style), + fl::Fill(stack_style.top()->fill) + }); + } + + combo.label_text->setFields(fl::X(F2T(x_advance + combo.label_pad)), fl::Y(F2T(y))); + + x_advance += combo.label_width + combo.label_pad; + } + else { + auto x_label = x_advance; + x_advance += combo.label_pad + combo.label_width; + + position_widget(combo, segment, Viewport, stack_style.top(), x_advance, 0, true, wx, wy); + + DOUBLE y = wy + avail_space - ((avail_space - font->metrics.Height) * 0.5); + + if (combo.label_text.empty()) { + combo.label_text = objVectorText::create::global({ + fl::Name("combo_label"), + fl::Owner(Viewport->UID), + fl::String(combo.label), + fl::Face(font->face), + fl::FontSize(font->font_size), + fl::FontStyle(font->style), + fl::Fill(stack_style.top()->fill) + }); + } + + combo.label_text->setFields(fl::X(F2T(x_label)), fl::Y(F2T(y))); + } + } + else position_widget(combo, segment, Viewport, stack_style.top(), x_advance, 0, true, wx, wy); + + if (combo.clip_vp.empty()) { + // Create the button that will control the drop-down list + + objVectorViewport::create::global({ + fl::Name("vp_combo_button"), + fl::Owner(combo.viewport->UID), + fl::Y(0), fl::XOffset(0), fl::YOffset(0), + fl::Width(combo.full_height()) // Button width matches the widget height + }); + + vecSubscribeInput(*combo.viewport, JTYPE::BUTTON|JTYPE::CROSSING, FUNCTION(inputevent_dropdown)); + + vecSubscribeFeedback(*combo.viewport, FM::HAS_FOCUS|FM::CHILD_HAS_FOCUS|FM::LOST_FOCUS, FUNCTION(combo_feedback)); + + combo.clip_vp = objVectorViewport::create::global({ + fl::Name("vp_clip_combo"), + fl::Owner(combo.viewport->UID), + fl::Overflow(VOF::HIDDEN) + }); + + DOUBLE y = avail_space - ((avail_space - font->metrics.Height) * 0.5); + + combo.input = objVectorText::create::global({ + fl::Name("combo_input"), + fl::Owner(combo.clip_vp->UID), + fl::X(0), fl::Y(F2T(y)), + fl::String(combo.value), + fl::Cursor(PTC::TEXT), + fl::Face(font->face), + fl::FontSize(font->font_size), + fl::FontStyle(font->style), + fl::Fill(combo.font_fill), + fl::LineLimit(1), + fl::TextFlags(VTXF::EDITABLE) + }); + } + + if (!combo.clip_vp.empty()) { + combo.clip_vp->setFields(fl::X(combo.label_pad * 0.75), fl::Y(0), + fl::XOffset(combo.label_pad + (combo.final_height * 0.75)), fl::YOffset(0)); + } + + combo.menu.define_font(font); + combo.menu.m_ref = &combo; + combo.menu.m_style = combo.style; + + Self->VPToEntity.emplace(combo.viewport.id, vp_to_entity { &combo }); + break; + } + + case SCODE::IMAGE: { + auto &img = segment.stream->lookup(cursor); + DOUBLE wx, wy; + position_widget(img, segment, Viewport, stack_style.top(), x_advance, 0, false, wx, wy); + break; + } + + case SCODE::INPUT: { + auto &input = segment.stream->lookup(cursor); + auto font = stack_style.top()->get_font(); + + DOUBLE wx, wy; + const DOUBLE avail_space = input.final_height - font->metrics.Descent; + + if (!input.label.empty()) { + if (input.label_pos) { + position_widget(input, segment, Viewport, stack_style.top(), x_advance, 0, true, wx, wy); + + DOUBLE y = wy + avail_space - ((avail_space - font->metrics.Height) * 0.5); + + if (input.label_text.empty()) { + input.label_text = objVectorText::create::global({ + fl::Name("input_label"), + fl::Owner(Viewport->UID), + fl::String(input.label), + fl::Face(font->face), + fl::FontSize(font->font_size), + fl::FontStyle(font->style), + fl::Fill(stack_style.top()->fill) + }); + } + + input.label_text->setFields(fl::X(F2T(x_advance + input.label_pad)), fl::Y(F2T(y))); + + x_advance += input.label_width + input.label_pad; + } + else { + auto x_label = x_advance; + x_advance += input.label_pad + input.label_width; + + position_widget(input, segment, Viewport, stack_style.top(), x_advance, 0, true, wx, wy); + + DOUBLE y = wy + avail_space - ((avail_space - font->metrics.Height) * 0.5); + + if (input.label_text.empty()) { + input.label_text = objVectorText::create::global({ + fl::Name("input_label"), + fl::Owner(Viewport->UID), + fl::String(input.label), + fl::Face(font->face), + fl::FontSize(font->font_size), + fl::FontStyle(font->style), + fl::Fill(stack_style.top()->fill) + }); + } + + input.label_text->setFields(fl::X(F2T(x_label)), fl::Y(F2T(y))); + } + } + else position_widget(input, segment, Viewport, stack_style.top(), x_advance, 0, true, wx, wy); + + if (input.clip_vp.empty()) { + input.clip_vp = objVectorViewport::create::global({ + fl::Name("vp_clip_input"), + fl::Owner(input.viewport->UID), + fl::Overflow(VOF::HIDDEN) + }); + + auto flags = VTXF::EDITABLE; + if (input.secret) flags |= VTXF::SECRET; + + DOUBLE y = avail_space - ((avail_space - font->metrics.Height) * 0.5); + + objVectorText::create::global({ + fl::Name("input_text"), + fl::Owner(input.clip_vp->UID), + fl::X(0), fl::Y(F2T(y)), + fl::String(input.value), + fl::Cursor(PTC::TEXT), + fl::Face(font->face), + fl::FontSize(font->font_size), + fl::FontStyle(font->style), + fl::Fill(input.font_fill), + fl::LineLimit(1), + fl::TextFlags(flags) + }); + } + + if (!input.clip_vp.empty()) { + input.clip_vp->setFields(fl::X(input.label_pad), fl::Y(0), fl::XOffset(input.label_pad), fl::YOffset(0)); + } + + break; + } + + case SCODE::TEXT: { + auto &txt = segment.stream->lookup(cursor); + auto font = stack_style.top()->get_font(); + + std::string str; + if (cursor.index < segment.trim_stop.index) str.append(txt.text, cursor.offset, std::string::npos); + else str.append(txt.text, cursor.offset, segment.trim_stop.offset - cursor.offset); + + if (!str.empty()) { + DOUBLE x = segment.x(x_advance, stack_style.top()->options); + DOUBLE y = segment.y(stack_style.top()->valign, font); + + if (auto vt = objVectorText::create::global({ + fl::Name("doc_text"), + fl::Owner(Viewport->UID), + fl::X(F2T(x)), fl::Y(F2T(y)), + fl::String(str), + fl::Cursor(PTC::TEXT), + fl::Face(font->face), + fl::FontSize(font->font_size), + fl::FontStyle(font->style), + fl::Fill(stack_style.top()->fill), + fl::TextFlags(((stack_style.top()->options & FSO::UNDERLINE) != FSO::NIL) ? VTXF::UNDERLINE : VTXF::NIL) + })) { + + Self->UIObjects.push_back(vt->UID); + + txt.vector_text.push_back(vt); + + DOUBLE twidth; + vt->get(FID_TextWidth, &twidth); + x_advance += twidth; + } + } + break; + } + + default: break; + } // switch() + } // for cursor + + if (!stack_ui_link.empty()) { + auto &link = stack_ui_link.top(); + link.area.Width = x_advance - link.area.X; + if (link.area.Width >= 1) link.append_link(); + } + + } // for segment +} diff --git a/src/document/dunit.cpp b/src/document/dunit.cpp new file mode 100644 index 000000000..1c66bd927 --- /dev/null +++ b/src/document/dunit.cpp @@ -0,0 +1,70 @@ + +DUNIT::DUNIT(const std::string_view pValue, DU pDefaultType, DOUBLE pMin) +{ + const DOUBLE dpi = 96.0; // TODO: Needs to be derived from the display + std::size_t i = 0; + while ((i < pValue.size()) and (unsigned(pValue[i]) <= 0x20)) i++; + + DOUBLE fv; + auto [ ptr, error ] = std::from_chars(pValue.data() + i, pValue.data() + pValue.size(), fv); + + if (error IS std::errc()) { + if (ptr IS pValue.data() + pValue.size()) { value = fv; type = pDefaultType; } + else if (ptr[0] IS '%') { value = fv * 0.01; type = DU::SCALED; } + else if (ptr+2 <= pValue.data() + pValue.size()) { + if ((ptr[0] IS 'p') and (ptr[1] IS 'x')) { value = fv; type = DU::PIXEL; } + else if ((ptr[0] IS 'e') and (ptr[1] IS 'm')) { value = fv; type = DU::FONT_SIZE; } + else if ((ptr[0] IS 'e') and (ptr[1] IS 'x')) { value = fv * 2.0; type = DU::FONT_SIZE; } + else if ((ptr[0] IS 'i') and (ptr[1] IS 'n')) { value = fv * dpi; type = DU::PIXEL; } // Inches -> Pixels + else if ((ptr[0] IS 'c') and (ptr[1] IS 'm')) { value = fv * (1.0 / 2.56) * dpi; type = DU::PIXEL; } // Centimetres -> Pixels + else if ((ptr[0] IS 'm') and (ptr[1] IS 'm')) { value = fv * (1.0 / 20.56) * dpi; type = DU::PIXEL; } // Millimetres -> Pixels + else if ((ptr[0] IS 'p') and (ptr[1] IS 't')) { value = fv * (4.0 / 3.0); type = DU::PIXEL; } // Points -> Pixels. A point is 4/3 of a pixel + else if ((ptr[0] IS 'p') and (ptr[1] IS 'c')) { value = fv * (4.0 / 3.0) * 12.0; type = DU::PIXEL; } // Pica -> Pixels. 1 Pica is equal to 12 Points + else { value = fv; type = pDefaultType; } + } + else { value = fv; type = pDefaultType; } + } + else value = 0; + + if (value < pMin) value = pMin; +} + +//******************************************************************************************************************** +// Return values are truncated because true floating point values can lead to subtle computational bugs that aren't +// worth the time of investigation. + +DOUBLE DUNIT::px(class layout &Layout) { + switch (type) { + case DU::PIXEL: return value; + // Using the true font-size in the Height value gives a more consistent result vs the client's + // requested 'font-size' (which guarantees nothing as to what is returned by Freetype). + case DU::FONT_SIZE: return std::trunc(value * Layout.m_font->metrics.Height); //Layout.m_font->font_size * 72.0 / 96.0); + case DU::TRUE_LINE_HEIGHT: return std::trunc(value * Layout.m_line.height); + case DU::LINE_HEIGHT: return std::trunc(value * Layout.m_font->metrics.LineSpacing); + case DU::CHAR: return std::trunc(value * DOUBLE(vecCharWidth(Layout.m_font->handle, '0', 0, NULL))); // Equivalent to CSS + case DU::VP_WIDTH: return std::trunc(value * Layout.m_viewport->Parent->get(FID_Width) * 0.01); + case DU::VP_HEIGHT: return std::trunc(value * Layout.m_viewport->Parent->get(FID_Height) * 0.01); + case DU::ROOT_FONT_SIZE: return std::trunc(value * Layout.Self->FontSize); // Measured in 72DPI pixels + case DU::ROOT_LINE_HEIGHT: return std::trunc(value * (Layout.Self->FontSize * 1.3)); // Guesstimate + + case DU::VP_MIN: { + auto w = std::trunc(value * Layout.m_viewport->Parent->get(FID_Width) * 0.01); + auto h = std::trunc(value * Layout.m_viewport->Parent->get(FID_Height) * 0.01); + return std::min(w, h); + } + + case DU::VP_MAX: { + auto w = std::trunc(value * Layout.m_viewport->Parent->get(FID_Width) * 0.01); + auto h = std::trunc(value * Layout.m_viewport->Parent->get(FID_Height) * 0.01); + return std::max(w, h); + } + + case DU::SCALED: // wrap_edge equates to m_page_width - m_margins.right; + return std::trunc(value * 0.01 * (Layout.wrap_edge() - Layout.m_cursor_x)); + //return value * 0.01 * (Layout.wrap_edge() - m_margins.left); + + default: return 0; + } + + return 0; +} diff --git a/src/document/entities.cpp b/src/document/entities.cpp new file mode 100644 index 000000000..cd19439fc --- /dev/null +++ b/src/document/entities.cpp @@ -0,0 +1,18 @@ + +void bc_cell::set_fill(const std::string Fill) +{ + if (rect_fill.empty()) { + auto rect = objVectorRectangle::create::global({ + fl::Name("cell_rect"), + fl::Owner(viewport->UID), + fl::X(0), fl::Y(0), fl::Width(SCALE(1.0)), fl::Height(SCALE(1.0)), + fl::Fill(Fill) + }); + + if (rect) { + rect_fill.set(rect); + rect_fill->moveToBack(); + } + } + else rect_fill->set(FID_Fill, Fill); +} diff --git a/src/document/functions.cpp b/src/document/functions.cpp index d339f9f69..ee2eee9c1 100644 --- a/src/document/functions.cpp +++ b/src/document/functions.cpp @@ -1,377 +1,15 @@ -#define MAXLOOP 100000 - -// This is a list of the default class types that may be used in document pages. Its purpose is to restrict the types -// of objects that can be used so that we don't run into major security problems. Basically, if an instantiated -// object could have the potential to run any program that the user has access to, or if it could gain access to local -// information and use it for nefarious purposes, then it's not secure enough for document usage. -// -// TODO: NEEDS TO BE REPLACED WITH AN XML DEFINITION and PARSED INTO A KEY VALUE STORE. - -static const struct { - CSTRING ClassName; - CLASSID ClassID; - CSTRING PageTarget; - CSTRING Fields; -} glDocClasses[] = { - // GUI - { "vector", ID_VECTOR, "surface", "" }, - { "document", ID_DOCUMENT, "surface", "" }, - // TOOLS - { "scintilla", ID_SCINTILLA, NULL, "" }, - // NETWORK - { "http", ID_HTTP, NULL, "" }, - // DATA - { "config", ID_CONFIG, NULL, "" }, - { "xml", ID_XML, NULL, "" } -}; +static const LONG MAXLOOP = 1000; static const char glDefaultStyles[] = -"

    \n\ -\n\ -\n\ -\n\ -\n\ -\n"; - -#if defined(DEBUG) || defined(DBG_LAYOUT) -static char glPrintable[80]; - -static STRING printable(CSTRING String, LONG Length) __attribute__ ((unused)); - -static STRING printable(CSTRING String, LONG Length) -{ - LONG i = 0, j = 0; - while ((String[i]) and (i < Length) and (j < ARRAYSIZE(glPrintable)-1)) { - if (String[i] IS CTRL_CODE) { - glPrintable[j++] = '%'; - i += ESCAPE_LEN(String+i); - } - else if (String[i] < 0x20) { - glPrintable[j++] = '?'; - i++; - } - else glPrintable[j++] = String[i++]; - } - glPrintable[j] = 0; - return glPrintable; -} - -static char glPrintable2[80]; - -static STRING printable2(CSTRING String, LONG Length) __attribute__ ((unused)); - -static STRING printable2(CSTRING String, LONG Length) -{ - LONG i = 0, j = 0; - while ((String[i]) and (i < Length) and (j < ARRAYSIZE(glPrintable2)-1)) { - if (String[i] IS CTRL_CODE) { - glPrintable2[j++] = '%'; - i += ESCAPE_LEN(String+i); - } - else if (String[i] < 0x20) { - glPrintable[j++] = '?'; - i++; - } - else glPrintable2[j++] = String[i++]; - } - glPrintable2[j] = 0; - return glPrintable2; -} - -static void print_xmltree(XMLTag *Tag, LONG *Indent) -{ - pf::Log log(__FUNCTION__); - XMLTag *child; - LONG i, j; - char buffer[1000]; - - if (!Indent) { - i = 0; - while (Tag) { - print_xmltree(Tag, &i); - Tag=Tag->Next; - } - return; - } - - if (!Tag->Attrib) { - log.warning("Error - no Attrib in tag %d", Tag->Index); - return; - } - - for (i=0; i < *Indent; i++) buffer[i] = ' '; - - if (Tag->Attrib->Name) { - for (j=0; Tag->Attrib->Name[j]; j++) buffer[i++] = Tag->Attrib->Name[j]; - } - else { - // Extract up to 20 characters of content - buffer[i++] = '['; - for (j=0; (Tag->Attrib->Value[j]) and (j < 20); j++) buffer[i++] = Tag->Attrib->Value[j]; - buffer[i++] = ']'; - } - buffer[i] = 0; - - log.msg("%s", buffer); - - Indent[0]++; - for (child=Tag->Child; child; child=child->Next) { - print_xmltree(child, Indent); - } - Indent[0]--; -} -#endif - -#ifdef DBG_STREAM - -#include -#include -#undef NULL -#define NULL 0 - -static void print_stream(extDocument *Self, STRING Stream) -{ - STRING str; - escFont *style; - LONG i, len, code; - BYTE printpos; - - if ((!(str = Stream)) or (!str[0])) return; - - fprintf(stderr, "\nSTREAM: %d bytes\n------\n", Self->StreamLen); - i = 0; - printpos = FALSE; - while (str[i]) { - if (str[i] IS CTRL_CODE) { - code = ESCAPE_CODE(str, i); - fprintf(stderr, "(%d)", i); - len = ESCAPE_LEN(str+i); - if (len < ESC_LEN) { - fprintf(stderr, "\nInvalid escape code length of %d at index %d. Code: %d\n", len, i, code); - break; - } - if (code IS ESC_FONT) { - style = escape_data(str, i); - fprintf(stderr, "[E:Font:%d:%d", len, style->Index); - if (style->Options & FSO_ALIGN_RIGHT) fprintf(stderr, ":A/R"); - if (style->Options & FSO_ALIGN_CENTER) fprintf(stderr, ":A/C"); - if (style->Options & FSO_BOLD) fprintf(stderr, ":Bold"); - fprintf(stderr, ":#%.2x%.2x%.2x%.2x", style->Colour.Red, style->Colour.Green, style->Colour.Blue, style->Colour.Alpha); - fprintf(stderr, "]"); - } - else if (code IS ESC_PARAGRAPH_START) { - auto para = escape_data(str, i); - if (para->ListItem) fprintf(stderr, "[E:LI]"); - else fprintf(stderr, "[E:PS]"); - } - else if (code IS ESC_PARAGRAPH_END) { - fprintf(stderr, "[E:PE]\n"); - } -/* - else if (ESCAPE_CODE(str, i) IS ESC_LIST_ITEM) { - auto item = escape_data(str, i); - fprintf(stderr, "[I:X(%d):Width(%d):Custom(%d)]", item->X, item->Width, item->CustomWidth); - } -*/ - else if (code < ARRAYSIZE(strCodes)) { - fprintf(stderr, "[E:%s:%d]", strCodes[code], len); - } - else fprintf(stderr, "[E:%d:%d]", code, len); - i += len; - printpos = TRUE; - } - else { - if (printpos) { - printpos = FALSE; - fprintf(stderr, "(%d)", i); - } - if ((str[i] <= 0x20) or (str[i] > 127)) fprintf(stderr, "."); - else fprintf(stderr, "%c", str[i]); - i++; - } - } - - fprintf(stderr, "\nActive Edit: %d, Cursor Index: %d / X: %d, Select Index: %d\n", Self->ActiveEditCellID, Self->CursorIndex, Self->CursorCharX, Self->SelectIndex); -} - -#endif - -#ifdef DBG_LINES - -#include -#include -#undef NULL -#define NULL 0 - -static void print_lines(extDocument *Self) -{ - fprintf(stderr, "\nSEGMENTS\n--------\n"); - - STRING str = Self->Stream; - for (LONG row=0; row < Self->SegCount; row++) { - DocSegment *line = Self->Segments + row; - LONG i = line->Index; - - fprintf(stderr, "Seg %d, Bytes %d-%d: %dx%d,%dx%d: ", row, line->Index, line->Stop, line->X, line->Y, line->Width, line->Height); - if (line->Edit) fprintf(stderr, "{ "); - fprintf(stderr, "\""); - while (i < line->Stop) { - if (str[i] IS CTRL_CODE) { - if (ESCAPE_CODE(str, i) IS ESC_FONT) { - auto style = escape_data(str, i); - fprintf(stderr, "[E:Font:%d:%d:$%.2x%.2x%.2x", ESCAPE_LEN(str+i), style->Index, style->Colour.Red, style->Colour.Green, style->Colour.Blue); - fprintf(stderr, "]"); - } - else if (ESCAPE_CODE(str, i) IS ESC_PARAGRAPH_START) { - para = escape_data(str, i); - if (para->ListItem) fprintf(stderr, "[E:LI]"); - else fprintf(stderr, "[E:PS]"); - } - else if (ESCAPE_CODE(str, i) IS ESC_PARAGRAPH_END) { - fprintf(stderr, "[E:PE]\n"); - } - else if (ESCAPE_CODE(str, i) IS ESC_OBJECT) { - auto obj = escape_data(str, i); - fprintf(stderr, "[E:OBJ:%d]", obj->ObjectID); - } - else if (ESCAPE_CODE(str, i) < ARRAYSIZE(strCodes)) { - fprintf(stderr, "[E:%s:%d]", strCodes[(UBYTE)ESCAPE_CODE(str, i)], ESCAPE_LEN(str+i)); - } - else fprintf(stderr, "[E:%d:%d]", ESCAPE_CODE(str, i), ESCAPE_LEN(str+i)); - i += ESCAPE_LEN(str+i); - } - else { - if ((str[i] <= 0x20) or (str[i] > 127)) fprintf(stderr, "."); - else fprintf(stderr, "%c", str[i]); - i++; - } - } - - fprintf(stderr, "\""); - if (line->Edit) fprintf(stderr, " }"); - fprintf(stderr, "\n"); - } -} - -static void print_sorted_lines(extDocument *Self) -{ - fprintf(stderr, "\nSORTED SEGMENTS\n---------------\n"); - - STRING str = Self->Stream; - for (LONG row=0; row < Self->SortCount; row++) { - DocSegment *line = Self->Segments + Self->SortSegments[row].Segment; - fprintf(stderr, "%d: Y: %d-%d, Seg: %d \"", row, Self->SortSegments[row].Y, Self->Segments[Self->SortSegments[row].Segment].X, Self->SortSegments[row].Segment); - - LONG i = line->Index; - while (i < line->Stop) { - if (str[i] IS CTRL_CODE) { - if (ESCAPE_CODE(str, i) IS ESC_FONT) { - auto style = escape_data(str, i); - fprintf(stderr, "[E:Font:%d:%d:$%.2x%.2x%.2x", ESCAPE_LEN(str+i), style->Index, style->Colour.Red, style->Colour.Green, style->Colour.Blue); - fprintf(stderr, "]"); - } - else if (ESCAPE_CODE(str, i) IS ESC_PARAGRAPH_START) { - para = escape_data(str, i); - if (para->ListItem) fprintf(stderr, "[E:LI]"); - else fprintf(stderr, "[E:PS]"); - } - else if (ESCAPE_CODE(str, i) IS ESC_PARAGRAPH_END) { - fprintf(stderr, "[E:PE]\n"); - } - else if (ESCAPE_CODE(str, i) IS ESC_OBJECT) { - obj = escape_data(str, i); - fprintf(stderr, "[E:OBJ:%d]", obj->ObjectID); - } - else if (ESCAPE_CODE(str, i) < ARRAYSIZE(strCodes)) { - fprintf(stderr, "[E:%s:%d]", strCodes[(UBYTE)ESCAPE_CODE(str, i)], ESCAPE_LEN(str+i)); - } - else fprintf(stderr, "[E:%d:%d]", ESCAPE_CODE(str, i), ESCAPE_LEN(str+i)); - i += ESCAPE_LEN(str+i); - } - else { - if ((str[i] <= 0x20) or (str[i] > 127)) fprintf(stderr, "."); - else fprintf(stderr, "%c", str[i]); - i++; - } - } - - fprintf(stderr, "\"\n"); - } -} - -static void print_tabfocus(extDocument *Self) -{ - if (Self->TabIndex) { - fprintf(stderr, "\nTAB FOCUSLIST\n-------------\n"); - - for (LONG i=0; i < Self->TabIndex; i++) { - fprintf(stderr, "%d: Type: %d, Ref: %d, XRef: %d\n", i, Self->Tabs[i].Type, Self->Tabs[i].Ref, Self->Tabs[i].XRef); - } - } -} - -#endif +"\n\ +\n\ +\n\ +\n\ +\n\ +\n"; -//static BYTE glWhitespace = TRUE; // Setting this to TRUE tells the parser to ignore whitespace (prevents whitespace being used as content) - -// RESET_SEGMENT: Resets the string management variables, usually done when a string -// has been broken up on the current line due to an object or table graphic for example. - -#define RESET_SEGMENT(index,x,l) \ - (l)->line_index = (index); \ - (l)->line_x = (x); \ - (l)->kernchar = 0; \ - (l)->textcontent = 0; - -#define RESET_SEGMENT_WORD(index,x,l) \ - (l)->line_index = (index); \ - (l)->line_x = (x); \ - (l)->kernchar = 0; \ - (l)->wordindex = -1; \ - (l)->wordwidth = 0; \ - (l)->textcontent = 0; - -struct layout { - objFont *font; - escLink *link; - LONG alignwidth; - LONG base_line; // The complete height of the line, covers the height of all objects and tables anchored to the line. Text is drawn so that the text gutter is aligned to the base line - LONG line_height; // Height of the line with respect to the text - LONG paragraph_end; - LONG cursorx, cursory; - LONG line_index; - LONG line_x; - LONG left_margin; - LONG link_x; - LONG link_index; - LONG link_align; - LONG kernchar; - LONG right_margin; - LONG split_start; - LONG start_clips; - LONG wrapedge; - LONG wordindex; - LONG wordwidth; - LONG line_increase; - LONG paragraph_y; - LONG alignflags; - WORD spacewidth; - WORD len; - UBYTE anchor; - UBYTE nowrap:1; - UBYTE link_open:1; - UBYTE setsegment:1; - UBYTE textcontent:1; -}; - -enum { - WRAP_DONOTHING=0, - WRAP_EXTENDPAGE, - WRAP_WRAPPED -}; - -static Field * find_field(OBJECTPTR Object, CSTRING Name, OBJECTPTR *Source) // Read-only, thread safe function. +static const Field * find_field(OBJECTPTR Object, CSTRING Name, OBJECTPTR *Source) // Read-only, thread safe function. { // Skip any special characters that are leading the field name (e.g. $, @). Some symbols like / are used for XPath // lookups, so we only want to skip reserved symbols or we risk confusion between real fields and variable fields. @@ -382,65 +20,52 @@ static Field * find_field(OBJECTPTR Object, CSTRING Name, OBJECTPTR *Source) // else break; } - return FindField(Object, StrHash(Name, FALSE), Source); + return FindField(Object, StrHash(Name, false), Source); } -static void check_clips(extDocument *Self, LONG Index, layout *l, - LONG ObjectIndex, LONG *ObjectX, LONG *ObjectY, LONG ObjectWidth, LONG ObjectHeight); +//******************************************************************************************************************** + +constexpr DOUBLE fast_hypot(DOUBLE Width, DOUBLE Height) +{ + if (Width > Height) std::swap(Width, Height); + if ((Height / Width) <= 1.5) return 5.0 * (Width + Height) / 7.0; // Fast hypot calculation accurate to within 1% for specific use cases. + else return std::sqrt((Width * Width) + (Height * Height)); +} //******************************************************************************************************************** static bool read_rgb8(CSTRING Value, RGB8 *RGB) { - FRGB rgb; - if (!vecReadPainter(NULL, Value, &rgb, NULL, NULL, NULL)) { - RGB->Red = F2T(rgb.Red * 255.0); - RGB->Green = F2T(rgb.Green * 255.0); - RGB->Blue = F2T(rgb.Blue * 255.0); - RGB->Alpha = F2T(rgb.Alpha * 255.0); + VectorPainter painter; + if (vecReadPainter(NULL, Value, &painter, NULL) IS ERR::Okay) { + RGB->Red = F2T(painter.Colour.Red * 255.0); + RGB->Green = F2T(painter.Colour.Green * 255.0); + RGB->Blue = F2T(painter.Colour.Blue * 255.0); + RGB->Alpha = F2T(painter.Colour.Alpha * 255.0); return true; } else return false; } //******************************************************************************************************************** +// Extract all printable text between start and End. -static bool test_statement(CSTRING TestString, CSTRING CompareString, LONG Condition) +static std::string stream_to_string(RSTREAM &Stream, stream_char Start, stream_char End) { - pf::Log log(__FUNCTION__); + if (End < Start) std::swap(Start, End); - //log.msg("\"%s\" %d \"%s\"", TestString, Condition, CompareString); - - // Convert the If->Compare to its specified type - - LONG cmp_type = StrDatatype(CompareString); - LONG test_type = StrDatatype(TestString); - - bool result = false; - if (((test_type IS STT_NUMBER) or (test_type IS STT_FLOAT)) and ((cmp_type IS STT_NUMBER) or (cmp_type IS STT_FLOAT))) { - DOUBLE cmp_float = StrToFloat(CompareString); - DOUBLE test_float = StrToFloat(TestString); - switch(Condition) { - case COND_NOT_EQUAL: if (test_float != cmp_float) result = true; break; - case COND_EQUAL: if (test_float IS cmp_float) result = true; break; - case COND_LESS_THAN: if (test_float < cmp_float) result = true; break; - case COND_LESS_EQUAL: if (test_float <= cmp_float) result = true; break; - case COND_GREATER_THAN: if (test_float > cmp_float) result = true; break; - case COND_GREATER_EQUAL: if (test_float >= cmp_float) result = true; break; - default: log.warning("Unsupported condition type %d.", Condition); - } - } - else { - if (Condition IS COND_EQUAL) { - if (StrMatch(TestString, CompareString) IS ERR_Okay) result = true; - } - else if (Condition IS COND_NOT_EQUAL) { - if (StrMatch(TestString, CompareString) != ERR_Okay) result = true; + std::ostringstream str; + auto cs = Start; + for (; (cs.index <= End.index) and (cs.index < INDEX(Stream.size())); cs.next_code()) { + if (Stream[cs.index].code IS SCODE::TEXT) { + auto &text = Stream.lookup(cs); + if (cs.index < End.index) { + str << text.text.substr(cs.offset, text.text.size() - cs.offset); + } + else str << text.text.substr(cs.offset, End.offset - cs.offset); } - else log.warning("String comparison for condition %d not possible.", Condition); } - - return result; + return str.str(); } /********************************************************************************************************************* @@ -466,7962 +91,949 @@ Special operators include: *********************************************************************************************************************/ -static WORD write_calc(STRING Buffer, LONG BufferSize, DOUBLE Value, WORD Precision) +static std::string write_calc(DOUBLE Value, WORD Precision) { - LONG index = 0; - LARGE wholepart = F2T(Value); - if (wholepart < 0) wholepart = -wholepart; - - // Sign the value if it is less than 0 - - if ((Value < 0) and (index < BufferSize - 1)) Buffer[index++] = '-'; - - if (!Precision) { - index += IntToStr(wholepart, Buffer+index, BufferSize); - return index; - } - - DOUBLE fraction = (Value - wholepart); - if (fraction < 0) fraction = -fraction; + if (!Precision) return std::to_string(F2T(Value)); - index += IntToStr(wholepart, Buffer+index, BufferSize); - - if ((index < BufferSize-1) and ((fraction > 0) or (Precision < 0))) { - Buffer[index++] = '.'; - fraction = fraction * 10; - auto px = Precision; - if (px < 0) px = -px; - while ((fraction > 0.00001) and (index < BufferSize-1) and (px > 0)) { - LONG ival = F2T(fraction); - Buffer[index++] = ival + '0'; + LARGE wholepart = F2T(Value); + auto out = std::to_string(wholepart); + + DOUBLE fraction = std::abs(Value) - std::abs(wholepart); + if ((fraction > 0) or (Precision < 0)) { + out += '.'; + fraction *= 10; + auto px = std::abs(Precision); + while ((fraction > 0.00001) and (px > 0)) { + auto ival = F2T(fraction); + out += char(ival) + '0'; fraction = (fraction - ival) * 10; px--; } - if (Precision < 0) { - while (px > 0) { Buffer[index++] = '0'; px--; } - } + while (px > 0) { out += '0'; px--; } } - return index; + return out; } -ERROR calc(CSTRING String, DOUBLE *Result, STRING Output, LONG OutputSize) +//******************************************************************************************************************** +// Designed for reading unit values such as '50%' and '6px'. The returned value is scaled to pixels. + +static CSTRING read_unit(CSTRING Input, DOUBLE &Output, bool &Scaled) { - enum SIGN { - PLUS=1, - MINUS, - MULTIPLY, - DIVIDE, - MODULO - }; - - if (Result) *Result = 0; - - if (Output) { - if (OutputSize < 1) return ERR_BufferOverflow; - Output[0] = 0; - } + bool isnumber = true; + auto v = Input; + while ((*v) and (unsigned(*v) <= 0x20)) v++; - // Search for brackets and translate them first + auto str = v; + if ((*str IS '-') or (*str IS '+')) str++; - std::string in(String); - while (1) { - // Find the last bracketed reference + Scaled = false; + if (((*str >= '0') and (*str <= '9')) or (*str IS '.')) { + while ((*str >= '0') and (*str <= '9')) str++; - LONG last_bracket = 0; - for (LONG i=0; in[i]; i++) { - if (in[i] IS '\'') { // Skip anything in quotes - i++; - while (in[i]) { - if (in[i] IS '\\') { - i++; // Skip backslashes and the following character - if (!in[i]) break; - } - else if (in[i] IS '\'') break; - i++; - } - if (in[i] IS '\'') i++; + if (*str IS '.') { + str++; + if ((*str >= '0') and (*str <= '9')) { + while ((*str >= '0') and (*str <= '9')) str++; } - else if (in[i] IS '(') last_bracket = i; - } - - if (last_bracket > 0) { // Bracket found, translate its contents - LONG end; - for (end=last_bracket+1; (in[end]) and (in[end-1] != ')'); end++); - std::string buf(in, last_bracket, end - last_bracket); - - DOUBLE calc_float; - calc(buf.c_str()+1, &calc_float, NULL, 0); - char num[30]; - snprintf(num, sizeof(num), "%f", calc_float); - - in.replace(last_bracket, end - last_bracket, num); + else isnumber = false; } - else break; - } - // Perform the calculation - - STRING end; - WORD precision = 9; - DOUBLE total = 0; - DOUBLE overall = 0; - LONG index = 0; - SIGN sign = PLUS; - bool number = false; - for (LONG s=0; in[s];) { - if (in[s] <= 0x20); // Do nothing with whitespace - else if (in[s] IS '\'') { - if (Output) { - if (number) { // Write the current floating point number to the buffer before the next calculation - index += write_calc(Output+index, OutputSize - index, total, precision); - overall += total; // Reset the number - total = 0; - number = false; - } - - s++; - while (index < OutputSize-1) { - if (in[s] IS '\\') s++; // Skip the \ character and continue so that we can copy the character immediately after it - else if (in[s] IS '\'') break; - - Output[index++] = in[s++]; - } - } - else { // Skip string content if there is no string buffer - s++; - while (in[s] != '\'') s++; - } - } - else if (in[s] IS 'f') { // Fixed floating point precision adjustment - s++; - precision = -strtol(in.c_str() + s, &end, 10); - s += end - in.c_str(); - continue; - } - else if (in[s] IS 'p') { // Floating point precision adjustment - s++; - precision = strtol(in.c_str() + s, &end, 10); - s += end - in.c_str(); - continue; - } - else if ((in[s] >= '0') and (in[s] <= '9')) { - number = true; - DOUBLE fvalue = strtod(in.c_str() + s, &end); - s += end - in.c_str(); - - if (sign IS MINUS) total = total - fvalue; - else if (sign IS MULTIPLY) total = total * fvalue; - else if (sign IS MODULO) total = F2I(total) % F2I(fvalue); - else if (sign IS DIVIDE) { - if (fvalue) total = total / fvalue; // NB: Avoid division by zero errors - } - else total += fvalue; + DOUBLE multiplier = 1.0; + DOUBLE dpi = 96.0; - sign = PLUS; // The mathematical sign is reset whenever a number is encountered - continue; + if (*str IS '%') { + Scaled = true; + multiplier = 0.01; + str++; } - else if (in[s] IS '-') { - if (sign IS MINUS) sign = PLUS; // Handle double-negatives - else sign = MINUS; - } - else if (in[s] IS '+') sign = PLUS; - else if (in[s] IS '*') sign = MULTIPLY; - else if (in[s] IS '/') sign = DIVIDE; - else if (in[s] IS '%') sign = MODULO; - - for (++s; (in[s] & 0xc0) IS 0x80; s++); - } + else if ((str[0] IS 'p') and (str[1] IS 'x')) str += 2; // Pixel. This is the default type + else if ((str[0] IS 'e') and (str[1] IS 'm')) { str += 2; multiplier = 12.0 * (4.0 / 3.0); } // Current font-size + else if ((str[0] IS 'e') and (str[1] IS 'x')) { str += 2; multiplier = 6.0 * (4.0 / 3.0); } // Current font-size, reduced to the height of the 'x' character. + else if ((str[0] IS 'i') and (str[1] IS 'n')) { str += 2; multiplier = dpi; } // Inches + else if ((str[0] IS 'c') and (str[1] IS 'm')) { str += 2; multiplier = (1.0 / 2.56) * dpi; } // Centimetres + else if ((str[0] IS 'm') and (str[1] IS 'm')) { str += 2; multiplier = (1.0 / 20.56) * dpi; } // Millimetres + else if ((str[0] IS 'p') and (str[1] IS 't')) { str += 2; multiplier = (4.0 / 3.0); } // Points. A point is 4/3 of a pixel + else if ((str[0] IS 'p') and (str[1] IS 'c')) { str += 2; multiplier = (4.0 / 3.0) * 12.0; } // Pica. 1 Pica is equal to 12 Points - if (Output) { - if (number) index += write_calc(Output+index, OutputSize - index, total, precision); - Output[index] = 0; + Output = StrToFloat(v) * multiplier; } + else Output = 0; - if (Result) *Result = overall + total; - return ERR_Okay; + return str; } -/********************************************************************************************************************* - -This function is used to translate strings that make object and field references using the standard referencing format. -References are made to objects by enclosing statements within square brackets. As a result of calling this function, -all references within the Buffer will be translated to their relevant format. The Buffer needs to be large enough to -accommodate these adjustments as it will be expanded during the translation. It is recommended that the Buffer is at -least two times the actual length of the string that you are translating. - -Valid references can be made to an object by name, ID or relative parameters. Here are some examples illustrating the -different variations: +//******************************************************************************************************************** +// Checks if the file path is safe, i.e. does not refer to an absolute file location. - -Name reference. -ID reference. -Relative reference to the object that has the current context, or the document. -
    +static LONG safe_file_path(extDocument *Self, const std::string &Path) +{ + if ((Self->Flags & DCF::UNRESTRICTED) != DCF::NIL) return true; -Field references are a slightly different matter and will be converted to the value of the field that they are -referencing. A field reference is defined using the object referencing format, but they contain a `.fieldname` -extension. Here are some examples: -
    -[surface.width]
    -[file.location]
    -
    -A string such as `[mywindow.height] + [mywindow.width]` could be translated to `255 + 120` for instance. References to -string based fields can expand the Buffer very quickly, which is why large buffer spaces are recommended for all-purpose -translations. -Simple calculations are possible by enclosing a statement within a `[=...]` section. For example the aforementioned -string can be expanded to `[=[mywindow.height] + [mywindow.width]]`, which would give a result of 375. -The escape character for string translation is `$` and should be used as `[$...]`, which prevents everything within the -square brackets from being translated. The `[$]` characters will be removed as part of this process unless the -KEEP_ESCAPE flag is used. To escape a single right or left bracket, use `[rb]` or `[lb]` respectively. + return false; +} -*********************************************************************************************************************/ +//******************************************************************************************************************** +// Process an XML tree by setting correct style information and then calling parse_tags(). -static ERROR eval(extDocument *Self, STRING Buffer, LONG BufferLength, LONG Flags) +static ERR insert_xml(extDocument *Self, RSTREAM *Stream, objXML *XML, objXML::TAGS &Tag, INDEX TargetIndex, + STYLE StyleFlags, IPF Options) { pf::Log log(__FUNCTION__); - LONG pos, i, j; - if ((!Buffer) or (BufferLength < 3)) return log.warning(ERR_Args); + if (TargetIndex < 0) TargetIndex = Stream->size(); - // Quick check for translation symbols + log.traceBranch("Index: %d, Flags: $%.2x, Tag: %s", TargetIndex, LONG(StyleFlags), Tag[0].Attribs[0].Name.c_str()); - for (pos=0; Buffer[pos] != '['; pos++) { - if (!Buffer[pos]) return ERR_EmptyString; - } - - log.traceBranch("Size: %d, %s", BufferLength, Buffer); - - Field *classfield; - - ERROR error = ERR_Okay; - ERROR majorerror = ERR_Okay; - STRING calcbuffer = NULL; + if ((StyleFlags & STYLE::INHERIT_STYLE) != STYLE::NIL) { // Do nothing to change the style + parser parse(Self, XML, Stream); + parse.m_index = stream_char(TargetIndex); - // Skip to the end of the buffer (translation occurs 'backwards') - - for (; Buffer[pos]; pos++); - pos--; - while (pos >= 0) { - // Do not translate quoted areas - - if ((Buffer[pos] IS '"') and (!(Flags & SEF_IGNORE_QUOTES))) { - pos--; - while ((pos >= 0) and (Buffer[pos] != '"')) pos--; - if (pos < 0) { - log.warning("Badly defined string: %.80s", Buffer); - if (calcbuffer) free(calcbuffer); - return ERR_InvalidData; - } + if (Stream->data.empty()) { + parse.parse_tags(Tag, Options); } - - if ((Buffer[pos] IS '[') and ((Buffer[pos+1] IS '@') or (Buffer[pos+1] IS '%'))) { - // Ignore arguments, e.g. [@id] or [%id]. It's also useful for ignoring [@attrib] in xpath. - pos--; + else { + // Override the paragraph-content sanity check when inserting content in an existing document + parse.m_paragraph_depth++; + parse.parse_tags(Tag, Options); + parse.m_paragraph_depth--; } - else if (Buffer[pos] IS '[') { - // Make sure that there is a closing bracket - - WORD endbracket; - WORD balance = 0; - for (endbracket=pos; Buffer[endbracket]; endbracket++) { - if (Buffer[endbracket] IS '[') balance++; - else if (Buffer[endbracket] IS ']') { - balance--; - if (!balance) break; - } - } - - if (Buffer[endbracket] != ']') { - log.warning("Unbalanced string: %.90s ...", Buffer); - if (calcbuffer) free(calcbuffer); - return ERR_InvalidData; - } - - if (Buffer[pos+1] IS '=') { // Perform a calculation - DOUBLE value; - char num[endbracket-pos]; - - CopyMemory(Buffer+pos+2, num, endbracket-(pos+2)); - num[endbracket-(pos+2)] = 0; + } + else { + bc_font style; + style.fill = Self->FontFill; - if ((calcbuffer) or (BufferLength > 2048)) { - if (!calcbuffer) { - if (!(calcbuffer = (char *)malloc(BufferLength))) { - return ERR_AllocMemory; - } - } - calc(num, &value, calcbuffer, BufferLength); - if (insert_string(calcbuffer, Buffer, BufferLength, pos, endbracket-pos+1)) { - log.warning("Buffer overflow (%d bytes) while inserting to buffer \"%.30s\"", BufferLength, Buffer); - free(calcbuffer); - return ERR_BufferOverflow; - } + if ((StyleFlags & STYLE::RESET_STYLE) != STYLE::NIL) { + // Do not search for the most recent font style (force a reset) + } + else { + for (auto i = TargetIndex - 1; i >= 0; i--) { + if (Stream[0][i].code IS SCODE::FONT) { + style = Stream->lookup(i); + break; } - else { - char calcbuffer[2048]; - calc(num, &value, calcbuffer, sizeof(calcbuffer)); - if (insert_string(calcbuffer, Buffer, BufferLength, pos, endbracket-pos+1)) { - log.warning("Buffer overflow (%d bytes) while inserting to buffer \"%.30s\"", BufferLength, Buffer); - return ERR_BufferOverflow; - } + else if (Stream[0][i].code IS SCODE::PARAGRAPH_START) { + style = Stream->lookup(i).font; + break; } - } - else if (Buffer[pos+1] IS '$') { // Escape sequence - e.g. translates [$ABC] to ABC. Note: Use [rb] and [lb] instead for brackets. - if (Flags & SEF_KEEP_ESCAPE); // Special option to ignore escape sequences. - else { - for (i=pos+1, j=pos+2; Buffer[j]; i++,j++) Buffer[i] = Buffer[j]; - Buffer[i] = 0; + else if (Stream[0][i].code IS SCODE::LINK) { + style = Stream->lookup(i).font; + break; } - pos--; - continue; } - else { - char name[MAX_NAME_LEN]; + } - LONG j = 0; - for (i=pos+1; (Buffer[i] != '.') and (i < endbracket); i++) { - if ((size_t)j < sizeof(name)-1) name[j++] = std::tolower(Buffer[i]); - } - name[j] = 0; + // Revert to the default style if none is available. - // Check for [lb] and [rb] escape codes + if (auto font = style.get_font()) { + style.face = font->face; + style.font_size = font->font_size; + } - char code = 0; - if (j IS 2) { - if ((name[0] IS 'r') and (name[1] IS 'b')) code = ']'; - else if ((name[0] IS 'l') and (name[1] IS 'b')) code = '['; - } + parser parse(Self, XML, Stream); + parse.m_index = stream_char(TargetIndex); - if (code) { - Buffer[pos] = code; - for (i=pos+j+2, j=pos+1; Buffer[i]; i++) Buffer[j++] = Buffer[i]; - Buffer[j] = 0; - pos--; - continue; - } - else { - // Get the object ID + if (Stream->data.empty()) { + parse.parse_tags_with_style(Tag, style, Options); + } + else { + parse.m_paragraph_depth++; + parse.parse_tags_with_style(Tag, style, Options); + parse.m_paragraph_depth--; + } + } - OBJECTID objectid = 0; + // Check that the FocusIndex is valid (there's a slim possibility that it may not be if AC_Focus has been + // incorrectly used). - if (name[0]) { - if (!StrMatch(name, "self")) { - objectid = CurrentContext()->UID; - } - else FindObject(name, 0, FOF_SMART_NAMES, &objectid); - } + if (Self->FocusIndex >= std::ssize(Self->Tabs)) Self->FocusIndex = -1; - if (objectid) { - OBJECTPTR object = NULL; - Self->TBuffer[0] = 0; - if (Buffer[i] IS '.') { - // Get the field from the object - i++; - - LONG j = 0; - char field[60]; - while ((i < endbracket) and ((size_t)j < sizeof(field)-1)) { - field[j++] = Buffer[i++]; - } - field[j] = 0; - if (!AccessObject(objectid, 2000, &object)) { - OBJECTPTR target; - if (((classfield = find_field(object, field, &target))) and (classfield->Flags & FD_STRING)) { - error = GetField(object, (FIELD)classfield->FieldID|TSTR, &Self->TBuffer); - } - else { - // Get field as an unlisted type and manage any buffer overflow -repeat: - Self->TBuffer[Self->TBufferSize-1] = 0; - GetFieldVariable(object, field, Self->TBuffer, Self->TBufferSize); - - if (Self->TBuffer[Self->TBufferSize-1]) { - STRING newbuf; - if (!AllocMemory(Self->TBufferSize + 1024, MEM::STRING, &newbuf)) { - FreeResource(Self->TBuffer); - Self->TBuffer = newbuf; - Self->TBufferSize = Self->TBufferSize + 1024; - goto repeat; - } - } - } - error = ERR_Okay; // For fields, error code is always Okay so that the reference evaluates to NULL - } - else error = ERR_AccessObject; - } - else { - // Convert the object reference to an ID - Self->TBuffer[0] = '#'; - IntToStr(objectid, Self->TBuffer+1, Self->TBufferSize-1); - error = ERR_Okay; - } + return ERR::Okay; +} - if (!error) { - error = insert_string(Self->TBuffer, Buffer, BufferLength, pos, endbracket-pos+1); - if (object) ReleaseObject(object); +//******************************************************************************************************************** +// This is the principal function for adding/inserting text into the document stream, whether that be in the parse +// phase or from user editing. +// +// Preformat must be set to true if all consecutive whitespace characters in Text are to be inserted. - if (error) { - log.warning("Buffer overflow (%d bytes) while inserting to buffer \"%.30s\"", BufferLength, Buffer); - if (calcbuffer) free(calcbuffer); - return ERR_BufferOverflow; - } - } - else if (object) ReleaseObject(object); - } - else { - error = ERR_NoMatchingObject; - log.traceWarning("Failed to find object '%s'", name); - } - } - } +static ERR insert_text(extDocument *Self, RSTREAM *Stream, stream_char &Index, const std::string_view Text, bool Preformat) +{ + // Check if there is content to be processed - if (error != ERR_Okay) { - if (Flags & SEF_STRICT) { - // Do not delete everything in square brackets if the STRICT flags is used and retain the error code. - pos--; - majorerror = error; - } - else { - // If an error occurred, delete everything contained by the square brackets to prevent recursion errors. + if ((!Preformat) and (Self->NoWhitespace)) { + unsigned i; + for (i=0; i < Text.size(); i++) if (unsigned(Text[i]) > 0x20) break; + if (i IS Text.size()) return ERR::Okay; + } - for (i=endbracket+1; Buffer[i]; i++) Buffer[pos++] = Buffer[i]; - Buffer[pos] = 0; - } - error = ERR_Okay; + if (Preformat) { + bc_text et(Text, true); + Stream->emplace(Index, et); + } + else { + bc_text et; + et.text.reserve(Text.size()); + auto ws = Self->NoWhitespace; // Retrieve previous whitespace state + for (unsigned i=0; i < Text.size(); ) { + if (unsigned(Text[i]) <= 0x20) { // Whitespace encountered + for (++i; (unsigned(Text[i]) <= 0x20) and (i < Text.size()); i++); + if (!ws) et.text += ' '; + ws = true; + } + else { + et.text += Text[i++]; + ws = false; } } - else pos--; + Self->NoWhitespace = ws; + Stream->emplace(Index, et); } - log.trace("Result: %s", Buffer); - - if (calcbuffer) free(calcbuffer); - return majorerror; + return ERR::Okay; } //******************************************************************************************************************** -static bool eval_condition(CSTRING String) +static ERR load_doc(extDocument *Self, std::string Path, bool Unload, ULD UnloadFlags) { pf::Log log(__FUNCTION__); - static const FieldDef table[] = { - { "<>", COND_NOT_EQUAL }, - { "!=", COND_NOT_EQUAL }, - { "=", COND_EQUAL }, - { "==", COND_EQUAL }, - { "<", COND_LESS_THAN }, - { "<=", COND_LESS_EQUAL }, - { ">", COND_GREATER_THAN }, - { ">=", COND_GREATER_EQUAL }, - { NULL, 0 } - }; - - if (!String) return false; - while ((*String) and (*String <= 0x20)) String++; - - bool reverse = false; - - // Find the condition statement - - LONG i; - for (i=0; String[i]; i++) { - if ((String[i] IS '!') and (String[i+1] IS '=')) break; - if (String[i] IS '>') break; - if (String[i] IS '<') break; - if (String[i] IS '=') break; - } + log.branch("Loading file '%s', page '%s'", Path.c_str(), Self->PageName.c_str()); - // If there is no condition statement, evaluate the statement as an integer + if (Unload) unload_doc(Self, UnloadFlags); - if (!String[i]) { - if (StrToInt(String)) return true; - else return false; - } + process_parameters(Self, Path); - LONG cpos = i; + // Generate a path without parameter values. - // Test field + auto i = Path.find_first_of("&#?"); + if (i != std::string::npos) Path.erase(i); - while ((i > 0) and (String[i-1] IS ' ')) i--; - char test[i+1]; - CopyMemory(String, test, i); - test[i] = 0; + if (AnalysePath(Path.c_str(), NULL) IS ERR::Okay) { + auto task = CurrentTask(); + task->setPath(Path); - // Condition field + auto xml = objXML::create { + fl::Flags(XMF::ALL_CONTENT|XMF::PARSE_HTML|XMF::STRIP_HEADERS|XMF::WELL_FORMED), + fl::Path(Path), + fl::ReadOnly(true) + }; - LONG condition = 0; - { - char cond[3]; - UBYTE c; - for (i=cpos,c=0; (c < 2) and ((String[i] IS '!') or (String[i] IS '=') or (String[i] IS '>') or (String[i] IS '<')); i++) { - cond[c++] = String[i]; - } - cond[c] = 0; + if (xml.ok()) { + #ifndef RETAIN_LOG_LEVEL + pf::LogLevel level(3); + #endif + parser parse(Self, &Self->Stream); - LONG j; - for (j=0; table[j].Name; j++) { - if (!StrMatch(cond, table[j].Name)) { - condition = table[j].Value; - break; + if (Self->PretextXML) { + parse.process_page(Self->PretextXML); } - } - } - while ((String[i]) and (String[i] <= 0x20)) i++; // skip white-space + parse.process_page(*xml); + + if (Self->initialised()) { + Self->UpdatingLayout = true; + redraw(Self, true); + } - bool truth = false; - if (test[0]) { - if (condition) { - truth = test_statement(test, String+i, condition); + #ifdef DBG_STREAM + print_stream(Self->Stream); + #endif + return Self->Error; + } + else { + error_dialog("Document Load Error", std::string("Failed to load document file '") + Path + "'"); + return log.warning(ERR::OpenFile); } - else log.warning("No test condition in \"%s\".", String); } - else log.warning("No test value in \"%s\".", String); - - if (reverse) return truth ^ 1; - else return truth; + else return log.warning(ERR::FileNotFound); } //******************************************************************************************************************** +// This function removes all allocations that were made in displaying the current page, and resets a number of +// variables that they are at the default settings for the next page. +// +// Set ULD::TERMINATE if the document object is being destroyed. +// +// The PageName is not freed because the desired page must not be dropped during refresh of manually loaded XML for +// example. -INLINE BYTE sortseg_compare(extDocument *Self, SortSegment *Left, SortSegment *Right) +static ERR unload_doc(extDocument *Self, ULD Flags) { - if (Left->Y < Right->Y) return 1; - else if (Left->Y > Right->Y) return -1; - else { - if (Self->Segments[Left->Segment].X < Self->Segments[Right->Segment].X) return 1; - else if (Self->Segments[Left->Segment].X > Self->Segments[Right->Segment].X) return -1; - else return 0; - } -} - -//******************************************************************************************************************** -// Assists in the translation of URI strings where escape codes may be used. + pf::Log log(__FUNCTION__); -INLINE LONG uri_char(CSTRING *Source, STRING Dest, LONG Size) -{ - CSTRING src = Source[0]; - if ((src[0] IS '%') and (src[1] >= '0') and (src[1] <= '9') and (src[2] >= '0') and (src[2] <= '9')) { - Dest[0] = ((src[1] - '0') * 10) | (src[2] - '0'); - src += 3; - Source[0] = src; - return 1; - } - else if (Size > 1) { - *Dest = src[0]; - Source[0] = Source[0] + 1; - return 1; - } - else return 0; -} + log.branch("Flags: $%.2x", LONG(Flags)); -//******************************************************************************************************************** + #ifdef DBG_STREAM + print_stream(Self->Stream); + #endif -static ERROR consume_input_events(const InputEvent *Events, LONG Handle) -{ - auto Self = (extDocument *)CurrentContext(); + Self->Highlight = glHighlight; - for (auto input=Events; input; input=input->Next) { - if (input->Flags & JTYPE::MOVEMENT) { - for (auto scan=input->Next; (scan) and (scan->Flags & JTYPE::MOVEMENT); scan=scan->Next) { - input = scan; - } - - if (input->OverID IS Self->PageID) Self->MouseOver = TRUE; - else Self->MouseOver = FALSE; - - check_mouse_pos(Self, input->X, input->Y); - - // Note that this code has to 'drop through' due to the movement consolidation loop earlier in this subroutine. - } - - if (input->Type IS JET::LMB) { - if (input->Value > 0) { - Self->LMB = TRUE; - check_mouse_click(Self, input->X, input->Y); - } - else { - Self->LMB = FALSE; - check_mouse_release(Self, input->X, input->Y); - } - } - } - - return ERR_Okay; -} - -//******************************************************************************************************************** -// Checks if the file path is safe, i.e. does not refer to an absolute file location. - -static LONG safe_file_path(extDocument *Self, CSTRING Path) -{ - if (Self->Flags & DCF_UNRESTRICTED) return TRUE; - - - - - - return FALSE; -} - -//******************************************************************************************************************** -// Used by if, elseif, while statements to check the satisfaction of conditions. - -static BYTE check_tag_conditions(extDocument *Self, XMLTag *Tag) -{ - pf::Log log("eval"); - - BYTE satisfied = FALSE; - BYTE reverse = FALSE; - for (LONG i=0; i < Tag->TotalAttrib; i++) { - if (!StrMatch("statement", Tag->Attrib[i].Name)) { - satisfied = eval_condition(Tag->Attrib[i].Value); - log.trace("Statement: %s", Tag->Attrib[i].Value); - break; - } - else if (!StrMatch("exists", Tag->Attrib[i].Name)) { - OBJECTID object_id; - if (!FindObject(Tag->Attrib[i].Value, 0, FOF_SMART_NAMES, &object_id)) { - if (valid_objectid(Self, object_id)) { - satisfied = TRUE; - } - } - break; - } - else if (!StrMatch("notnull", Tag->Attrib[i].Name)) { - log.trace("NotNull: %s", Tag->Attrib[i].Value); - if (Tag->Attrib[i].Value) { - if (!Tag->Attrib[i].Value[0]) { - satisfied = FALSE; - } - else if ((Tag->Attrib[i].Value[0] IS '0') and (!Tag->Attrib[i].Value[1])) { - satisfied = FALSE; - } - else satisfied = TRUE; - } - else satisfied = FALSE; - } - else if ((!StrMatch("isnull", Tag->Attrib[i].Name)) or (!StrMatch("null", Tag->Attrib[i].Name))) { - log.trace("IsNull: %s", Tag->Attrib[i].Value); - if (Tag->Attrib[i].Value) { - if (!Tag->Attrib[i].Value[0]) { - satisfied = TRUE; - } - else if ((Tag->Attrib[i].Value[0] IS '0') and (!Tag->Attrib[i].Value[1])) { - satisfied = TRUE; - } - else satisfied = FALSE; - } - else satisfied = TRUE; - } - else if (!StrMatch("not", Tag->Attrib[i].Name)) { - reverse = TRUE; - } - } - - // Check for a not condition and invert the satisfied value if found - - if (reverse) satisfied = satisfied ^ 1; - - return satisfied; -} - -/********************************************************************************************************************* -** Processes an XML tag and passes it to parse_tag(). -** -** IXF_HOLDSTYLE: If set, the font style will not be cleared. -** IXF_RESETSTYLE: If set, the current font style will be completely reset, rather than defaulting to the most recent font style used at the insertion point. -** IXF_SIBLINGS: If set, sibling tags that follow the root will be parsed. -*/ - -static ERROR insert_xml(extDocument *Self, objXML *XML, XMLTag *Tag, LONG Index, UBYTE Flags) -{ - pf::Log log(__FUNCTION__); - objFont *font; - LONG insert_index, start; - - if (!Tag) return ERR_Okay; - - if (Index < 0) Index = Self->StreamLen; - - log.traceBranch("Index: %d, Flags: $%.2x, Tag: %s", Index, Flags, Tag->Attrib->Name); - - // Retrieve the most recent font definition and use that as the style that we're going to start with. - - if (Flags & IXF_HOLDSTYLE) { - // Do nothing to change the style - } - else { - ClearMemory(&Self->Style, sizeof(Self->Style)); - Self->Style.FontStyle.Index = -1; - Self->Style.FontChange = FALSE; - Self->Style.StyleChange = FALSE; - - if (Flags & IXF_RESETSTYLE) { - // Do not search for the most recent font style - } - else { - auto str = Self->Stream; - LONG i = Index; - PREV_CHAR(str, i); - while (i > 0) { - if ((str[i] IS CTRL_CODE) and (ESCAPE_CODE(str, i) IS ESC_FONT)) { - CopyMemory(escape_data(str, i), &Self->Style.FontStyle, sizeof(escFont)); - log.trace("Found existing font style, font index %d, flags $%.8x.", Self->Style.FontStyle.Index, Self->Style.FontStyle.Options); - break; - } - PREV_CHAR(str, i); - } - } - - // If no style is available, we need to create a default font style and insert it at the start of the stream. - - if (Self->Style.FontStyle.Index IS -1) { - if ((Self->Style.FontStyle.Index = create_font(Self->FontFace, "Regular", Self->FontSize)) IS -1) { - if ((Self->Style.FontStyle.Index = create_font("Open Sans", "Regular", 10)) IS -1) { - return ERR_Failed; - } - } - - Self->Style.FontStyle.Colour = Self->FontColour; - Self->Style.FontChange = TRUE; - } - - if ((font = lookup_font(Self->Style.FontStyle.Index, "insert_xml"))) { - StrCopy(font->Face, Self->Style.Face, sizeof(Self->Style.Face)); - Self->Style.Point = font->Point; - } - } - - // Parse content and insert it at the end of the stream (we will move it to the insertion point afterwards). - - start = Self->StreamLen; - insert_index = Self->StreamLen; - if (Flags & IXF_SIBLINGS) { - parse_tag(Self, XML, Tag, &insert_index, 0); - } - else { - auto save = Tag->Next; - Tag->Next = NULL; - parse_tag(Self, XML, Tag, &insert_index, 0); - Tag->Next = save; - } - - if (Flags & IXF_CLOSESTYLE) { - style_check(Self, &insert_index); - } - - // Sanity checks - - if (insert_index != Self->StreamLen) { - log.warning("Index %d does not match stream length %d", Index, Self->StreamLen); - Self->StreamLen = insert_index; - } - - if (Self->StreamLen <= start) { - log.trace("parse_tag() did not insert any content into the stream."); - return ERR_NothingDone; - } - - // Move the content from the end of the stream to the requested insertion point - - if (Index < start) { - STRING content; - LONG length = Self->StreamLen - start; - log.trace("Moving new content of %d bytes to the insertion point at index %d", Index, length); - if (!AllocMemory(length, MEM::DATA|MEM::NO_CLEAR, &content)) { - CopyMemory(Self->Stream + start, content, length); // Take a copy of the inserted data - CopyMemory(Self->Stream + Index, Self->Stream + Index + length, start - Index); // Make room for the data at the insertion point - CopyMemory(content, Self->Stream + Index, length); // Copy data to the insertion point - FreeResource(content); - } - } - - // Check that the FocusIndex is valid (there's a slim possibility that it may not be if AC_Focus has been - // incorrectly used). - - if (Self->FocusIndex >= Self->TabIndex) Self->FocusIndex = -1; - - return ERR_Okay; -} - -//******************************************************************************************************************** -// Supported Flags: -// IPF_NOCONTENT: -// IPF_STRIPFEEDS: - -#define SAVE_ARGS(tag) \ - b_revert = Self->BufferIndex; \ - s_revert = Self->ArgIndex; \ - e_revert = 0; \ - if (convert_xml_args(Self, (tag)->Attrib, (tag)->TotalAttrib) != ERR_Okay) goto next; \ - e_revert = Self->ArgIndex; - -#define RESTORE_ARGS() \ - if (e_revert > s_revert) { \ - while (e_revert > s_revert) { \ - e_revert--; \ - Self->VArg[e_revert].Attrib[0] = Self->VArg[e_revert].String; \ - } \ - } \ - Self->BufferIndex = b_revert; \ - Self->ArgIndex = s_revert; - -static LONG parse_tag(extDocument *Self, objXML *XML, XMLTag *Tag, LONG *Index, LONG Flags) -{ - pf::Log log(__FUNCTION__); - XMLTag *child, *object_template; - CSTRING content; - LONG i, b_revert, result, filter; - UBYTE s_revert, e_revert, template_match; - - if (!Tag) { - log.traceWarning("Tag parameter not specified."); - return 0; - } - - if (Self->Error) { - log.traceWarning("Error field is set, returning immediately."); - return 0; - } - - #ifdef _DEBUG - char tagarg[30]; - - if (Tag->Attrib->Name) { - for (i=0; ((size_t)i < sizeof(tagarg)-1) and (Tag->Attrib->Name[i]); i++) tagarg[i] = Tag->Attrib->Name[i]; - } - else if (Tag->Attrib->Value) { - for (i=0; ((size_t)i < sizeof(tagarg)-1) and (Tag->Attrib->Value[i]); i++) { - if (Tag->Attrib->Value[i] < 0x20) tagarg[i] = '.'; - else tagarg[i] = Tag->Attrib->Value[i]; - } - } - else i = 0; - - tagarg[i] = 0; - - log.traceBranch("XML: %d, First-Tag: '%.30s', Face: %.20s, Tag: %p, Flags: $%.8x", XML->UID, tagarg, Self->Style.Face, Tag, Flags); - - #endif - - CSTRING tagname = NULL; - filter = Flags & 0xffff0000; - result = 0; - - while (Tag) { - SAVE_ARGS(Tag); - - #ifdef _DEBUG - if (Tag->Attrib->Name) log.trace("Tag: %s", Tag->Attrib->Name); - else if (Tag->Attrib->Value) { - for (i=0; ((size_t)i < sizeof(tagarg)-1) and (Tag->Attrib->Value[i]); i++) { - if (Tag->Attrib->Value[i] < 0x20) tagarg[i] = '.'; - else tagarg[i] = Tag->Attrib->Value[i]; - } - tagarg[i] = 0; - log.trace("Content: %s", tagarg); - } - #endif - - child = Tag->Child; - - // If the tag is content based, process it - - if (!(tagname = Tag->Attrib->Name)) { - if (!(Flags & IPF_NOCONTENT)) { - if ((content = Tag->Attrib->Value)) { - if (Flags & IPF_STRIPFEEDS) { - while ((*content IS '\n') or (*content IS '\r')) content++; - Flags &= ~IPF_STRIPFEEDS; - } - - if (Self->CurrentObject) { - // Objects do not normally accept document content (user should use ) - // An exception is made for content that is injected within an object tag. - - if (XML IS Self->InjectXML) { - acDataContent(Self->CurrentObject, content); - } - } - else if (Self->ParagraphDepth) { // We must be in a paragraph to accept content as text - insert_text(Self, Index, content, StrLength(content), - (Self->Style.FontStyle.Options & FSO_PREFORMAT) ? TRUE : FALSE); - } - } - else log.traceWarning("Content tag contains no content string."); - } - - goto next; - } - - if (tagname[0] IS '$') tagname++; - - // Check for templates first, as they can be used to override the default RPL tag names. - - object_template = NULL; - template_match = FALSE; - if (Self->Templates) { - for (auto scan=Self->Templates->Tags[0]; scan; scan=scan->Next) { - for (LONG i=0; i < scan->TotalAttrib; i++) { - if ((!StrMatch("class", scan->Attrib[i].Name)) and - (!StrMatch(tagname, scan->Attrib[i].Value))) { - object_template = scan; - template_match = TRUE; - } - else if ((!StrMatch("Name", scan->Attrib[i].Name)) and - (!StrMatch(tagname, scan->Attrib[i].Value))) { - template_match = TRUE; - } - } - - if (template_match) { - if (object_template) { - goto process_object; - } - else { - // Process the template by jumping into it. Arguments in the tag are added to a sequential - // list that will be processed in reverse by convert_xml_args(). - - if (Self->ArgNestIndex < ARRAYSIZE(Self->ArgNest)) { - pf::Log log(__FUNCTION__); - - START_TEMPLATE(Tag->Child, XML, Tag); // Required for the feature to work inside the template - - log.traceBranch("Executing template '%s'.", tagname); - - Self->ArgNest[Self->ArgNestIndex++] = Tag; - - parse_tag(Self, Self->Templates, scan->Child, Index, Flags); - - Self->ArgNestIndex--; - - END_TEMPLATE(); - } - else log.warning("Template nesting limit of %d exceeded - cannot continue.", ARRAYSIZE(Self->ArgNest)); - - goto next; - } - } - } - } - - // Check if the instruction refers to a reserved tag name listed in glTags. - // If a match is found, a routine specific to that instruction is executed. - { - ULONG taghash = StrHash(tagname, 0); - - for (LONG i=0; glTags[i].TagHash; i++) { - if (glTags[i].TagHash IS taghash) { - if ((glTags[i].Flags & FILTER_ALL) and (!(glTags[i].Flags & filter))) { - // A filter applies to this tag and the filter flags do not match - log.warning("Invalid use of tag '%s' - Not applied to the correct tag parent.", tagname); - Self->Error = ERR_InvalidData; - } - else if (glTags[i].Routine) { - //log.traceBranch("%s", tagname); - - if ((Self->CurrentObject) and (!(glTags[i].Flags & (TAG_OBJECTOK|TAG_CONDITIONAL)))) { - log.warning("Illegal use of tag %s within object of class '%s'.", tagname, Self->CurrentObject->Class->ClassName); - continue; - } - - if (glTags[i].Flags & TAG_PARAGRAPH) Self->ParagraphDepth++; - - if ((Flags & IPF_NOCONTENT) and (glTags[i].Flags & TAG_CONTENT)) { - // Do nothing when content is not allowed - log.trace("Content disabled on '%s', tag not processed.", tagname); - } - else if (glTags[i].Flags & TAG_CHILDREN) { - // Child content is compulsory or tag has no effect - if (child) glTags[i].Routine(Self, XML, Tag, child, Index, Flags); - else log.trace("No content found in tag '%s'", tagname); - } - else glTags[i].Routine(Self, XML, Tag, child, Index, Flags); - - if (glTags[i].Flags & TAG_PARAGRAPH) Self->ParagraphDepth--; - } - goto next; - } - } - } - // Some reserved tag names are not listed in glTags as they affect the flow of the parser and are dealt with here. - - if (!StrMatch("break", tagname)) { - // Breaking stops executing all tags (within this section) beyond the breakpoint. If in a loop, the loop - // will stop executing. - - result |= TRF_BREAK; - RESTORE_ARGS(); - break; - } - else if (!StrMatch("continue", tagname)) { - // Continuing - does the same thing as a break but the loop continues. - // If used when not in a loop, then all sibling tags are skipped. - - result |= TRF_CONTINUE; - RESTORE_ARGS(); - break; - } - else if (!StrMatch("if", tagname)) { - if (check_tag_conditions(Self, Tag)) { - result = parse_tag(Self, XML, Tag->Child, Index, Flags); - } - else if (Tag->Next) { - // Check for an else statement in the next tag, if discovered then we can jump to it immediately. - - RESTORE_ARGS(); - - auto scan = Tag->Next; // Skip content tags - while ((scan) and (!scan->Attrib->Name)) scan = scan->Next; - - while (scan) { - if (!StrMatch("elseif", scan->Attrib->Name)) { - Tag = scan; - - SAVE_ARGS(scan); - i = check_tag_conditions(Self, scan); - RESTORE_ARGS(); - - if (i) { - result = parse_tag(Self, XML, scan->Child, Index, Flags); - break; - } - } - else if (!StrMatch("else", scan->Attrib->Name)) { - Tag = scan; - result = parse_tag(Self, XML, scan->Child, Index, Flags); - break; - } - else if (!scan->Attrib->Name); // Ignore any content inbetween if/else tags - else break; - - scan = scan->Next; - } - - goto next_skiprestore; - } - - if (result & (TRF_CONTINUE|TRF_BREAK)) { - RESTORE_ARGS(); - break; - } - } - else if (!StrMatch("while", tagname)) { - if ((Tag->Child) and (check_tag_conditions(Self, Tag))) { - // Save/restore the statement string on each cycle to fully evaluate the condition each time. - - LONG saveindex = Self->LoopIndex; - Self->LoopIndex = 0; - - RESTORE_ARGS(); - - i = TRUE; - while (i) { - SAVE_ARGS(Tag); - i = check_tag_conditions(Self, Tag); - RESTORE_ARGS(); - - if ((i) and (parse_tag(Self, XML, Tag->Child, Index, Flags) & TRF_BREAK)) break; - - Self->LoopIndex++; - } - - Self->LoopIndex = saveindex; - - goto next_skiprestore; - } - } - else { -process_object: - if (!(Flags & IPF_NOCONTENT)) { - // Check if the tagname refers to a class. For security reasons, we limit the classes that can be embedded - // in functional pages. - - if (!StrCompare("obj:", tagname, 4)) tagname += 4; - - CSTRING pagetarget = NULL; - CLASSID class_id = 0; - for (i=0; i < ARRAYSIZE(glDocClasses); i++) { - if (!StrMatch(tagname, glDocClasses[i].ClassName)) { - pagetarget = glDocClasses[i].PageTarget; - class_id = glDocClasses[i].ClassID; - break; - } - } - - if ((i >= ARRAYSIZE(glDocClasses)) and (Self->Flags & DCF_UNRESTRICTED)) { - class_id = ResolveClassName(tagname); - } - - if (class_id) { - tag_object(Self, pagetarget, class_id, object_template, XML, Tag, child, Index, 0, &s_revert, &e_revert, &b_revert); - } - else log.warning("Tag '%s' unsupported as an instruction, template or class.", tagname); - } - else log.warning("Unrecognised tag '%s' used in a content-restricted area.", tagname); - } - -next: - - RESTORE_ARGS(); - -next_skiprestore: - - if (Self->Error) break; - Tag = Tag->Next; - } - - return result; -} - -//******************************************************************************************************************** - -static void style_check(extDocument *Self, LONG *Index) -{ - if (Self->Style.FontChange) { - // Create a new font object for the current style - - CSTRING style_name = get_font_style(Self->Style.FontStyle.Options); - Self->Style.FontStyle.Index = create_font(Self->Style.Face, style_name, Self->Style.Point); - //log.trace("Changed font to index %d, face %s, style %s, size %d.", Self->Style.FontStyle.Index, Self->Style.Face, style_name, Self->Style.Point); - Self->Style.FontChange = FALSE; - Self->Style.StyleChange = TRUE; - } - - if (Self->Style.StyleChange) { - // Insert a font change into the text stream - //log.trace("Style change detected."); - insert_escape(Self, Index, ESC_FONT, &Self->Style.FontStyle, sizeof(Self->Style.FontStyle)); - Self->Style.StyleChange = FALSE; - } -} - -//******************************************************************************************************************** -// Inserts plain UTF8 text into the document stream. Insertion can be at any byte index, indicated by the Index -// parameter. The Index value will be increased by the number of bytes to insert, indicated by Length. The Document's -// StreamLen will have increased by Length on this function's return. -// -// Preformat must be set to TRUE if all consecutive whitespace characters in Text are to be inserted. - -static ERROR insert_text(extDocument *Self, LONG *Index, CSTRING Text, LONG Length, BYTE Preformat) -{ - UBYTE *stream; - LONG pos, i; - -#ifdef DBG_STREAM - pf::Log log(__FUNCTION__); - log.trace("Index: %d, WSpace: %d", *Index, Self->NoWhitespace); -#endif - - if (!Length) return ERR_Okay; - - // Check if there is content to be processed - - if ((Preformat IS FALSE) and (Self->NoWhitespace)) { - for (i=0; i < Length; i++) if (Text[i] > 0x20) break; - if (i IS Length) return ERR_Okay; - } - - style_check(Self, Index); - - LONG size = Self->StreamLen + Length + 1; - if (size >= Self->StreamSize) { - // The size of the text extends past the stream buffer, so allocate more space. - - size += (BUFFER_BLOCK > Length) ? BUFFER_BLOCK : Length; - if (!AllocMemory(size, MEM::NO_CLEAR, &stream)) { - if (*Index > 0) CopyMemory(Self->Stream, stream, *Index); - - pos = *Index; - - if (Preformat) { - for (i=0; i < Length; i++) { - if (Text[i] IS CTRL_CODE) stream[pos+i] = ' '; - else stream[pos+i] = Text[i]; - } - pos += Length; - } - else { - for (i=0; i < Length; ) { - if (Text[i] <= 0x20) { // Whitespace eliminator, also handles any unwanted presence of ESC_CODE which is < 0x20 - while ((Text[i] <= 0x20) and (i < Length)) i++; - if (!Self->NoWhitespace) { - stream[pos++] = ' '; - } - Self->NoWhitespace = TRUE; - } - else { - stream[pos++] = Text[i++]; - Self->NoWhitespace = FALSE; - } - } - Length = pos - *Index; - } - - if (*Index < Self->StreamLen) { - CopyMemory(Self->Stream + *Index, stream+pos, Self->StreamLen - *Index); - pos += Self->StreamLen - *Index; - } - stream[pos] = 0; - - FreeResource(Self->Stream); - Self->Stream = stream; - Self->StreamSize = size; - } - else return ERR_AllocMemory; - } - else { - if (Self->Stream[*Index]) { - // Make room at the insertion point - CopyMemory(Self->Stream + *Index, - Self->Stream + *Index + Length, - Self->StreamLen - *Index); - } - - auto stream = Self->Stream; - pos = *Index; - - if (Preformat) { - for (LONG i=0; i < Length; i++) { - if (Text[i] IS CTRL_CODE) stream[pos+i] = ' '; - else stream[pos+i] = Text[i]; - } - pos += Length; - } - else { - for (LONG i=0; i < Length; ) { - if (Text[i] <= 0x20) { // Whitespace eliminator, also handles any unwanted presence of ESC_CODE which is < 0x20 - while ((Text[i] <= 0x20) and (i < Length)) i++; - if (!Self->NoWhitespace) stream[pos++] = ' '; - Self->NoWhitespace = TRUE; - } - else { - stream[pos++] = Text[i++]; - Self->NoWhitespace = FALSE; - } - } - Length = pos - *Index; // Recalc the length - } - } - - *Index += Length; - Self->StreamLen += Length; - Self->Stream[Self->StreamLen] = 0; - return ERR_Okay; -} - -//******************************************************************************************************************** -// Inserts an escape sequence into the text stream. -// -// ESC,Code,Length[2],...Data...,Length[2],ESC - -static ERROR insert_escape(extDocument *Self, LONG *Index, WORD EscapeCode, APTR Data, LONG Length) -{ - pf::Log log(__FUNCTION__); - UBYTE *stream; - -#ifdef DBG_STREAM - log.trace("Index: %d, Code: %s (%d), Length: %d", *Index, strCodes[EscapeCode], EscapeCode, Length); -#else - //log.trace("Index: %d, Code: %d, Length: %d", *Index, EscapeCode, Length); -#endif - - if (Length > 0xffff - ESC_LEN) { - log.warning("Escape code length of %d exceeds %d bytes.", Length, 0xffff - ESC_LEN); - return ERR_BufferOverflow; - } - - LONG element_id = ++Self->ElementCounter; - LONG size = Self->StreamLen + Length + ESC_LEN + 1; - LONG total_length = Length + ESC_LEN; - if (size >= Self->StreamSize) { - size += BUFFER_BLOCK; - if (!AllocMemory(size, MEM::NO_CLEAR, &stream)) { - if (*Index > 0) CopyMemory(Self->Stream, stream, *Index); - - LONG pos = *Index; - stream[pos++] = CTRL_CODE; - stream[pos++] = EscapeCode; - stream[pos++] = total_length>>8; - stream[pos++] = total_length & 0xff; - ((LONG *)(stream + pos))[0] = element_id; - pos += sizeof(LONG); - if ((Data) and (Length > 0)) { - CopyMemory(Data, stream + pos, Length); - pos += Length; - } - stream[pos++] = total_length>>8; - stream[pos++] = total_length & 0xff; - stream[pos++] = CTRL_CODE; - - if (*Index < Self->StreamLen) { - CopyMemory(Self->Stream + *Index, stream+pos, Self->StreamLen - *Index); - pos += Self->StreamLen - *Index; - } - - FreeResource(Self->Stream); - Self->Stream = stream; - Self->StreamSize = size; - } - else return ERR_AllocMemory; - } - else { - if (Self->Stream[*Index]) { - CopyMemory(Self->Stream + *Index, - Self->Stream + *Index + Length + ESC_LEN, - Self->StreamLen - *Index); - } - - stream = Self->Stream; - LONG pos = *Index; - stream[pos++] = CTRL_CODE; - stream[pos++] = EscapeCode; - stream[pos++] = total_length>>8; - stream[pos++] = total_length & 0xff; - ((LONG *)(stream + pos))[0] = element_id; - pos += sizeof(LONG); - if ((Data) and (Length > 0)) { - CopyMemory(Data, stream + pos, Length); - pos += Length; - } - stream[pos++] = total_length>>8; - stream[pos++] = total_length & 0xff; - stream[pos++] = CTRL_CODE; - } - - Self->StreamLen += Length + ESC_LEN; - Self->Stream[Self->StreamLen] = 0; - *Index += Length + ESC_LEN; - return ERR_Okay; -} - -//******************************************************************************************************************** -// This function is called only when a paragraph or explicit line-break (\n) is encountered. - -static void end_line(extDocument *Self, layout *l, LONG NewLine, LONG Index, DOUBLE Spacing, LONG RestartIndex, CSTRING Caller) -{ - LONG i, bottomline, new_y; - - if ((!l->line_height) and (l->wordwidth)) { - // If this is a one-word line, the line height will not have been defined yet - //log.trace("Line Height being set to font (currently %d/%d)", l->line_height, l->base_line); - l->line_height = l->font->LineSpacing; - l->base_line = l->font->Ascent; - } - - LAYOUT("~end_line()","%s: CursorY: %d, ParaY: %d, ParaEnd: %d, Line Height: %d * %.2f, Index: %d/%d, Restart: %d", Caller, l->cursory, l->paragraph_y, l->paragraph_end, l->line_height, Spacing, l->line_index, Index, RestartIndex); - - for (LONG i=l->start_clips; i < Self->TotalClips; i++) { - if (Self->Clips[i].Transparent) continue; - if ((l->cursory + l->line_height >= Self->Clips[i].Clip.Top) and (l->cursory < Self->Clips[i].Clip.Bottom)) { - if (l->cursorx + l->wordwidth < Self->Clips[i].Clip.Left) { - if (Self->Clips[i].Clip.Left < l->alignwidth) l->alignwidth = Self->Clips[i].Clip.Left; - } - } - } - - if (Index > l->line_index) { - add_drawsegment(Self, l->line_index, Index, l, l->cursory, l->cursorx + l->wordwidth - l->line_x, l->alignwidth - l->line_x, "Esc:EndLine"); - } - - // Determine the new vertical position of the cursor. This routine takes into account multiple line-breaks, so that - // the overall amount of whitespace is no more than the biggest line-break specified in - // a line-break sequence. - - if (NewLine) { - bottomline = l->cursory + l->line_height; - if (l->paragraph_end > bottomline) bottomline = l->paragraph_end; - - // Check for a previous paragraph escape sequence. This resolves cases such as "

    ...

    ...

    " - - if ((i = Index) > 0) { - PREV_CHAR(Self->Stream, i); - while (i > 0) { - if (Self->Stream[i] IS CTRL_CODE) { - if ((ESCAPE_CODE(Self->Stream, i) IS ESC_PARAGRAPH_END) or - (ESCAPE_CODE(Self->Stream, i) IS ESC_PARAGRAPH_START)) { - - if (ESCAPE_CODE(Self->Stream, i) IS ESC_PARAGRAPH_START) { - // Check if a custom string is specified in the paragraph, in which case the paragraph counts - // as content. - - auto para = escape_data(Self->Stream, i); - if (para->CustomString) break; - } - - bottomline = l->paragraph_y; - break; - } - else if ((ESCAPE_CODE(Self->Stream, i) IS ESC_OBJECT) or (ESCAPE_CODE(Self->Stream, i) IS ESC_TABLE_END)) break; // Content encountered - - PREV_CHAR(Self->Stream, i); - } - else break; // Content encountered - } - } - - l->paragraph_y = bottomline; - - // Paragraph gap measured as default line height * spacing ratio - - new_y = bottomline + F2I(Self->LineHeight * Spacing); - if (new_y > l->cursory) l->cursory = new_y; - } - - // Reset line management variables for a new line starting from the left margin. - - l->line_x = l->left_margin; - l->cursorx = l->left_margin; - l->line_height = 0; - l->base_line = 0; - l->split_start = Self->SegCount; - l->line_index = RestartIndex; - l->wordindex = l->line_index; - l->kernchar = 0; - l->wordwidth = 0; - l->paragraph_end = 0; - LAYOUT_LOGRETURN(); -} - -//******************************************************************************************************************** -// Word-wrapping is checked whenever whitespace is encountered or certain escape codes are found in the text stream, -// e.g. paragraphs and objects will mark an end to the current word. -// -// Wrapping is always checked even if there is no 'active word' because we need to be able to wrap empty lines (e.g. -// solo
    tags). -// -// Index - The current index value. -// ObjectIndex - The index that indicates the start of the word. - -static UBYTE check_wordwrap(CSTRING Type, extDocument *Self, LONG Index, layout *l, LONG X, LONG *Width, - LONG ObjectIndex, LONG *GraphicX, LONG *GraphicY, LONG GraphicWidth, LONG GraphicHeight) -{ - pf::Log log(__FUNCTION__); - LONG minwidth; - UBYTE result; - LONG breakloop; - - if (!Self->BreakLoop) return WRAP_DONOTHING; - - // If the width of the object is larger than the available page width, extend the size of the page. - -/* - if (GraphicWidth > *Width - l->left_margin - l->right_margin) { - *Width = GraphicWidth + l->left_margin + l->right_margin; - return WRAP_EXTENDPAGE; - } -*/ - - // This code pushes the object along to the next available space when a boundary is encountered on the current line. - - WRAP("~check_wrap()","Index: %d/%d, %s: %dx%d,%dx%d, LineHeight: %d, Cursor: %dx%d, PageWidth: %d, Edge: %d", Index, ObjectIndex, Type, *GraphicX, *GraphicY, GraphicWidth, GraphicHeight, l->line_height, l->cursorx, l->cursory, *Width, l->wrapedge); - - result = WRAP_DONOTHING; - breakloop = MAXLOOP; - -restart: - l->alignwidth = l->wrapedge; - - if (Self->TotalClips > 0) check_clips(Self, Index, l, ObjectIndex, GraphicX, GraphicY, GraphicWidth, GraphicHeight); - - if (*GraphicX + GraphicWidth > l->wrapedge) { - if ((*Width < WIDTH_LIMIT) and ((*GraphicX IS l->left_margin) or (l->nowrap))) { - // Force an extension of the page width and recalculate from scratch - minwidth = *GraphicX + GraphicWidth + l->right_margin - X; - if (minwidth > *Width) { - *Width = minwidth; - WRAP("check_wrap:","Forcing an extension of the page width to %d", minwidth); - } - else *Width += 1; - WRAP_LOGRETURN(); - return WRAP_EXTENDPAGE; - } - else { - if (!l->line_height) { - l->line_height = 1; //l->font->LineSpacing; - l->base_line = 1; //l->font->Ascent; - } - - if (l->link) { - if (l->link_x IS *GraphicX) { - // If the link starts with the object, the link itself is going to be wrapped with it - } - else { - add_link(Self, ESC_LINK, l->link, l->link_x, *GraphicY, *GraphicX - l->link_x, l->line_height, "check_wrap"); - } - } - - // Set the line segment up to the object index. The line_index is - // updated so that this process only occurs in the first iteration. - - if (l->line_index < ObjectIndex) { - add_drawsegment(Self, l->line_index, ObjectIndex, l, *GraphicY, *GraphicX - l->line_x, l->alignwidth - l->line_x, "DoWrap"); - l->line_index = ObjectIndex; - } - - // Reset the line management variables so that the next line starts at the left margin. - - *GraphicX = l->left_margin; - *GraphicY += l->line_height; - l->cursorx = *GraphicX; - l->cursory = *GraphicY; - l->split_start = Self->SegCount; - l->line_x = l->left_margin; - l->link_x = l->left_margin; // Only matters if a link is defined - l->kernchar = 0; - l->base_line = 0; - l->line_height = 0; - - result = WRAP_WRAPPED; - if (--breakloop > 0) goto restart; // Go back and check the clip boundaries again - else { - log.traceWarning("Breaking out of continuous loop."); - Self->Error = ERR_Loop; - } - } - } - - // No wrap has occurred - - if ((l->link) and (l->link_open IS FALSE)) { - // A link is due to be closed - add_link(Self, ESC_LINK, l->link, l->link_x, *GraphicY, *GraphicX + GraphicWidth - l->link_x, l->line_height ? l->line_height : l->font->LineSpacing, "check_wrap"); - l->link = NULL; - } - - #ifdef DBG_WORDWRAP - if (result IS WRAP_WRAPPED) WRAP("check_wrap","A wrap to Y coordinate %d has occurred.", l->cursory); - #endif - - WRAP_LOGRETURN(); - return result; -} - -static void check_clips(extDocument *Self, LONG Index, layout *l, - LONG ObjectIndex, LONG *GraphicX, LONG *GraphicY, LONG GraphicWidth, LONG GraphicHeight) -{ - LONG clip, i, height; - UBYTE reset_link; - - WRAP("~check_clips()","Index: %d-%d, ObjectIndex: %d, Graphic: %dx%d,%dx%d, TotalClips: %d", l->line_index, Index, ObjectIndex, *GraphicX, *GraphicY, GraphicWidth, GraphicHeight, Self->TotalClips); - - for (clip=l->start_clips; clip < Self->TotalClips; clip++) { - if (Self->Clips[clip].Transparent) continue; - if (*GraphicY + GraphicHeight < Self->Clips[clip].Clip.Top) continue; - if (*GraphicY >= Self->Clips[clip].Clip.Bottom) continue; - if (*GraphicX >= Self->Clips[clip].Clip.Right) continue; - if (*GraphicX + GraphicWidth < Self->Clips[clip].Clip.Left) continue; - - if (Self->Clips[clip].Clip.Left < l->alignwidth) l->alignwidth = Self->Clips[clip].Clip.Left; - - WRAP("check_clips:","Word: \"%.20s\" (%dx%d,%dx%d) advances over clip %d-%d", - printable(Self->Stream+ObjectIndex, 60), *GraphicX, *GraphicY, GraphicWidth, GraphicHeight, - Self->Clips[clip].Clip.Left, Self->Clips[clip].Clip.Right); - - // Set the line segment up to the encountered boundary and continue checking the object position against the - // clipping boundaries. - - if ((l->link) and (Self->Clips[clip].Index < l->link_index)) { - // An open link intersects with a clipping region that was created prior to the opening of the link. We do - // not want to include this object as a clickable part of the link - we will wrap over or around it, so - // set a partial link now and ensure the link is reopened after the clipping region. - - WRAP("~check_clips","Setting hyperlink now to cross a clipping boundary."); - - if (!l->line_height) height = l->font->LineSpacing; - else height = l->line_height; - add_link(Self, ESC_LINK, l->link, l->link_x, *GraphicY, *GraphicX + GraphicWidth - l->link_x, height, "clip_intersect"); - - WRAP_LOGRETURN(); - - reset_link = TRUE; - } - else reset_link = FALSE; - - // Advance the object position. We break if a wordwrap is required - the code outside of this loop will detect - // the need for a wordwrap and then restart the wordwrapping process. - - if (*GraphicX IS l->line_x) l->line_x = Self->Clips[clip].Clip.Right; - *GraphicX = Self->Clips[clip].Clip.Right; // Push the object over the clip boundary - - if (*GraphicX + GraphicWidth > l->wrapedge) { - WRAP("check_clips:","Wrapping-Break: X(%d)+Width(%d) > Edge(%d) at clip '%s' %dx%d,%dx%d", *GraphicX, GraphicWidth, l->wrapedge, Self->Clips[clip].Name, Self->Clips[clip].Clip.Left, Self->Clips[clip].Clip.Top, Self->Clips[clip].Clip.Right, Self->Clips[clip].Clip.Bottom); - break; - } - - if ((GraphicWidth) and (ObjectIndex >= 0)) i = ObjectIndex; - else i = Index; - - if (l->line_index < i) { - if (!l->line_height) { - add_drawsegment(Self, l->line_index, i, l, *GraphicY, *GraphicX - l->line_x, *GraphicX - l->line_x, "Wrap:EmptyLine"); - } - else add_drawsegment(Self, l->line_index, i, l, *GraphicY, *GraphicX + GraphicWidth - l->line_x, l->alignwidth - l->line_x, "Wrap"); - } - - WRAP("check_clips","Line index reset to %d, previously %d", i, l->line_index); - - l->line_index = i; - l->line_x = *GraphicX; - if ((reset_link) and (l->link)) l->link_x = *GraphicX; - - clip = l->start_clips-1; // Check all the clips from the beginning - } - - WRAP_LOGRETURN(); -} - -//******************************************************************************************************************** -// Calculate the position, pixel length and height of each line for the entire page. This function does not recurse, -// but it reiterates if the size of the page section is expanded. It is also called for individual table cells -// which are treated as miniature pages. -// -// Offset: The byte offset within the document stream to start layout processing. -// X/Y: Section coordinates, starts at 0,0 for the main page, subsequent sections (table cells) can be at any location, measured as absolute to the top left corner of the page. -// Width: Minimum width of the page/section. Can be increased if insufficient space is available. Includes the left and right margins in the resulting calculation. -// Height: Minimum height of the page/section. Will be increased to match the number of lines in the layout. -// Margins: Margins within the page area. These are inclusive to the resulting page width/height. If in a cell, margins reflect cell padding values. - -struct LAYOUT_STATE { - layout Layout; - LONG Index; - LONG TotalClips; - LONG TotalLinks; - LONG SegCount; - LONG ECIndex; - - LAYOUT_STATE() { - Index = 0; - TotalClips = 0; - TotalLinks = 0; - SegCount = 0; - ECIndex = 0; - } -}; - -#define SAVE_STATE(s) \ - CopyMemory(&l, &s.Layout, sizeof(l)); \ - s.Index = i; \ - s.TotalClips = Self->TotalClips; \ - s.TotalLinks = Self->TotalLinks; \ - s.ECIndex = Self->ECIndex; \ - s.SegCount = Self->SegCount; - -// You must execute a goto to the point at which SAVE_STATE() was used after calling this macro - -#define RESTORE_STATE(s) \ - restore_state(Self, s); \ - l = (s)->Layout; \ - i = (s)->Index; - -INLINE void restore_state(extDocument *Self, LAYOUT_STATE *State) -{ - LAYOUT("layout_restore:","Restoring earlier layout state to index %d", State->Index); - - Self->TotalClips = State->TotalClips; - Self->TotalLinks = State->TotalLinks; - Self->SegCount = State->SegCount; - Self->ECIndex = State->ECIndex; -} - -static LONG layout_section(extDocument *Self, LONG Offset, objFont **Font, - LONG AbsX, LONG AbsY, LONG *Width, LONG *Height, - LONG LeftMargin, LONG TopMargin, LONG RightMargin, LONG BottomMargin, BYTE *VerticalRepass) -{ - pf::Log log(__FUNCTION__); - layout l; - escFont *style; - escAdvance *advance; - escObject *escobj; - escList *esclist; - escCell *esccell; - escRow *escrow, *lastrow; - DocEdit *edit; - escTable *esctable; - escParagraph *escpara; - LAYOUT_STATE tablestate, rowstate, liststate; - LONG start_ecindex, start_links, start_SegCount, unicode, i, j, page_height, lastheight, lastwidth, edit_segment; - UBYTE checkwrap; - BYTE object_vertical_repass; - - if ((!Self->Stream) or (!Self->Stream[Offset]) or (!Font)) { - log.trace("No document stream to be processed."); - return 0; - } - - if (Self->Depth >= MAX_DEPTH) { - log.trace("Depth limit exceeded (too many tables-within-tables)."); - return 0; - } - - start_links = Self->TotalLinks; - start_SegCount = Self->SegCount; - l.start_clips = Self->TotalClips; - start_ecindex = Self->ECIndex; - page_height = *Height; - object_vertical_repass = FALSE; - - *VerticalRepass = FALSE; - - LAYOUT("~layout_section()","Dimensions: %dx%d,%dx%d (edge %d), LM %d RM %d TM %d BM %d", - AbsX, AbsY, *Width, *Height, AbsX + *Width - RightMargin, - LeftMargin, RightMargin, TopMargin, BottomMargin); - - Self->Depth++; - -extend_page: - if (*Width > WIDTH_LIMIT) { - LAYOUT("layout_section:","Restricting page width from %d to %d", *Width, WIDTH_LIMIT); - *Width = WIDTH_LIMIT; - if (Self->BreakLoop > 4) Self->BreakLoop = 4; // Very large page widths normally means that there's a parsing problem - } - - if (Self->Error) { - Self->Depth--; - LAYOUT_LOGRETURN(); - return 0; - } - else if (!Self->BreakLoop) { - Self->Error = ERR_Loop; - Self->Depth--; - LAYOUT_LOGRETURN(); - return 0; - } - Self->BreakLoop--; - - Self->TotalLinks = start_links; // Also refer to SAVE_STATE() and restore_state() - Self->SegCount = start_SegCount; - Self->TotalClips = l.start_clips; - Self->ECIndex = start_ecindex; - - lastrow = NULL; // For table management - lastwidth = *Width; - lastheight = page_height; - esclist = NULL; - escrow = NULL; - esctable = NULL; - escpara = NULL; - edit = NULL; - esccell = NULL; - style = NULL; - edit_segment = 0; - checkwrap = FALSE; // TRUE if a wordwrap or collision check is required - l.anchor = FALSE; // TRUE if in an anchored section (objects are anchored to the line) - l.alignflags = 0; // Current alignment settings according to the font style - l.link = NULL; - l.paragraph_y = 0; - l.paragraph_end = 0; - l.line_increase = 0; - l.len = 0; - l.left_margin = AbsX + LeftMargin; - l.right_margin = RightMargin; // Retain the right margin in an adjustable variable, in case we adjust the margin - l.wrapedge = AbsX + *Width - l.right_margin; - l.alignwidth = l.wrapedge; - l.cursorx = AbsX + LeftMargin; // The absolute position of the cursor - l.cursory = AbsY + TopMargin; - l.wordwidth = 0; // The pixel width of the current word. Zero if no word is being worked on - l.wordindex = -1; // A byte index in the stream, for the word currently being operated on - l.line_index = Offset; // The starting index of the line we are operating on - l.line_x = AbsX + LeftMargin; - l.line_height = 0; - l.base_line = 0; - l.kernchar = 0; // Previous character of the word being operated on - l.link_x = 0; - l.link_index = 0; - l.split_start = Self->SegCount; // Set to the previous line index if line is segmented. Used for ensuring that all distinct entries on the line use the same line height - l.font = *Font; - l.nowrap = FALSE; // TRUE if word wrapping is to be turned off - l.link_open = FALSE; - l.setsegment = FALSE; - l.textcontent = FALSE; - l.spacewidth = fntCharWidth(l.font, ' ', 0, NULL); - - i = Offset; - - while (1) { - // For certain graphics-related escape codes, set the line segment up to the encountered escape code if the text - // string will be affected (e.g. if the string will be broken up due to a clipping region etc). - - if (Self->Stream[i] IS CTRL_CODE) { - // Any escape code that sets l.setsegment to TRUE in its case routine, must set breaksegment to TRUE now so - // that any textual content can be handled immediately. - // - // This is done particular for escape codes that can be treated as wordwrap breaks. - - if (l.line_index < i) { - BYTE breaksegment; - breaksegment = 0; - switch (ESCAPE_CODE(Self->Stream, i)) { - case ESC_ADVANCE: - case ESC_TABLE_START: - breaksegment = 1; - break; - - case ESC_FONT: - if (l.textcontent) { - style = escape_data(Self->Stream, i); - objFont *font = lookup_font(style->Index, "ESC_FONT"); - if (l.font != font) breaksegment = 1; - } - break; - - case ESC_OBJECT: - escobj = escape_data(Self->Stream, i); - if (escobj->Graphical) breaksegment = 1; - break; - - case ESC_INDEX_START: { - auto index = escape_data(Self->Stream, i); - if (!index->Visible) breaksegment = 1; - break; - } - } - - if (breaksegment) { - LAYOUT("~layout_section:","Setting line at escape '%s', index %d, line_x: %d, wordwidth: %d", strCodes[(UBYTE)ESCAPE_CODE(Self->Stream,i)], l.line_index, l.line_x, l.wordwidth); - l.cursorx += l.wordwidth; - add_drawsegment(Self, l.line_index, i, &l, l.cursory, l.cursorx - l.line_x, l.alignwidth - l.line_x, "Esc:Object"); - RESET_SEGMENT_WORD(i, l.cursorx, &l); - l.alignwidth = l.wrapedge; - LAYOUT_LOGRETURN(); - } - } - } - - // Wordwrap checking. Any escape code that results in a word-break for the current word will initiate a wrapping - // check. Encountering whitespace also results in a wrapping check. - - if (esctable) { - l.alignwidth = l.wrapedge; - } - else { - if (Self->Stream[i] IS CTRL_CODE) { - switch (ESCAPE_CODE(Self->Stream, i)) { - // These escape codes cause wrapping because they can break up words - - case ESC_PARAGRAPH_START: - case ESC_PARAGRAPH_END: - case ESC_TABLE_END: - case ESC_OBJECT: - case ESC_ADVANCE: - case ESC_LINK_END: - checkwrap = TRUE; - break; - - default: - l.alignwidth = l.wrapedge; - break; - } - } - else if (Self->Stream[i] > 0x20) { - // Non-whitespace characters do not result in a wordwrap check - l.alignwidth = l.wrapedge; - } - else checkwrap = TRUE; - - if (checkwrap) { - LONG wrap_result; - - checkwrap = FALSE; - - wrap_result = check_wordwrap("Text", Self, i, &l, AbsX, Width, l.wordindex, &l.cursorx, &l.cursory, (l.wordwidth < 1) ? 1 : l.wordwidth, (l.line_height < 1) ? 1 : l.line_height); - - if (wrap_result IS WRAP_EXTENDPAGE) { - LAYOUT("layout_section:","Expanding page width on wordwrap request."); - goto extend_page; - } - else if ((Self->Stream[i] IS '\n') and (wrap_result IS WRAP_WRAPPED)) { - // The presence of the line-break must be ignored, due to word-wrap having already made the new line for us - i++; - l.line_index = i; - continue; - } - } - } - - // Break the loop if there are no more characters to process - - if (!Self->Stream[i]) break; - - if (Self->Stream[i] IS CTRL_CODE) { - // Escape code encountered. The escape code format is: - // ESC,Code,Length,Data,Length,ESC - -#ifdef DBG_LAYOUT_ESCAPE - LAYOUT("layout_section","ESC_%s: %p, Index: %d-%d-%d, Length: %d, WordWidth: %d", strCodes[ESCAPE_CODE(Self->Stream, i)], esctable, l.line_index, i, l.wordindex, ESCAPE_LEN(Self->Stream+i), l.wordwidth); -#endif - l.setsegment = FALSE; // Escape codes that draw something in draw_document() (e.g. object, table) should set this flag to TRUE in their case statement - l.len = ESCAPE_LEN(Self->Stream+i); - switch (ESCAPE_CODE(Self->Stream, i)) { - case ESC_ADVANCE: - advance = escape_data(Self->Stream, i); - l.cursorx += advance->X; - l.cursory += advance->Y; - if (advance->X) { - RESET_SEGMENT_WORD(i, l.cursorx, &l); - } - break; - - case ESC_FONT: - style = escape_data(Self->Stream, i); - l.font = lookup_font(style->Index, "ESC_FONT"); - - if (l.font) { - if (style->Options & FSO_ALIGN_RIGHT) l.font->Align = ALIGN_RIGHT; - else if (style->Options & FSO_ALIGN_CENTER) l.font->Align = ALIGN_HORIZONTAL; - else l.font->Align = 0; - - if (style->Options & FSO_ANCHOR) l.anchor = TRUE; - else l.anchor = FALSE; - - if (style->Options & FSO_NO_WRAP) { - l.nowrap = TRUE; - //wrapedge = 1000; - } - else l.nowrap = FALSE; - - LAYOUT("layout_section:","Font Index: %d, LineSpacing: %d, Height: %d, Ascent: %d, Cursor: %dx%d", style->Index, l.font->LineSpacing, l.font->Height, l.font->Ascent, l.cursorx, l.cursory); - l.spacewidth = fntCharWidth(l.font, ' ', 0, 0); - - // Treat the font as if it is a text character by setting the wordindex. This ensures it is included in the drawing process - - if (!l.wordwidth) l.wordindex = i; - } - else LAYOUT("layout_section:","ESC_FONT: Unable to lookup font using style index %d.", style->Index); - - break; - - case ESC_INDEX_START: { - // Indexes don't do anything, but recording the cursor's Y value when they are encountered - // makes it really easy to scroll to a bookmark when requested (show_bookmark()). - - LONG end; - auto escindex = escape_data(Self->Stream, i); - escindex->Y = l.cursory; - - if (!escindex->Visible) { - // If Visible is false, then all content within the index is not to be displayed - - end = i; - while (Self->Stream[end]) { - if (Self->Stream[end] IS CTRL_CODE) { - if (ESCAPE_CODE(Self->Stream, end) IS ESC_INDEX_END) { - escIndexEnd *iend = escape_data(Self->Stream, end); - if (iend->ID IS escindex->ID) break; - } - } - - NEXT_CHAR(Self->Stream, end); - } - - if (Self->Stream[end] IS 0) { - log.warning("Failed to find matching index-end. Document stream is corrupt."); - goto exit; - } - - NEXT_CHAR(Self->Stream, end); - - // Do some cleanup work to complete the content skip. NB: There is some code associated with this at - // the top of this routine, with breaksegment = 1. - - l.line_index = end; - i = end; - l.len = 0; - } - - break; - } - - case ESC_SETMARGINS: { - auto escmargins = escape_data(Self->Stream, i); - - if (escmargins->Left != 0x7fff) { - l.cursorx += escmargins->Left; - l.line_x += escmargins->Left; - l.left_margin += escmargins->Left; - } - - if (escmargins->Right != 0x7fff) { - l.right_margin += escmargins->Right; - l.alignwidth -= escmargins->Right; - l.wrapedge -= escmargins->Right; - } - - if (escmargins->Top != 0x7fff) { - if (l.cursory < AbsY + escmargins->Top) l.cursory = AbsY + escmargins->Top; - } - - if (escmargins->Bottom != 0x7fff) { - BottomMargin += escmargins->Bottom; - if (BottomMargin < 0) BottomMargin = 0; - } - break; - } - - // LINK MANAGEMENT - - case ESC_LINK: { - if (l.link) { - // Close the currently open link because it's illegal to have a link embedded within a link. - - if (l.font) { - add_link(Self, ESC_LINK, l.link, l.link_x, l.cursory, l.cursorx + l.wordwidth - l.link_x, l.line_height ? l.line_height : l.font->LineSpacing, "esc_link"); - } - } - - l.link = escape_data(Self->Stream, i); - l.link_x = l.cursorx + l.wordwidth; - l.link_index = i; - l.link_open = TRUE; - l.link_align = l.font->Align; - break; - } - - case ESC_LINK_END: { - // We don't call add_link() unless the entire word that contains the link has - // been processed. This is necessary due to the potential for a word-wrap. - - if (l.link) { - l.link_open = FALSE; - - if (l.wordwidth < 1) { - add_link(Self, ESC_LINK, l.link, l.link_x, l.cursory, l.cursorx - l.link_x, l.line_height ? l.line_height : l.font->LineSpacing, "esc_link_end"); - l.link = NULL; - } - } - - break; - } - - // LIST MANAGEMENT - - case ESC_LIST_START: - // This is the start of a list. Each item in the list will be identified by ESC_PARAGRAPH codes. The - // cursor position is advanced by the size of the item graphics element. - - SAVE_STATE(liststate); - - if (esclist) { - auto ptr = esclist; - esclist = escape_data(Self->Stream, i); - esclist->Stack = ptr; - } - else { - esclist = escape_data(Self->Stream, i); - esclist->Stack = NULL; - } -list_repass: - esclist->Repass = FALSE; - break; - - case ESC_LIST_END: - // If it is a custom list, a repass is required - - if ((esclist) and (esclist->Type IS LT_CUSTOM) and (esclist->Repass)) { - LAYOUT("esc_list","Repass for list required, commencing..."); - RESTORE_STATE(&liststate); - goto list_repass; - } - - if (esclist) { - esclist = esclist->Stack; - } - - // At the end of a list, increase the whitespace to that of a standard paragraph. - - if (!esclist) { - if (escpara) end_line(Self, &l, NL_PARAGRAPH, i, escpara->VSpacing, i, "Esc:ListEnd"); - else end_line(Self, &l, NL_PARAGRAPH, i, 1.0, i, "Esc:ListEnd"); - } - - break; - - // EMBEDDED OBJECT MANAGEMENT - - case ESC_OBJECT: { - SurfaceClip cell; - OBJECTID object_id; - - // Tell the object our CursorX and CursorY positions so that it can position itself within the stream - // layout. The object will tell us its clipping boundary when it returns (if it has a clipping boundary). - - auto escobj = escape_data(Self->Stream, i); - if (!(object_id = escobj->ObjectID)) break; - if (!escobj->Graphical) break; // Do not bother with objects that do not draw anything - if (escobj->Owned) break; // Do not manipulate objects that have owners - - // cell: Reflects the page/cell coordinates and width/height of the page/cell. - -//wrap_object: - cell.Left = AbsX; - cell.Top = AbsY; - cell.Right = cell.Left + *Width; - if ((!Offset) and (page_height < Self->AreaHeight)) cell.Bottom = AbsY + Self->AreaHeight; // The reported page height cannot be shorter than the document's surface area - else cell.Bottom = AbsY + page_height; - - if (l.line_height) { - if (cell.Bottom < l.cursory + l.line_height) cell.Bottom = AbsY + l.line_height; - } - else if (cell.Bottom < l.cursory + 1) cell.Bottom = l.cursory + 1; - -/* - LONG width_check = 0; - LONG dimensions = 0; - LONG layoutflags = 0; - if (!(error = AccessObject(object_id, 5000, &object))) { - LAYOUT("layout_object:","[Idx:%d] The %s's available page area is %d-%d,%d-%d, margins %dx%d,%d, cursor %dx%d", i, object->Class->ClassName, cell.Left, cell.Right, cell.Top, cell.Bottom, l.left_margin-AbsX, l.right_margin, TopMargin, l.cursorx, l.cursory); - - LONG cellwidth, cellheight, align, leftmargin, lineheight, zone_height; - OBJECTID layout_surface_id; - - if ((FindField(object, FID_LayoutSurface, NULL)) and (!object->get(FID_LayoutSurface, &layout_surface_id))) { - objSurface *surface; - LONG new_x, new_y, new_width, new_height, calc_x; - - // This layout method is used for objects that do not have a Layout object for graphics management and - // simply rely on a Surface object instead. - - if (!(error = AccessObject(layout_surface_id, 3000, &surface))) { - leftmargin = l.left_margin - AbsX; - lineheight = (l.base_line) ? l.base_line : l.font->Ascent; - - cellwidth = cell.Right - cell.Left; - cellheight = cell.Bottom - cell.Top; - align = l.font->Align | surface->Align; - - // Relative dimensions can use the full size of the page/cell only when text-wrapping is disabled. - - zone_height = lineheight; - cell.Left += leftmargin; - cellwidth = cellwidth - l.right_margin - leftmargin; // Remove margins from the cellwidth because we're only interested in the space available to the object - new_x = l.cursorx; - - // WIDTH - - if (surface->Dimensions & DMF_RELATIVE_WIDTH) { - new_width = (DOUBLE)cellwidth * (DOUBLE)surface->WidthPercent * 0.01; - if (new_width < 1) new_width = 1; - else if (new_width > cellwidth) new_width = cellwidth; - } - else if (surface->Dimensions & DMF_FIXED_WIDTH) new_width = surface->Width; - else if ((surface->Dimensions & DMF_X) and (surface->Dimensions & DMF_X_OFFSET)) { - // Calculate X boundary - - calc_x = new_x; - - if (surface->Dimensions & DMF_FIXED_X); - else if (surface->Dimensions & DMF_RELATIVE_X) { - // Relative X, such as 10% would mean 'NewX must be at least 10% beyond 'cell.left + leftmargin' - LONG minx; - minx = cell.Left + F2T((DOUBLE)cellwidth * (DOUBLE)surface->XPercent * 0.01); - if (minx > calc_x) calc_x = minx; - } - else calc_x = l.cursorx; - - // Calculate width - - if (surface->Dimensions & DMF_FIXED_X_OFFSET) new_width = cellwidth - surface->XOffset - (calc_x - cell.Left); - else new_width = cellwidth - (calc_x - cell.Left) - (cellwidth * surface->XOffsetPercent * 0.01); - - if (new_width < 1) new_width = 1; - else if (new_width > cellwidth) new_width = cellwidth; - } - else { - LAYOUT("@layout_obj","No width specified for %s #%d (dimensions $%x), defaulting to 1 pixel.", object->Class->ClassName, object->UID, surface->Dimensions); - new_width = 1; - } - - // X COORD - - if ((align & ALIGN_HORIZONTAL) and (surface->Dimensions & DMF_WIDTH)) { - new_x = new_x + ((cellwidth - new_width)/2); - } - else if ((align & ALIGN_RIGHT) and (surface->Dimensions & DMF_WIDTH)) { - new_x = (AbsX + *Width) - l.right_margin - new_width; - } - else if (surface->Dimensions & DMF_RELATIVE_X) { - new_x += F2T(surface->XPercent * cellwidth * 0.01); - } - else if ((surface->Dimensions & DMF_WIDTH) and (surface->Dimensions & DMF_X_OFFSET)) { - if (surface->Dimensions & DMF_FIXED_X_OFFSET) { - new_x += (cellwidth - new_width - surface->XOffset); - } - else new_x += F2T((DOUBLE)cellwidth - (DOUBLE)new_width - ((DOUBLE)cellwidth * (DOUBLE)surface->XOffsetPercent * 0.01)); - } - else if (surface->Dimensions & DMF_FIXED_X) { - new_x += surface->X; - } - - // HEIGHT - - if (surface->Dimensions & DMF_RELATIVE_HEIGHT) { - // If the object is inside a paragraph

    section, the height will be calculated based - // on the current line height. Otherwise, the height is calculated based on the cell/page - // height. - - new_height = (DOUBLE)zone_height * (DOUBLE)surface->HeightPercent * 0.01; - if (new_height > zone_height) new_height = zone_height; - } - else if (surface->Dimensions & DMF_FIXED_HEIGHT) { - new_height = surface->Height; - } - else if ((surface->Dimensions & DMF_Y) and - (surface->Dimensions & DMF_Y_OFFSET)) { - if (surface->Dimensions & DMF_FIXED_Y) new_y = surface->Y; - else if (surface->Dimensions & DMF_RELATIVE_Y) new_y = F2T((DOUBLE)zone_height * (DOUBLE)surface->YPercent * 0.01); - else new_y = l.cursory; - - if (surface->Dimensions & DMF_FIXED_Y_OFFSET) new_height = zone_height - surface->YOffset; - else new_height = zone_height - F2T((DOUBLE)zone_height * (DOUBLE)surface->YOffsetPercent * 0.01); - - if (new_height > zone_height) new_height = zone_height; - } - else new_height = lineheight; - - if (new_height < 1) new_height = 1; - - // Y COORD - - if (layoutflags & LAYOUT_IGNORE_CURSOR) new_y = cell.Top; - else new_y = l.cursory; - - if (surface->Dimensions & DMF_RELATIVE_Y) { - new_y += F2T(surface->YPercent * lineheight * 0.01); - } - else if ((surface->Dimensions & DMF_HEIGHT) and - (surface->Dimensions & DMF_Y_OFFSET)) { - if (surface->Dimensions & DMF_FIXED_Y_OFFSET) new_y = cell.Top + F2T(zone_height - surface->Height - surface->YOffset); - else new_y += F2T((DOUBLE)zone_height - (DOUBLE)surface->Height - ((DOUBLE)zone_height * (DOUBLE)surface->YOffsetPercent * 0.01)); - } - else if (surface->Dimensions & DMF_Y_OFFSET) { - // This section resolves situations where no explicit Y coordinate has been defined, - // but the Y offset has been defined. This means we leave the existing Y coordinate as-is and - // adjust the height. - - if (surface->Dimensions & DMF_FIXED_Y_OFFSET) new_height = zone_height - surface->YOffset; - else new_height = zone_height - F2T((DOUBLE)zone_height * (DOUBLE)surface->YOffsetPercent * 0.01); - - if (new_height < 1) new_height = 1; - if (new_height > zone_height) new_height = zone_height; - } - else if (surface->Dimensions & DMF_FIXED_Y) { - new_y += surface->Y; - } - - // Set the clipping - - LAYOUT("layout_object","Clip region is being restricted to the bounds: %dx%d,%dx%d", new_x, new_y, new_width, new_height); - - cell.Left = new_x; - cell.Top = new_y; - cell.Right = new_x + new_width; - cell.Bottom = new_y + new_height; - - // If LAYOUT_RIGHT is set, no text may be printed to the right of the object. This has no impact - // on the object's bounds. - - if (layoutflags & LAYOUT_RIGHT) { - LAYOUT("layout_object","LAYOUT_RIGHT: Expanding clip.right boundary from %d to %d.", cell.Right, AbsX + *Width - l.right_margin); - cell.Right = (AbsX + *Width) - l.right_margin; //cellwidth; - } - - // If LAYOUT_LEFT is set, no text may be printed to the left of the object (but not - // including text that has already been printed). This has no impact on the object's - // bounds. - - if (layoutflags & LAYOUT_LEFT) { - LAYOUT("layout_object","LAYOUT_LEFT: Expanding clip.left boundary from %d to %d.", cell.Left, AbsX); - cell.Left = AbsX; //leftmargin; - } - - if (layoutflags & LAYOUT_IGNORE_CURSOR) width_check = cell.Right - AbsX; - else width_check = cell.Right + l.right_margin; - - LAYOUT("layout_object","#%d, Pos: %dx%d,%dx%d, Align: $%.8x, From: %dx%d,%dx%d,%dx%d, WidthCheck: %d/%d", object->UID, new_x, new_y, new_width, new_height, align, F2T(surface->X), F2T(surface->Y), F2T(surface->Width), F2T(surface->Height), F2T(surface->XOffset), F2T(surface->YOffset), width_check, *Width); - LAYOUT("layout_object","Clip Size: %dx%d,%dx%d, LineHeight: %d, LayoutFlags: $%.8x", cell.Left, cell.Top, cellwidth, cellheight, lineheight, layoutflags); - - dimensions = surface->Dimensions; - error = ERR_Okay; - - acRedimension(surface, new_x, new_y, 0, new_width, new_height, 0); - - ReleaseObject(surface); - } - else { - dimensions = 0; - } - } - else if ((FindField(object, FID_Layout, NULL)) and (!object->getPtr(FID_Layout, &layout))) { - leftmargin = l.left_margin - AbsX; - lineheight = (l.base_line) ? l.base_line : l.font->Ascent; - - cellwidth = cell.Right - cell.Left; - cellheight = cell.Bottom - cell.Top; - align = l.font->Align | layout->Align; - - layoutflags = layout->Layout; - - if (layoutflags & (LAYOUT_BACKGROUND|LAYOUT_TILE)) { - // In background mode, the bounds are adjusted to match the size of the cell - // if the object supports GraphicWidth and GraphicHeight. For all other objects, - // it is assumed that the bounds have been preset. - // - // Positioning within the cell bounds is managed by the GraphicX/Y/Width/Height and - // Align fields. - // - // Gaps are automatically worked into the calculated X/Y value. - - if ((layout->GraphicWidth) and (layout->GraphicHeight) and (!(layoutflags & LAYOUT_TILE))) { - layout->BoundX = cell.Left; - layout->BoundY = cell.Top; - - if (align & ALIGN_HORIZONTAL) { - layout->GraphicX = cell.Left + layout->LeftMargin + ((cellwidth - layout->GraphicWidth)>>1); - } - else if (align & ALIGN_RIGHT) layout->GraphicX = cell.Left + cellwidth - layout->RightMargin - layout->GraphicWidth; - else if (!layout->PresetX) { - if (!layout->PresetWidth) { - layout->GraphicX = cell.Left + layout->LeftMargin; - } - else layout->GraphicX = l.cursorx + layout->LeftMargin; - } - - if (align & ALIGN_VERTICAL) layout->GraphicY = cell.Top + ((cellheight - layout->TopMargin - layout->BottomMargin - F2T(layout->GraphicHeight))>>1); - else if (align & ALIGN_BOTTOM) layout->GraphicY = cell.Top + cellheight - layout->BottomMargin - layout->GraphicHeight; - else if (!layout->PresetY) { - if (!layout->PresetHeight) { - layout->GraphicY = cell.Top + layout->TopMargin; - } - else layout->GraphicY = l.cursory + layout->TopMargin; - } - - // The object bounds are set to the GraphicWidth/Height. When the object is drawn, - // the bounds will be automatically restricted to the size of the cell (or page) so - // that there is no over-draw. - - layout->BoundWidth = layout->GraphicWidth; - layout->BoundHeight = layout->GraphicHeight; - - LAYOUT("layout_object","X/Y: %dx%d, W/H: %dx%d (Width/Height are preset)", layout->BoundX, layout->BoundY, layout->BoundWidth, layout->BoundHeight); - } - else { - // If the object does not use preset GraphicWidth and GraphicHeight, then - // we just want to use the preset X/Y/Width/Height in relation to the available - // space within the cell. - - layout->ParentSurface.Width = cell.Right - cell.Left; - layout->ParentSurface.Height = cell.Bottom - cell.Top; - - object->get(FID_X, &layout->BoundX); - object->get(FID_Y, &layout->BoundY); - object->get(FID_Width, &layout->BoundWidth); - object->get(FID_Height, &layout->BoundHeight); - - layout->BoundX += cell.Left; - layout->BoundY += cell.Top; - - - LAYOUT("layout_object","X/Y: %dx%d, W/H: %dx%d, Parent W/H: %dx%d (Width/Height not preset), Dimensions: $%.8x", layout->BoundX, layout->BoundY, layout->BoundWidth, layout->BoundHeight, layout->ParentSurface.Width, layout->ParentSurface.Height, layout->Dimensions); - } - - dimensions = layout->Dimensions; - error = ERR_NothingDone; // Do not add a clipping region because the graphic is in the background - } - else { - // The object can extend the line's height if the GraphicHeight is larger than the line. - // - // Alignment calculations are restricted to this area, which forms the initial Bounds*: - // - // X: CursorX - // Y: CursorY - // Right: PageWidth - RightMargin - // Bottom: LineHeight - GraphicHeight - // - // If LAYOUT_IGNORE_CURSOR is set, then the user has set fixed values for both X and Y. - // The cursor is completely ignored and the existing Bound* fields will be used without alteration. - // Use of IGNORECURSOR also means that the left, right, top and bottom margins are all ignored. Text - // will still be wrapped around the boundaries as long as LAYOUT_BACKGROUND isn't set. - - LONG extclip_left, extclip_right; - - extclip_left = 0; - extclip_right = 0; - - if (layoutflags & LAYOUT_IGNORE_CURSOR); - else { - // In cursor-relative (normal) layout mode, the graphic will be restricted by - // the margins, so we adjust cell.left and the cellwidth accordingly. - // - // The BoundWidth and BoundHeight can be expanded if the GraphicWidth/GraphicHeight exceed the bound values. - // - // Relative width/height values are allowed. - // - // A relative XOffset is allowed, this will be computed against the cellwidth. - // - // Y Coordinates are allowed, these are computed from the top of the line. - // - // Relative height and vertical offsets are allowed, these are computed from the lineheight. - // - // Vertical alignment is managed within the bounds of the object when - // it is drawn, so we do not cater for vertical alignment when positioning - // the object in this code. - - cell.Left += leftmargin; - cellwidth = cellwidth - l.right_margin - leftmargin; // Remove margins from the cellwidth because we're only interested in the space available to the object - } - - // Adjust the bounds to reflect special dimension settings. The minimum - // width and height is 1, and the bounds may not exceed the size of the - // available cell space (because a width of 110% would cause infinite recursion). - - if (layoutflags & LAYOUT_IGNORE_CURSOR) layout->BoundX = cell.Left; - else layout->BoundX = l.cursorx; - - layout->BoundWidth = 1; // Just a default in case no width in the Dimension flags is defined - - if ((align & ALIGN_HORIZONTAL) and (layout->GraphicWidth)) { - // In horizontal mode where a GraphicWidth is preset, we force the BoundX and BoundWidth to their - // exact settings and override any attempt by the user to have preset the X and Width fields. - // The object will attempt a horizontal alignment within the bounds, this will be to no effect as the - // GraphicWidth is equivalent to the BoundWidth. Text can still appear to the left and right of the object, - // if the author does not like this then the LAYOUT_LEFT and LAYOUT_RIGHT flags can be used to extend - // the clipping region. - - - LONG new_x = layout->BoundX + ((cellwidth - (layout->GraphicWidth + layout->LeftMargin + layout->RightMargin))/2); - if (new_x > layout->BoundX) layout->BoundX = new_x; - layout->BoundX += layout->LeftMargin; - layout->BoundWidth = layout->GraphicWidth; - extclip_left = layout->LeftMargin; - extclip_right = layout->RightMargin; - } - else if ((align & ALIGN_RIGHT) and (layout->GraphicWidth)) { - LONG new_x = ((AbsX + *Width) - l.right_margin) - (layout->GraphicWidth + layout->RightMargin); - if (new_x > layout->BoundX) layout->BoundX = new_x; - layout->BoundWidth = layout->GraphicWidth; - extclip_left = layout->LeftMargin; - extclip_right = layout->RightMargin; - } - else { - LONG xoffset; - - if (layout->Dimensions & DMF_FIXED_X_OFFSET) xoffset = layout->XOffset; - else if (layout->Dimensions & DMF_RELATIVE_X_OFFSET) xoffset = (DOUBLE)cellwidth * (DOUBLE)layout->XOffset * 0.01; - else xoffset = 0; - - if (layout->Dimensions & DMF_RELATIVE_X) { - LONG new_x = layout->BoundX + layout->LeftMargin + F2T(layout->X * cellwidth * 0.01); - if (new_x > layout->BoundX) layout->BoundX = new_x; - extclip_left = layout->LeftMargin; - extclip_right = layout->RightMargin; - } - else if (layout->Dimensions & DMF_FIXED_X) { - LONG new_x = layout->BoundX + layout->X + layout->LeftMargin; - if (new_x > layout->BoundX) layout->BoundX = new_x; - extclip_left = layout->LeftMargin; - extclip_right = layout->RightMargin; - } - - // WIDTH - - if (layout->Dimensions & DMF_RELATIVE_WIDTH) { - layout->BoundWidth = (DOUBLE)(cellwidth - (layout->BoundX - cell.Left)) * (DOUBLE)layout->Width * 0.01; - if (layout->BoundWidth < 1) layout->BoundWidth = 1; - else if (layout->BoundWidth > cellwidth) layout->BoundWidth = cellwidth; - } - else if (layout->Dimensions & DMF_FIXED_WIDTH) layout->BoundWidth = layout->Width; - - // GraphicWidth and GraphicHeight settings will expand the width and height - // bounds automatically unless the Width and Height fields in the Layout have been preset - // by the user. - // - // NOTE: If the object supports GraphicWidth and GraphicHeight, it must keep - // them up to date if they are based on relative values. - - if ((layout->GraphicWidth > 0) and (!(layout->Dimensions & DMF_WIDTH))) { - LAYOUT("layout_object","Setting BoundWidth from %d to preset GraphicWidth of %d", layout->BoundWidth, layout->GraphicWidth); - layout->BoundWidth = layout->GraphicWidth; - } - else if ((layout->Dimensions & DMF_X) and (layout->Dimensions & DMF_X_OFFSET)) { - if (layout->Dimensions & DMF_FIXED_X_OFFSET) layout->BoundWidth = cellwidth - xoffset - (layout->BoundX - cell.Left); - else layout->BoundWidth = cellwidth - (layout->BoundX - cell.Left) - xoffset; - - if (layout->BoundWidth < 1) layout->BoundWidth = 1; - else if (layout->BoundWidth > cellwidth) layout->BoundWidth = cellwidth; - } - else if ((layout->Dimensions & DMF_WIDTH) and - (layout->Dimensions & DMF_X_OFFSET)) { - if (layout->Dimensions & DMF_FIXED_X_OFFSET) { - LONG new_x = layout->BoundX + cellwidth - layout->BoundWidth - xoffset - layout->RightMargin; - if (new_x > layout->BoundX) layout->BoundX = new_x; - extclip_left = layout->LeftMargin; - } - else { - LONG new_x = layout->BoundX + F2T((DOUBLE)cellwidth - (DOUBLE)layout->BoundWidth - xoffset); - if (new_x > layout->BoundX) layout->BoundX = new_x; - } - } - else { - if ((align & ALIGN_HORIZONTAL) and (layout->Dimensions & DMF_WIDTH)) { - LONG new_x = layout->BoundX + ((cellwidth - (layout->BoundWidth + layout->LeftMargin + layout->RightMargin))/2); - if (new_x > layout->BoundX) layout->BoundX = new_x; - layout->BoundX += layout->LeftMargin; - extclip_left = layout->LeftMargin; - extclip_right = layout->RightMargin; - } - else if ((align & ALIGN_RIGHT) and (layout->Dimensions & DMF_WIDTH)) { - // Note that it is possible the BoundX may end up behind the cursor, or the cell's left margin. - // A check for this is made later, so don't worry about it here. - - LONG new_x = ((AbsX + *Width) - l.right_margin) - (layout->BoundWidth + layout->RightMargin); - if (new_x > layout->BoundX) layout->BoundX = new_x; - extclip_left = layout->LeftMargin; - extclip_right = layout->RightMargin; - } - } - } - - // VERTICAL SUPPORT - - LONG obj_y; - - if (layoutflags & LAYOUT_IGNORE_CURSOR) layout->BoundY = cell.Top; - else layout->BoundY = l.cursory; - - obj_y = 0; - if (layout->Dimensions & DMF_RELATIVE_Y) obj_y = F2T((DOUBLE)layout->Y * (DOUBLE)lineheight * 0.01); - else if (layout->Dimensions & DMF_FIXED_Y) obj_y = layout->Y; - obj_y += layout->TopMargin; - layout->BoundY += obj_y; - layout->BoundHeight = lineheight - obj_y; // This is merely a default - - LONG zone_height; - - if ((escpara) or (page_height < 1)) zone_height = lineheight; - else zone_height = page_height; - - // HEIGHT - - if (layout->Dimensions & DMF_RELATIVE_HEIGHT) { - // If the object is inside a paragraph

    section, the height will be calculated based - // on the current line height. Otherwise, the height is calculated based on the cell/page - // height. - - layout->BoundHeight = (DOUBLE)(zone_height - obj_y) * (DOUBLE)layout->Height * 0.01; - if (layout->BoundHeight > zone_height - obj_y) layout->BoundHeight = lineheight - obj_y; - } - else if (layout->Dimensions & DMF_FIXED_HEIGHT) { - layout->BoundHeight = layout->Height; - } - - if ((layout->GraphicHeight > layout->BoundHeight) and (!(layout->Dimensions & DMF_HEIGHT))) { - LAYOUT("layout_object","Expanding BoundHeight from %d to preset GraphicHeight of %d", layout->BoundHeight, layout->GraphicHeight); - layout->BoundHeight = layout->GraphicHeight; - } - else { - if (layout->BoundHeight < 1) layout->BoundHeight = 1; - - // This code deals with vertical offsets - - if (layout->Dimensions & DMF_Y_OFFSET) { - if (layout->Dimensions & DMF_Y) { - if (layout->Dimensions & DMF_FIXED_Y_OFFSET) layout->BoundHeight = zone_height - layout->YOffset; - else layout->BoundHeight = zone_height - F2T((DOUBLE)zone_height * (DOUBLE)layout->YOffset * 0.01); - - if (layout->BoundHeight > zone_height) layout->BoundHeight = zone_height; - } - else if (layout->Dimensions & DMF_HEIGHT) { - if (layout->Dimensions & DMF_FIXED_Y_OFFSET) layout->BoundY = cell.Top + F2T(zone_height - layout->Height - layout->YOffset); - else layout->BoundY += F2T((DOUBLE)zone_height - (DOUBLE)layout->Height - ((DOUBLE)zone_height * (DOUBLE)layout->YOffset * 0.01)); - } - } - } - - if (layoutflags & (LAYOUT_BACKGROUND|LAYOUT_TILE)) { - error = ERR_NothingDone; // No text wrapping for background and tile layouts - } - else { - // Set the clipping - - LAYOUT("layout_object","Clip region is being restricted to the bounds: %dx%d,%dx%d", layout->BoundX, layout->BoundY, layout->BoundWidth, layout->BoundHeight); - - cell.Left = layout->BoundX - extclip_left; - cell.Top = layout->BoundY - layout->TopMargin; - cell.Right = layout->BoundX + layout->BoundWidth + extclip_right; - cell.Bottom = layout->BoundY + layout->BoundHeight + layout->BottomMargin; - - // If LAYOUT_RIGHT is set, no text may be printed to the right of the object. This has no impact - // on the object's bounds. - - if (layoutflags & LAYOUT_RIGHT) { - LAYOUT("layout_object","LAYOUT_RIGHT: Expanding clip.right boundary from %d to %d.", cell.Right, AbsX + *Width - l.right_margin); - LONG new_right = (AbsX + *Width) - l.right_margin; //cellwidth; - if (new_right > cell.Right) cell.Right = new_right; - } - - // If LAYOUT_LEFT is set, no text may be printed to the left of the object (but not - // including text that has already been printed). This has no impact on the object's - // bounds. - - if (layoutflags & LAYOUT_LEFT) { - LAYOUT("layout_object","LAYOUT_LEFT: Expanding clip.left boundary from %d to %d.", cell.Left, AbsX); - - if (layoutflags & LAYOUT_IGNORE_CURSOR) cell.Left = AbsX; - else cell.Left = l.left_margin; - } - - if (layoutflags & LAYOUT_IGNORE_CURSOR) width_check = cell.Right - AbsX; - else width_check = cell.Right + l.right_margin; - - LAYOUT("layout_object","#%d, Pos: %dx%d,%dx%d, Align: $%.8x, From: %dx%d,%dx%d,%dx%d, WidthCheck: %d/%d", object->UID, layout->BoundX, layout->BoundY, layout->BoundWidth, layout->BoundHeight, align, F2T(layout->X), F2T(layout->Y), F2T(layout->Width), F2T(layout->Height), F2T(layout->XOffset), F2T(layout->YOffset), width_check, *Width); - LAYOUT("layout_object","Clip Size: %dx%d,%dx%d, LineHeight: %d, GfxSize: %dx%d, LayoutFlags: $%.8x", cell.Left, cell.Top, cellwidth, cellheight, lineheight, layout->GraphicWidth, layout->GraphicHeight, layoutflags); - - dimensions = layout->Dimensions; - error = ERR_Okay; - } - } - } - else error = ERR_NoSupport; - - ReleaseObject(object); - } - else { - if (error IS ERR_DoesNotExist) escobj->ObjectID = 0; - } - - if ((!error) and (width_check)) { - // The cursor must advance past the clipping region so that the segment positions will be - // correct when set. - - checkwrap = TRUE; - - // Check if the clipping region is invalid. Invalid clipping regions are not added to the clip - // region list (i.e. layout of document text will ignore the presence of the object). - - if ((cell.Bottom <= cell.Top) or (cell.Right <= cell.Left)) { - CSTRING name; - if ((name = object->Name)) log.warning("%s object %s returned an invalid clip region of %dx%d,%dx%d", object->Class->ClassName, name, cell.Left, cell.Top, cell.Right, cell.Bottom); - else log.warning("%s object #%d returned an invalid clip region of %dx%d,%dx%d", object->Class->ClassName, object->UID, cell.Left, cell.Top, cell.Right, cell.Bottom); - break; - } - - // If the right-side of the object extends past the page width, increase the width. - - LONG left_check; - - if (layoutflags & LAYOUT_IGNORE_CURSOR) left_check = AbsX; - else if (layoutflags & LAYOUT_LEFT) left_check = l.left_margin; - else left_check = l.left_margin; //l.cursorx; - - if (*Width >= WIDTH_LIMIT); - else if ((cell.Left < left_check) or (layoutflags & LAYOUT_IGNORE_CURSOR)) { - // The object is < left-hand side of the page/cell, this means - // that we may have to force a page/cell width increase. - // - // Note: Objects with IGNORECURSOR are always checked here, because they aren't subject - // to wrapping due to the X/Y being fixed. Such objects are limited to width increases only. - - LONG cmp_width; - - if (layoutflags & LAYOUT_IGNORE_CURSOR) cmp_width = AbsX + (cell.Right - cell.Left); - else cmp_width = l.left_margin + (cell.Right - cell.Left) + l.right_margin; - - if (*Width < cmp_width) { - LAYOUT("@layout_object:","Restarting as %s clip.left %d < %d and extends past the page width (%d > %d).", object->Class->ClassName, cell.Left, left_check, width_check, *Width); - *Width = cmp_width; - goto extend_page; - } - } - else if (width_check > *Width) { - // Perform a wrapping check if the object possibly extends past the width of the page/cell. - - LAYOUT("layout_object","Wrapping %s object #%d as it extends past the page width (%d > %d). Pos: %dx%d", object->Class->ClassName, object->UID, width_check, *Width, cell.Left, cell.Top); - - j = check_wordwrap("Object", Self, i, &l, AbsX, Width, i, &cell.Left, &cell.Top, cell.Right - cell.Left, cell.Bottom - cell.Top); - - if (j IS WRAP_EXTENDPAGE) { - LAYOUT("layout_object","Expanding page width due to object size."); - goto extend_page; - } - else if (j IS WRAP_WRAPPED) { - LAYOUT("layout_object","Object coordinates wrapped to %dx%d", cell.Left, cell.Top); - // The check_wordwrap() function will have reset l.cursorx and l.cursory, so - // on our repass, the cell.left and cell.top will reflect this new cursor position. - - goto wrap_object; - } - } - - LAYOUT("layout_object:","Adding %s clip to the list: %dx%d,%dx%d", object->Class->ClassName, cell.Left, cell.Top, cell.Right-cell.Left, cell.Bottom-cell.Top); - - if ((error = add_clip(Self, &cell, i, object->Class->ClassName, layoutflags & (LAYOUT_BACKGROUND|LAYOUT_FOREGROUND) ? TRUE : FALSE))) { - LAYOUT("layout_object:","Error adding clip area."); - Self->Error = ERR_Memory; - goto exit; - } - - if (!(layoutflags & (LAYOUT_BACKGROUND|LAYOUT_FOREGROUND))) { - if (cell.Bottom > l.cursory) { - objheight = cell.Bottom - l.cursory; - if ((l.anchor) or (escobj->Embedded)) { - // If all objects in the current section need to be anchored to the text, each - // object becomes part of the current line (e.g. treat the object as if it were - // a text character). This requires us to adjust the line height. - - if (objheight > l.line_height) { - l.line_height = objheight; - l.base_line = l.font->Ascent; - } - } - else { - // If anchoring is not set, the height of the object will still define the height - // of the line, but cannot exceed the height of the font for that line. - - if (objheight < l.font->LineSpacing) { - l.line_height = objheight; - l.base_line = objheight; - } - } - } - - //if (cell.Right > l.cursorx) l.wordwidth += cell.Right - l.cursorx; - - if (escpara) { - j = cell.Bottom - escpara->Y; - if (j > escpara->Height) escpara->Height = j; - } - } - } - else if ((error != ERR_NothingDone) and (error != ERR_NoAction)) { - LAYOUT("layout_object","Error code #%d during object layout: %s", error, GetErrorMsg(error)); - } - - l.setsegment = TRUE; - - // If the object uses a relative height or vertical offset, a repass will be required if the page height - // increases. - - if ((dimensions & (DMF_RELATIVE_HEIGHT|DMF_FIXED_Y_OFFSET|DMF_RELATIVE_Y_OFFSET)) and (layoutflags & (LAYOUT_BACKGROUND|LAYOUT_IGNORE_CURSOR))) { - LAYOUT("layout_object","Vertical repass may be required."); - object_vertical_repass = TRUE; - } -*/ - break; - } - - case ESC_TABLE_START: { - // Table layout steps are as follows: - // - // 1. Copy prefixed/default widths and heights to all cells in the table. - // 2. Calculate the size of each cell with respect to its content. This can - // be left-to-right or top-to-bottom, it makes no difference. - // 3. During the cell-layout process, keep track of the maximum width/height - // for the relevant row/column. If either increases, make a second pass - // so that relevant cells are resized correctly. - // 4. If the width of the rows is less than the requested table width (e.g. - // table width = 100%) then expand the cells to meet the requested width. - // 5. Restart the page layout using the correct width and height settings - // for the cells. - - LONG width; - - SAVE_STATE(tablestate); - - if (esctable) { - auto ptr = esctable; - esctable = escape_data(Self->Stream, i); - esctable->Stack = ptr; - } - else { - esctable = escape_data(Self->Stream, i); - esctable->Stack = NULL; - } - - esctable->ResetRowHeight = TRUE; // All rows start with a height of MinHeight up until TABLE_END in the first pass - esctable->ComputeColumns = 1; - esctable->Width = -1; - - for (j=0; j < esctable->TotalColumns; j++) esctable->Columns[j].MinWidth = 0; - -wrap_table_start: - // Calculate starting table width, ensuring that the table meets the minimum width according to the cell - // spacing and padding values. - - if (esctable->WidthPercent) { - width = ((*Width - (l.cursorx - AbsX) - l.right_margin) * esctable->MinWidth) / 100; - } - else width = esctable->MinWidth; - - if (width < 0) width = 0; - - { - LONG min = (esctable->Thickness * 2) + (esctable->CellHSpacing * (esctable->TotalColumns-1)) + (esctable->CellPadding * 2 * esctable->TotalColumns); - if (esctable->Thin) min -= esctable->CellHSpacing * 2; // Thin tables do not have spacing on the left and right borders - if (width < min) width = min; - } - - if (width > WIDTH_LIMIT - l.cursorx - l.right_margin) { - log.traceWarning("Table width in excess of allowable limits."); - width = WIDTH_LIMIT - l.cursorx - l.right_margin; - if (Self->BreakLoop > 4) Self->BreakLoop = 4; - } - - if (esctable->ComputeColumns) { - if (esctable->Width >= width) esctable->ComputeColumns = 0; - } - - esctable->Width = width; - -wrap_table_end: -wrap_table_cell: - esctable->CursorX = l.cursorx; - esctable->CursorY = l.cursory; - esctable->X = l.cursorx; - esctable->Y = l.cursory; - esctable->RowIndex = 0; - esctable->TotalClips = Self->TotalClips; - esctable->Height = esctable->Thickness; - - LAYOUT("~layout_table:","(i%d) Laying out table of %dx%d, coords %dx%d,%dx%d%s, page width %d.", i, esctable->TotalColumns, esctable->Rows, esctable->X, esctable->Y, esctable->Width, esctable->MinHeight, esctable->HeightPercent ? "%" : "", *Width); - // NB: LOGRETURN() is matched in ESC_TABLE_END - - if (esctable->ComputeColumns) { - // Compute the default column widths - - esctable->ComputeColumns = 0; - esctable->CellsExpanded = FALSE; - - if (esctable->Columns) { - for (j=0; j < esctable->TotalColumns; j++) { - //if (esctable->ComputeColumns IS 1) { - // esctable->Columns[j].Width = 0; - // esctable->Columns[j].MinWidth = 0; - //} - - if (esctable->Columns[j].PresetWidth & 0x8000) { - // Percentage width value - esctable->Columns[j].Width = (DOUBLE)((esctable->Columns[j].PresetWidth & 0x7fff) * esctable->Width) * 0.01; - } - else if (esctable->Columns[j].PresetWidth) { - // Fixed width value - esctable->Columns[j].Width = esctable->Columns[j].PresetWidth; - } - else { - esctable->Columns[j].Width = 0; - } - - if (esctable->Columns[j].MinWidth > esctable->Columns[j].Width) esctable->Columns[j].Width = esctable->Columns[j].MinWidth; - } - } - else { - log.warning("No columns array defined for table."); - esctable->TotalColumns = 0; - } - } - - LAYOUT("layout_table:","Checking for table collisions before layout (%dx%d). ResetRowHeight: %d", esctable->X, esctable->Y, esctable->ResetRowHeight); - - j = check_wordwrap("Table", Self, i, &l, AbsX, Width, i, &esctable->X, &esctable->Y, (esctable->Width < 1) ? 1 : esctable->Width, esctable->Height); - if (j IS WRAP_EXTENDPAGE) { - LAYOUT("layout_table:","Expanding page width due to table size."); - LAYOUT_LOGRETURN(); - goto extend_page; - } - else if (j IS WRAP_WRAPPED) { - // The width of the table and positioning information needs - // to be recalculated in the event of a table wrap. - - LAYOUT("layout_table:","Restarting table calculation due to page wrap to position %dx%d.", l.cursorx, l.cursory); - esctable->ComputeColumns = 1; - LAYOUT_LOGRETURN(); - goto wrap_table_start; - } - l.cursorx = esctable->X; - l.cursory = esctable->Y; - - l.setsegment = TRUE; - - l.cursory += esctable->Thickness + esctable->CellVSpacing; - lastrow = NULL; - - break; - } - - case ESC_TABLE_END: { - SurfaceClip clip; - LONG minheight, totalclips; - - if (esctable->CellsExpanded IS FALSE) { - DOUBLE cellwidth; - LONG unfixed, colwidth; - - // Table cells need to match the available width inside the table. - // This routine checks for that - if the cells are short then the - // table processing is restarted. - - LAYOUT("layout_table_end:","Checking table @ index %d for cell/table widening. Table width: %d", i, esctable->Width); - - esctable->CellsExpanded = TRUE; - - if (esctable->Columns) { - colwidth = (esctable->Thickness * 2) + esctable->CellHSpacing; - for (j=0; j < esctable->TotalColumns; j++) { - colwidth += esctable->Columns[j].Width + esctable->CellHSpacing; - } - if (esctable->Thin) colwidth -= esctable->CellHSpacing * 2; // Thin tables have no spacing allocated on the sides - - if (colwidth < esctable->Width) { // Cell layout is less than the pre-determined table width - LONG avail_width; - - // Calculate the amount of additional space that is available for cells to expand into - - avail_width = esctable->Width - (esctable->Thickness * 2) - - (esctable->CellHSpacing * (esctable->TotalColumns - 1)); - - if (!esctable->Thin) avail_width -= (esctable->CellHSpacing * 2); - - // Count the number of columns that do not have a fixed size - - unfixed = 0; - for (j=0; j < esctable->TotalColumns; j++) { - if (esctable->Columns[j].PresetWidth) avail_width -= esctable->Columns[j].Width; - else unfixed++; - } - - // Adjust for expandable columns that we know have exceeded the pre-calculated cell width - // on previous passes (we want to treat them the same as the PresetWidth columns) Such cells - // will often exist that contain large graphics for example. - - if (unfixed > 0) { - cellwidth = avail_width / unfixed; - for (LONG j=0; j < esctable->TotalColumns; j++) { - if ((esctable->Columns[j].MinWidth) and (esctable->Columns[j].MinWidth > cellwidth)) { - avail_width -= esctable->Columns[j].MinWidth; - unfixed--; - } - } - - if (unfixed > 0) { - cellwidth = avail_width / unfixed; - bool expanded = FALSE; - - //total = 0; - for (LONG j=0; j < esctable->TotalColumns; j++) { - if (esctable->Columns[j].PresetWidth) continue; // Columns with preset-widths are never auto-expanded - if (esctable->Columns[j].MinWidth > cellwidth) continue; - - if (esctable->Columns[j].Width < cellwidth) { - LAYOUT("layout_table_end","Expanding column %d from width %d to %.2f", j, esctable->Columns[j].Width, cellwidth); - esctable->Columns[j].Width = cellwidth; - //if (total - (DOUBLE)F2I(total) >= 0.5) esctable->Columns[j].Width++; // Fractional correction - - expanded = TRUE; - } - //total += cellwidth; - } - - if (expanded) { - LAYOUT("layout_table:","At least one cell was widened - will repass table layout."); - RESTORE_STATE(&tablestate); - LAYOUT_LOGRETURN(); - goto wrap_table_end; - } - } - } - } - } - else LAYOUT("layout_table_end:","Table is missing its columns array."); - } - else LAYOUT("layout_table_end:","Cells already widened - keeping table width of %d.", esctable->Width); - - // Cater for the minimum height requested - - if (esctable->HeightPercent) { - // If the table height is expressed as a percentage, it is calculated with - // respect to the height of the display port. - - if (!Offset) { - minheight = ((Self->AreaHeight - BottomMargin - esctable->Y) * esctable->MinHeight) / 100; - } - else minheight = ((*Height - BottomMargin - TopMargin) * esctable->MinHeight) / 100; - - if (minheight < 0) minheight = 0; - } - else minheight = esctable->MinHeight; - - if (minheight > esctable->Height + esctable->CellVSpacing + esctable->Thickness) { - // The last row in the table needs its height increased - if (lastrow) { - j = minheight - (esctable->Height + esctable->CellVSpacing + esctable->Thickness); - LAYOUT("layout_table:","Extending table height to %d (row %d+%d) due to a minimum height of %d at coord %d", minheight, lastrow->RowHeight, j, esctable->MinHeight, esctable->Y); - lastrow->RowHeight += j; - RESTORE_STATE(&rowstate); - LAYOUT_LOGRETURN(); - escrow = lastrow; - goto repass_row_height_ext; - } - else log.warning("No last row defined for table height extension."); - } - - // Adjust for cellspacing at the bottom - - esctable->Height += esctable->CellVSpacing + esctable->Thickness; - - // Restart if the width of the table will force an extension of the page. - - j = esctable->X + esctable->Width - AbsX + l.right_margin; - if ((j > *Width) and (*Width < WIDTH_LIMIT)) { - LAYOUT("layout_table:","Table width (%d+%d) increases page width to %d, layout restart forced.", esctable->X, esctable->Width, j); - *Width = j; - LAYOUT_LOGRETURN(); - goto extend_page; - } - - // Extend the height of the current line to the height of the table if the table is to be anchored (a - // technique typically applied to objects). We also extend the line height if the table covers the - // entire width of the page (this is a valuable optimisation for the layout routine). - - if ((l.anchor) or ((esctable->X <= l.left_margin) and (esctable->X + esctable->Width >= l.wrapedge))) { - if (esctable->Height > l.line_height) { - l.line_height = esctable->Height; - l.base_line = l.font->Ascent; - } - } - - if (escpara) { - j = (esctable->Y + esctable->Height) - escpara->Y; - if (j > escpara->Height) escpara->Height = j; - } - - // Check if the table collides with clipping boundaries and - // adjust its position accordingly. Such a check is performed in - // ESC_TABLE_START - this second check is required only if the width - // of the table has been extended. - // - // Note that the total number of clips is adjusted so that only - // clips up to the TABLE_START are considered (otherwise, clips - // inside the table cells will cause collisions against the parent - // table). - - - LAYOUT("layout_table:","Checking table collisions (%dx%d).", esctable->X, esctable->Y); - - totalclips = Self->TotalClips; - Self->TotalClips = esctable->TotalClips; - j = check_wordwrap("Table", Self, i, &l, AbsX, Width, i, &esctable->X, &esctable->Y, esctable->Width, esctable->Height); - Self->TotalClips = totalclips; - - if (j IS WRAP_EXTENDPAGE) { - LAYOUT("layout_table:","Table wrapped - expanding page width due to table size/position."); - LAYOUT_LOGRETURN(); - goto extend_page; - } - else if (j IS WRAP_WRAPPED) { - // A repass is necessary as everything in the table will need to be rearranged - LAYOUT("layout_table:","Table wrapped - rearrangement necessary."); - - RESTORE_STATE(&tablestate); - LAYOUT_LOGRETURN(); - goto wrap_table_end; - } - - //LAYOUT("layout_table:","new table pos: %dx%d", esctable->X, esctable->Y); - - // The table sets a clipping region in order to state its placement (the surrounds of a table are - // effectively treated as a graphical object, since it's not text). - - clip.Left = esctable->X; - clip.Top = esctable->Y; - clip.Right = clip.Left + esctable->Width; - clip.Bottom = clip.Top + esctable->Height; - - //if (clip.Left IS l.left_margin) clip.Left = 0; // Extending the clipping to the left doesn't hurt - - add_clip(Self, &clip, i, "Table", FALSE); - - l.cursorx = esctable->X + esctable->Width; - l.cursory = esctable->Y; - - LAYOUT("layout_table:","Final Table Size: %dx%d,%dx%d", esctable->X, esctable->Y, esctable->Width, esctable->Height); - - esctable = esctable->Stack; - - l.setsegment = TRUE; - - LAYOUT_LOGRETURN(); - break; - } - - case ESC_ROW: - if (escrow) { - auto ptr = escrow; - escrow = escape_data(Self->Stream, i); - escrow->Stack = ptr; - } - else { - escrow = escape_data(Self->Stream, i); - escrow->Stack = NULL; - } - - SAVE_STATE(rowstate); - - if (esctable->ResetRowHeight) escrow->RowHeight = escrow->MinHeight; - -repass_row_height_ext: - escrow->VerticalRepass = FALSE; - escrow->Y = l.cursory; - esctable->RowWidth = (esctable->Thickness<<1) + esctable->CellHSpacing; - - l.setsegment = TRUE; - break; - - case ESC_ROW_END: - esctable->RowIndex++; - - // Increase the table height if the row extends beyond it - - j = escrow->Y + escrow->RowHeight + esctable->CellVSpacing; - if (j > esctable->Y + esctable->Height) { - esctable->Height = j - esctable->Y; - } - - // Advance the cursor by the height of this row - - l.cursory += escrow->RowHeight + esctable->CellVSpacing; - l.cursorx = esctable->X; - LAYOUT("layout_row:","Row ends, advancing down by %d+%d, new height: %d, y-cursor: %d", - escrow->RowHeight, esctable->CellVSpacing, esctable->Height, l.cursory); - - if (esctable->RowWidth > esctable->Width) esctable->Width = esctable->RowWidth; - - lastrow = escrow; - escrow = escrow->Stack; - l.setsegment = TRUE; - break; - - case ESC_CELL: { - // In the first pass, the size of each cell is calculated with - // respect to its content. When ESC_TABLE_END is reached, the - // max height and width for each row/column will be calculated - // and a subsequent pass will be made to fill out the cells. - // - // If the width of a cell increases, there is a chance that the height of all - // cells in that column will decrease, subsequently lowering the row height - // of all rows in the table, not just the current row. Therefore on the second - // pass the row heights need to be recalculated from scratch. - - - BYTE savechar, vertical_repass; - - esccell = escape_data(Self->Stream, i); - - if (!esctable) { - log.warning("escTable variable not defined for cell @ index %d - document byte code is corrupt.", i); - goto exit; - } - - if (esccell->Column >= esctable->TotalColumns) { - LAYOUT("@layout_cell:","Cell %d exceeds total table column limit of %d.", esccell->Column, esctable->TotalColumns); - break; - } - - // Setting the line is the only way to ensure that the table graphics will be accounted for when drawing. - - add_drawsegment(Self, i, i+l.len, &l, l.cursory, 0, 0, "Esc:Cell"); - - // Set the AbsX location of the cell. AbsX determines the true location of the cell for layout_section() - - esccell->AbsX = l.cursorx; - esccell->AbsY = l.cursory; - - if (esctable->Thin) { - //if (esccell->Column IS 0); - //else esccell->AbsX += esctable->CellHSpacing; - } - else { - esccell->AbsX += esctable->CellHSpacing; - } - - if (esccell->Column IS 0) esccell->AbsX += esctable->Thickness; - - esccell->Width = esctable->Columns[esccell->Column].Width; // Minimum width for the cell's column - esccell->Height = escrow->RowHeight; - //LAYOUT("Min:","%d / %d", escrow->MinHeight, escrow->RowHeight); - - LAYOUT("~layout_cell:","Index %d, Processing cell at %dx %dy, size %dx%d, column %d", i, l.cursorx, l.cursory, esccell->Width, esccell->Height, esccell->Column); - - // Find the matching CELL_END - - LONG cell_end = i; - while (Self->Stream[cell_end]) { - if (Self->Stream[cell_end] IS CTRL_CODE) { - if (ESCAPE_CODE(Self->Stream, cell_end) IS ESC_CELL_END) { - escCellEnd *end = escape_data(Self->Stream, cell_end); - if (end->CellID IS esccell->CellID) break; - } - } - - NEXT_CHAR(Self->Stream, cell_end); - } - - if (Self->Stream[cell_end] IS 0) { - log.warning("Failed to find matching cell-end. Document stream is corrupt."); - goto exit; - } - - i += l.len; // Go to start of cell content - l.len = 0; - - if (i < cell_end) { - LONG segcount = Self->SegCount; - savechar = Self->Stream[cell_end]; - Self->Stream[cell_end] = 0; - - if (esccell->EditHash) Self->EditMode = TRUE; - else Self->EditMode = FALSE; - - i = layout_section(Self, i, &l.font, - esccell->AbsX, esccell->AbsY, - &esccell->Width, &esccell->Height, - esctable->CellPadding, esctable->CellPadding, esctable->CellPadding, esctable->CellPadding, &vertical_repass); - - if (esccell->EditHash) Self->EditMode = FALSE; - - Self->Stream[cell_end] = savechar; - - if (esccell->EditHash) { - // Edit cells have a minimum width/height so that the user can still interact with them when empty. - - if (Self->SegCount IS segcount) { - // No content segments were created, which means that there's nothing for the cursor to attach - // itself too. - - //do we really want to do something here? - //I'd suggest that we instead break up the segments a bit more??? ANother possibility - create an ESC_NULL - //type that gets placed at the start of the edit cell. If there's no genuine content, then we at least have the ESC_NULL - //type for the cursor to be attached to? ESC_NULL does absolutely nothing except act as faux content. - - -// TODO Work on this next - - - - - } - - if (esccell->Width < 16) esccell->Width = 16; - if (esccell->Height < l.font->LineSpacing) { - esccell->Height = l.font->LineSpacing; - } - } - } - - LAYOUT_LOGRETURN(); - - if (!i) goto exit; - - LAYOUT("layout_cell","Cell (%d:%d) is size %dx%d (min width %d)", esctable->RowIndex, esccell->Column, esccell->Width, esccell->Height, esctable->Columns[esccell->Column].Width); - - // Increase the overall width for the entire column if this cell has increased the column width. - // This will affect the entire table, so a restart from TABLE_START is required. - - if (esctable->Columns[esccell->Column].Width < esccell->Width) { - LAYOUT("layout_cell","Increasing column width of cell (%d:%d) from %d to %d (table_start repass required).", esctable->RowIndex, esccell->Column, esctable->Columns[esccell->Column].Width, esccell->Width); - esctable->Columns[esccell->Column].Width = esccell->Width; // This has the effect of increasing the minimum column width for all cells in the column - - // Percentage based and zero columns need to be recalculated. The easiest thing to do - // would be for a complete recompute (ComputeColumns = TRUE) with the new minwidth. The - // problem with ComputeColumns is that it does it all from scratch - we need to adjust it - // so that it can operate in a second style of mode where it recognises temporary width values. - - esctable->Columns[esccell->Column].MinWidth = esccell->Width; // Column must be at least this size - esctable->ComputeColumns = 2; - - esctable->ResetRowHeight = TRUE; // Row heights need to be reset due to the width increase - RESTORE_STATE(&tablestate); - LAYOUT_LOGRETURN(); // WHAT DOES THIS MATCH TO? - goto wrap_table_cell; - } - - // Advance the width of the entire row and adjust the row height - - esctable->RowWidth += esctable->Columns[esccell->Column].Width; - - if (!esctable->Thin) esctable->RowWidth += esctable->CellHSpacing; - else if ((esccell->Column + esccell->ColSpan) < esctable->TotalColumns-1) esctable->RowWidth += esctable->CellHSpacing; - - if ((esccell->Height > escrow->RowHeight) or (escrow->VerticalRepass)) { - // A repass will be required if the row height has increased - // and objects or tables have been used in earlier cells, because - // objects need to know the final dimensions of their table cell. - - if (esccell->Column IS esctable->TotalColumns-1) { - LAYOUT("layout_cell","Extending row height from %d to %d (row repass required)", escrow->RowHeight, esccell->Height); - } - - escrow->RowHeight = esccell->Height; - if ((esccell->Column + esccell->ColSpan) >= esctable->TotalColumns) { - RESTORE_STATE(&rowstate); - goto repass_row_height_ext; - } - else escrow->VerticalRepass = TRUE; // Make a note to do a vertical repass once all columns on this row have been processed - } - - l.cursorx += esctable->Columns[esccell->Column].Width; - - if (!esctable->Thin) l.cursorx += esctable->CellHSpacing; - else if ((esccell->Column + esccell->ColSpan) < esctable->TotalColumns) l.cursorx += esctable->CellHSpacing; - - if (esccell->Column IS 0) { - l.cursorx += esctable->Thickness; - } - - break; - } - - case ESC_CELL_END: { - // CELL_END helps draw_document(), so set the segment to ensure that it is - // included in the draw stream. Please refer to ESC_CELL to see how content is - // processed and how the cell dimensions are formed. - - l.setsegment = TRUE; - - if ((esccell) and (esccell->OnClick)) { - add_link(Self, ESC_CELL, esccell, esccell->AbsX, esccell->AbsY, esccell->Width, esccell->Height, "esc_cell_end"); - } - - if ((esccell) and (esccell->EditHash)) { - // The area of each edit cell is logged in an array, which is used for assisting interaction between - // the mouse pointer and the edit cells. - - if (Self->ECIndex >= Self->ECMax) { - EditCell *cells; - if (!AllocMemory(sizeof(Self->EditCells[0]) * (Self->ECMax + 10), MEM::NO_CLEAR, &cells)) { - if (Self->EditCells) { - CopyMemory(Self->EditCells, cells, sizeof(Self->EditCells[0]) * Self->ECMax); - FreeResource(Self->EditCells); - } - Self->ECMax += 10; - Self->EditCells = cells; - } - else { - Self->Error = ERR_AllocMemory; - break; - } - } - Self->EditCells[Self->ECIndex].CellID = esccell->CellID; - Self->EditCells[Self->ECIndex].X = esccell->AbsX; - Self->EditCells[Self->ECIndex].Y = esccell->AbsY; - Self->EditCells[Self->ECIndex].Width = esccell->Width; - Self->EditCells[Self->ECIndex].Height = esccell->Height; - Self->ECIndex++; - } - - break; - } - - case ESC_PARAGRAPH_START: { - escParagraph *parent; - - if ((parent = escpara)) { - DOUBLE ratio; - - // If a paragraph is embedded within a paragraph, insert a newline before the new paragraph starts. - - l.left_margin = parent->X; // Reset the margin so that the next line will be flush with the parent - - if (l.paragraph_y > 0) { - if (escpara->LeadingRatio > escpara->VSpacing) ratio = escpara->LeadingRatio; - else ratio = escpara->VSpacing; - } - else ratio = escpara->VSpacing; - - end_line(Self, &l, NL_PARAGRAPH, i, ratio, i, "Esc:PStart"); - - auto ptr = escpara; - escpara = escape_data(Self->Stream, i); - escpara->Stack = ptr; - } - else { - escpara = escape_data(Self->Stream, i); - escpara->Stack = NULL; - - // Leading ratio is only used if the paragraph is preceeded by content. - // This check ensures that the first paragraph is always flush against - // the top of the page. - - if ((escpara->LeadingRatio > 0) and (l.paragraph_y > 0)) { - end_line(Self, &l, NL_PARAGRAPH, i, escpara->LeadingRatio, i, "Esc:PStart"); - } - } - - // Indentation support - - if (esclist) { - // For list items, indentation is managed by the list that this paragraph is contained within. - - if (escpara->ListItem) { - if (parent) escpara->Indent = esclist->BlockIndent; - escpara->ItemIndent = esclist->ItemIndent; - escpara->Relative = FALSE; - - if (escpara->CustomString) { - LONG strwidth; - strwidth = fntStringWidth(l.font, (STRING)(escpara + 1), -1) + 10; - if (strwidth > esclist->ItemIndent) { - esclist->ItemIndent = strwidth; - escpara->ItemIndent = strwidth; - esclist->Repass = TRUE; - } - } - } - else escpara->Indent = esclist->ItemIndent; - } - - if (escpara->Indent) { - if (escpara->Relative) escpara->BlockIndent = escpara->Indent * 100 / *Width; - else escpara->BlockIndent = escpara->Indent; - } - - escpara->X = l.left_margin + escpara->BlockIndent; - - l.left_margin += escpara->BlockIndent + escpara->ItemIndent; - l.cursorx += escpara->BlockIndent + escpara->ItemIndent; - l.line_x += escpara->BlockIndent + escpara->ItemIndent; - - // Paragraph management variables - - if (esclist) { - escpara->VSpacing = esclist->VSpacing; - } - - escpara->Y = l.cursory; - escpara->Height = 0; - break; - } - - case ESC_PARAGRAPH_END: { - if (escpara) { - // The paragraph height reflects the true size of the paragraph after we take into account - // any objects and tables within the paragraph. - - l.paragraph_end = escpara->Y + escpara->Height; - - end_line(Self, &l, NL_PARAGRAPH, i, escpara->VSpacing, i + l.len, "Esc:PEnd"); - - l.left_margin = escpara->X - escpara->BlockIndent; - l.cursorx = escpara->X - escpara->BlockIndent; - l.line_x = escpara->X - escpara->BlockIndent; - - escpara = escpara->Stack; - } - else end_line(Self, &l, NL_PARAGRAPH, i, escpara->VSpacing, i + l.len, "Esc:PEnd-NP"); - - break; - } - } - - if (l.setsegment) { - // Notice that this version of our call to add_drawsegment() does not define content position information (i.e. X/Y coordinates) - // because we only expect to add an escape code to the drawing sequence, with the intention that the escape code carries - // information relevant to the drawing process. It is vital therefore that all content has been set with an earlier call - // to add_drawsegment() before processing of the escape code. See earlier in this routine. - - add_drawsegment(Self, i, i+l.len, &l, l.cursory, 0, 0, strCodes[(UBYTE)ESCAPE_CODE(Self->Stream, i)]); //"Esc:SetSegment"); - RESET_SEGMENT_WORD(i+l.len, l.cursorx, &l); - } - - i += l.len; - } - else { - // If the font character is larger or equal to the current line height, extend - // the height for the current line. Note that we go for >= because we want to - // correct the base line in case there is an object already set on the line that - // matches the font's line spacing. - - if (l.font->LineSpacing >= l.line_height) { - l.line_height = l.font->LineSpacing; - l.base_line = l.font->Ascent; - } - - if (Self->Stream[i] IS '\n') { -#if 0 - // This link code is likely going to be needed for a case such as : - // blah blah
    blah
    - // But we haven't tested it in a rpl document yet. - - if ((l.link) and (l.link_open IS FALSE)) { - // A link is due to be closed - add_link(Self, ESC_LINK, l.link, l.link_x, l.cursory, l.cursorx + l.wordwidth - l.link_x, l.line_height, "
    "); - l.link = NULL; - } -#endif - end_line(Self, &l, NL_PARAGRAPH, i+1 /* index */, 0 /* spacing */, i+1 /* restart-index */, "CarriageReturn"); - i++; - } - else if (Self->Stream[i] <= 0x20) { - if (Self->Stream[i] IS '\t') { - LONG tabwidth = (l.spacewidth + l.font->GlyphSpacing) * l.font->TabSize; - if (tabwidth) l.cursorx += pf::roundup(l.cursorx, tabwidth); - i++; - } - else { - l.cursorx += l.wordwidth + l.spacewidth; - i++; - } - - l.kernchar = 0; - l.wordwidth = 0; - l.textcontent = TRUE; - } - else { - LONG kerning; - - if (!l.wordwidth) l.wordindex = i; // Record the index of the new word (if this is one) - - i += getutf8((CSTRING)Self->Stream+i, &unicode); - l.wordwidth += fntCharWidth(l.font, unicode, l.kernchar, &kerning); - l.wordwidth += kerning; - l.kernchar = unicode; - l.textcontent = TRUE; - } - } - } // while(1) - - // Check if the cursor + any remaining text requires closure - - if ((l.cursorx + l.wordwidth > l.left_margin) or (l.wordindex != -1)) { - end_line(Self, &l, NL_NONE, i, 0, i, "SectionEnd"); - } - -exit: - - page_height = calc_page_height(Self, l.start_clips, AbsY, BottomMargin); - - // Force a second pass if the page height has increased and there are objects - // on the page (the objects may need to know the page height - e.g. if there - // is a gradient filling the background). - // - // This feature is also handled in ESC_CELL, so we only perform it here - // if processing is occurring within the root page area (Offset of 0). - - if ((!Offset) and (object_vertical_repass) and (lastheight < page_height)) { - LAYOUT("layout_section:","============================================================"); - LAYOUT("layout_section:","SECOND PASS [%d]: Root page height increased from %d to %d", Offset, lastheight, page_height); - goto extend_page; - } - - *Font = l.font; - if (page_height > *Height) *Height = page_height; - - *VerticalRepass = object_vertical_repass; - - Self->Depth--; - LAYOUT_LOGRETURN(); - return i; -} - -//******************************************************************************************************************** -// Calculate the page height, which is either going to be the coordinate of -// the bottom-most line, or one of the clipping regions if one of them -// extends further than the bottom-most line. - -static LONG calc_page_height(extDocument *Self, LONG FirstClip, LONG Y, LONG BottomMargin) -{ - // Find the last segment that had text and use that to determine the bottom of the page - - LONG height = 0; - LONG y = 0; - LONG last = Self->SegCount-1; - while ((last > 0) and (!height) and (!y)) { - if (Self->Segments[last].TextContent) { - height = Self->Segments[last].Height; - y = Self->Segments[last].Y; - break; - } - last--; - } - - LONG page_height = (y + height); - - // Check clipping regions to see if they extend past the last line of text - if so, we extend the height. - - for (LONG j=FirstClip; j < Self->TotalClips; j++) { - if (Self->Clips[j].Transparent) continue; - if (Self->Clips[j].Clip.Bottom > page_height) page_height = Self->Clips[j].Clip.Bottom; - } - - // Add the bottom margin and subtract the Y offset so that we have the true height of the page/cell. - - page_height = page_height + BottomMargin - Y; - -/* - log.trace("Page Height: %d + %d -> %d, Bottom: %d, Y: %d", - Self->Segments[last].Y, Self->Segments[last].Height, page_height, BottomMargin, Y); -*/ - return page_height; -} - -//******************************************************************************************************************** -// Terminates all links and frees the memory. Another method to clear the links -// is to set the TotalLinks to zero, which retains the link cache allocation. - -static void free_links(extDocument *Self) -{ - if (!Self->Links) return; - - FreeResource(Self->Links); - Self->Links = NULL; - - Self->MaxLinks = 0; - Self->TotalLinks = 0; -} - -//******************************************************************************************************************** -// Record a clickable link, cell, or other form of clickable area. - -static void add_link(extDocument *Self, UBYTE EscapeCode, APTR Escape, LONG X, LONG Y, LONG Width, LONG Height, CSTRING Caller) -{ - pf::Log log(__FUNCTION__); - - if ((!Self) or (!Escape)) return; - - if ((Width < 1) or (Height < 1)) { - log.traceWarning("Illegal width/height for link @ %dx%d, W/H %dx%d [%s]", X, Y, Width, Height, Caller); - return; - } - - if (!Self->Links) { - Self->TotalLinks = 0; - Self->MaxLinks = 20; - if (!AllocMemory(sizeof(DocLink) * Self->MaxLinks, MEM::DATA|MEM::NO_CLEAR, &Self->Links)) { - - } - else return; - } - else if (Self->TotalLinks+1 >= Self->MaxLinks) { - #define LINK_INC 40 - if (!ReallocMemory(Self->Links, sizeof(DocLink) * (Self->MaxLinks + LINK_INC), &Self->Links, NULL)) { - Self->MaxLinks += LINK_INC; - } - else return; - } - - LAYOUT("add_link()","%dx%d,%dx%d, %s", X, Y, Width, Height, Caller); - - LONG index = Self->TotalLinks; - Self->Links[index].EscapeCode = EscapeCode; - Self->Links[index].Escape = Escape; - Self->Links[index].X = X; - Self->Links[index].Y = Y; - Self->Links[index].Width = Width; - Self->Links[index].Height = Height; - Self->Links[index].Segment = Self->SegCount; - Self->TotalLinks++; -} - -//******************************************************************************************************************** - -static void draw_background(extDocument *Self, objSurface *Surface, objBitmap *Bitmap) -{ - gfxDrawRectangle(Bitmap, 0, 0, Surface->Width, Surface->Height, Bitmap->packPixel(Self->Background), BAF::FILL); -} - -//******************************************************************************************************************** -// Note that this function also controls the drawing of objects that have loaded into the document (see the -// subscription hook in the layout process). - -static void draw_document(extDocument *Self, objSurface *Surface, objBitmap *Bitmap) -{ - pf::Log log(__FUNCTION__); - escList *esclist; - escLink *esclink; - escParagraph *escpara; - escTable *esctable; - escCell *esccell; - escRow *escrow; - escObject *escobject; - DocSegment *segment; - RGB8 link_save_rgb; - UBYTE tabfocus, oob, cursor_drawn; - LONG fx, si, i; - - if (Self->UpdateLayout) { - // Drawing is disabled if the layout needs to be updated (this likely indicates that the document stream has been - // modified and has yet to be recalculated - drawing while in this state is liable to lead to a crash) - - return; - } - - auto font = lookup_font(0, "draw_document"); - if (!font) { - log.traceWarning("No default font defined."); - return; - } - - #ifdef _DEBUG - if ((!Self->Stream[0]) or (!Self->SegCount)) { - //log.traceWarning("No content in stream or no segments."); - return; - } - #endif - - Self->CurrentCell = NULL; - font->Bitmap = Bitmap; - esclist = NULL; - escpara = NULL; - esctable = NULL; - escrow = NULL; - esccell = NULL; - tabfocus = FALSE; - cursor_drawn = FALSE; - - #ifdef GUIDELINES - - // Page boundary is marked in blue - gfxDrawRectangle(Bitmap, Self->LeftMargin-1, Self->TopMargin-1, - Self->CalcWidth - Self->RightMargin - Self->LeftMargin + 2, Self->PageHeight - Self->TopMargin - Self->BottomMargin + 2, - Bitmap->packPixel(0, 0, 255), 0); - - // Special clip regions are marked in grey - for (i=0; i < Self->TotalClips; i++) { - gfxDrawRectangle(Bitmap, Self->Clips[i].Clip.Left, Self->Clips[i].Clip.Top, - Self->Clips[i].Clip.Right - Self->Clips[i].Clip.Left, Self->Clips[i].Clip.Bottom - Self->Clips[i].Clip.Top, - Bitmap->packPixel(255, 200, 200), 0); - } - #endif - - LONG select_start = -1; - LONG select_end = -1; - LONG select_startx = 0; - LONG select_endx = 0; - - if ((Self->ActiveEditDef) and (Self->SelectIndex IS -1)) { - select_start = Self->CursorIndex; - select_end = Self->CursorIndex; - select_startx = Self->CursorCharX; - select_endx = Self->CursorCharX; - } - else if ((Self->CursorIndex != -1) and (Self->SelectIndex != -1)) { - if (Self->SelectIndex < Self->CursorIndex) { - select_start = Self->SelectIndex; - select_end = Self->CursorIndex; - select_startx = Self->SelectCharX; - select_endx = Self->CursorCharX; - } - else { - select_start = Self->CursorIndex; - select_end = Self->SelectIndex; - select_startx = Self->CursorCharX; - select_endx = Self->SelectCharX; - } - } - - UBYTE alpha = Bitmap->Opacity; - for (LONG seg=0; seg < Self->SegCount; seg++) { - segment = Self->Segments + seg; - - // Don't process segments that are out of bounds. This can't be applied to objects, as they can draw anywhere. - - oob = FALSE; - if (!segment->ObjectContent) { - if (segment->Y >= Bitmap->Clip.Bottom) oob = TRUE; - if (segment->Y + segment->Height < Bitmap->Clip.Top) oob = TRUE; - if (segment->X + segment->Width < Bitmap->Clip.Left) oob = TRUE; - if (segment->X >= Bitmap->Clip.Right) oob = TRUE; - } - - // Highlighting of selected text - - if ((select_start <= segment->Stop) and (select_end > segment->Index)) { - if (select_start != select_end) { - Bitmap->Opacity = 80; - if ((select_start > segment->Index) and (select_start < segment->Stop)) { - if (select_end < segment->Stop) { - gfxDrawRectangle(Bitmap, segment->X + select_startx, segment->Y, - select_endx - select_startx, segment->Height, Bitmap->packPixel(0, 128, 0), BAF::FILL); - } - else { - gfxDrawRectangle(Bitmap, segment->X + select_startx, segment->Y, - segment->Width - select_startx, segment->Height, Bitmap->packPixel(0, 128, 0), BAF::FILL); - } - } - else if (select_end < segment->Stop) { - gfxDrawRectangle(Bitmap, segment->X, segment->Y, select_endx, segment->Height, - Bitmap->packPixel(0, 128, 0), BAF::FILL); - } - else { - gfxDrawRectangle(Bitmap, segment->X, segment->Y, segment->Width, segment->Height, - Bitmap->packPixel(0, 128, 0), BAF::FILL); - } - Bitmap->Opacity = 255; - } - } - - if ((Self->ActiveEditDef) and (Self->CursorState) and (!cursor_drawn)) { - if ((Self->CursorIndex >= segment->Index) and (Self->CursorIndex <= segment->Stop)) { - if ((Self->CursorIndex IS segment->Stop) and (Self->Stream[Self->CursorIndex-1] IS '\n')); // The -1 looks naughty, but it works as CTRL_CODE != \n, so use of PREV_CHAR() is unnecessary - else { - if (gfxGetUserFocus() IS Self->PageID) { // Standard text cursor - gfxDrawRectangle(Bitmap, segment->X + Self->CursorCharX, segment->Y, 2, segment->BaseLine, - Bitmap->packPixel(255, 0, 0), BAF::FILL); - cursor_drawn = TRUE; - } - } - } - } - - #ifdef GUIDELINES_CONTENT - if (segment->TextContent) { - gfxDrawRectangle(Bitmap, - segment->X, segment->Y, - (segment->Width > 0) ? segment->Width : 5, segment->Height, - Bitmap->packPixel(0, 255, 0), 0); - } - #endif - - char strbuffer[segment->Stop - segment->Index + 1]; - - fx = segment->X; - i = segment->Index; - si = 0; - - while (i < segment->TrimStop) { - if (Self->Stream[i] IS CTRL_CODE) { - switch (ESCAPE_CODE(Self->Stream, i)) { - case ESC_OBJECT: { - OBJECTPTR object; - - escobject = escape_data(Self->Stream, i); - - if ((escobject->Graphical) and (!escobject->Owned)) { - if (escobject->ObjectID < 0) { - object = NULL; - AccessObject(escobject->ObjectID, 3000, &object); - } - else object = GetObjectPtr(escobject->ObjectID); -/* - if (object) { - objLayout *layout; - - if ((FindField(object, FID_Layout, NULL)) and (!object->getPtr(FID_Layout, &layout))) { - if (layout->DrawCallback.Type) { - // If the graphic is within a cell, ensure that the graphic does not exceed - // the dimensions of the cell. - - if (Self->CurrentCell) { - if (layout->BoundX + layout->BoundWidth > Self->CurrentCell->AbsX + Self->CurrentCell->Width) { - layout->BoundWidth = Self->CurrentCell->AbsX + Self->CurrentCell->Width - layout->BoundX; - } - - if (layout->BoundY + layout->BoundHeight > Self->CurrentCell->AbsY + Self->CurrentCell->Height) { - layout->BoundHeight = Self->CurrentCell->AbsY + Self->CurrentCell->Height - layout->BoundY; - } - } - - auto opacity = Bitmap->Opacity; - Bitmap->Opacity = 255; - auto routine = (void (*)(OBJECTPTR, rkSurface *, objBitmap *))layout->DrawCallback.StdC.Routine; - routine(object, Surface, Bitmap); - Bitmap->Opacity = opacity; - } - } - - if (escobject->ObjectID < 0) ReleaseObject(object); - } -*/ - } - - break; - } - - case ESC_FONT: { - auto style = escape_data(Self->Stream, i); - if ((font = lookup_font(style->Index, "draw_document"))) { - font->Bitmap = Bitmap; - if (tabfocus IS FALSE) font->Colour = style->Colour; - else font->Colour = Self->SelectColour; - - if (style->Options & FSO_ALIGN_RIGHT) font->Align = ALIGN_RIGHT; - else if (style->Options & FSO_ALIGN_CENTER) font->Align = ALIGN_HORIZONTAL; - else font->Align = 0; - - if (style->Options & FSO_UNDERLINE) font->Underline = font->Colour; - else font->Underline.Alpha = 0; - } - break; - } - - case ESC_LIST_START: - if (esclist) { - auto ptr = esclist; - esclist = escape_data(Self->Stream, i); - esclist->Stack = ptr; - } - else esclist = escape_data(Self->Stream, i); - break; - - case ESC_LIST_END: - if (esclist) esclist = esclist->Stack; - break; - - case ESC_PARAGRAPH_START: - if (escpara) { - auto ptr = escpara; - escpara = escape_data(Self->Stream, i); - escpara->Stack = ptr; - } - else escpara = escape_data(Self->Stream, i); - - if ((esclist) and (escpara->ListItem)) { - // Handling for paragraphs that form part of a list - - if ((esclist->Type IS LT_CUSTOM) or (esclist->Type IS LT_ORDERED)) { - if (escpara->CustomString) { - font->X = fx - escpara->ItemIndent; - font->Y = segment->Y + font->Leading + (segment->BaseLine - font->Ascent); - font->AlignWidth = segment->AlignWidth; - font->setString((STRING)(escpara + 1)); - font->draw(); - } - } - else if (esclist->Type IS LT_BULLET) { - #define SIZE_BULLET 5 - // TODO: Requires conversion to vector - //gfxDrawEllipse(Bitmap, - // fx - escpara->ItemIndent, segment->Y + ((segment->BaseLine - SIZE_BULLET)/2), - // SIZE_BULLET, SIZE_BULLET, Bitmap->packPixel(esclist->Colour), TRUE); - } - } - break; - - case ESC_PARAGRAPH_END: - if (escpara) escpara = escpara->Stack; - break; - - case ESC_TABLE_START: { - if (esctable) { - auto ptr = esctable; - esctable = escape_data(Self->Stream, i); - esctable->Stack = ptr; - } - else esctable = escape_data(Self->Stream, i); - - //log.trace("Draw Table: %dx%d,%dx%d", esctable->X, esctable->Y, esctable->Width, esctable->Height); - - if (esctable->Colour.Alpha > 0) { - gfxDrawRectangle(Bitmap, - esctable->X+esctable->Thickness, esctable->Y+esctable->Thickness, - esctable->Width-(esctable->Thickness<<1), esctable->Height-(esctable->Thickness<<1), - Bitmap->packPixel(esctable->Colour), BAF::FILL|BAF::BLEND); - } - - if (esctable->Shadow.Alpha > 0) { - Bitmap->Opacity = esctable->Shadow.Alpha; - for (LONG j=0; j < esctable->Thickness; j++) { - gfxDrawRectangle(Bitmap, - esctable->X+j, esctable->Y+j, - esctable->Width-(j<<1), esctable->Height-(j<<1), - Bitmap->packPixel(esctable->Shadow), 0); - } - Bitmap->Opacity = alpha; - } - break; - } - - case ESC_TABLE_END: - if (esctable) esctable = esctable->Stack; - break; - - case ESC_ROW: { - if (escrow) { - auto ptr = escrow; - escrow = escape_data(Self->Stream, i); - escrow->Stack = ptr; - } - else escrow = escape_data(Self->Stream, i); - - if (escrow->Colour.Alpha) { - gfxDrawRectangle(Bitmap, esctable->X, escrow->Y, esctable->Width, escrow->RowHeight, - Bitmap->packPixel(escrow->Colour), BAF::FILL|BAF::BLEND); - } - break; - } - - case ESC_ROW_END: - if (escrow) escrow = escrow->Stack; - break; - - case ESC_CELL: { - if (esccell) { - auto ptr = esccell; - esccell = escape_data(Self->Stream, i); - esccell->Stack = ptr; - } - else esccell = escape_data(Self->Stream, i); - - Self->CurrentCell = esccell; - - if (esccell->Colour.Alpha > 0) { // Fill colour - WORD border; - if (esccell->Shadow.Alpha > 0) border = 1; - else border = 0; - - gfxDrawRectangle(Bitmap, esccell->AbsX+border, esccell->AbsY+border, - esctable->Columns[esccell->Column].Width-border, escrow->RowHeight-border, - Bitmap->packPixel(esccell->Colour), BAF::FILL|BAF::BLEND); - } - - if (esccell->Shadow.Alpha > 0) { // Border colour - gfxDrawRectangle(Bitmap, esccell->AbsX, esccell->AbsY, esctable->Columns[esccell->Column].Width, - escrow->RowHeight, Bitmap->packPixel(esccell->Shadow), 0); - } - break; - } - - case ESC_CELL_END: - if (esccell) esccell = esccell->Stack; - Self->CurrentCell = esccell; - break; - - case ESC_LINK: { - esclink = escape_data(Self->Stream, i); - if (Self->HasFocus) { - if ((Self->Tabs[Self->FocusIndex].Type IS TT_LINK) and (Self->Tabs[Self->FocusIndex].Ref IS esclink->ID) and (Self->Tabs[Self->FocusIndex].Active)) { - link_save_rgb = font->Colour; - font->Colour = Self->SelectColour; - tabfocus = TRUE; - } - } - - break; - } - - case ESC_LINK_END: - if (tabfocus) { - font->Colour = link_save_rgb; - tabfocus = FALSE; - } - break; - } - - i += ESCAPE_LEN(Self->Stream+i); - } - else if (!oob) { - if (Self->Stream[i] <= 0x20) { strbuffer[si++] = ' '; i++; } - else strbuffer[si++] = Self->Stream[i++]; - - // Print the string buffer content if the next string character is an escape code. - - if (Self->Stream[i] IS CTRL_CODE) { - strbuffer[si] = 0; - font->X = fx; - font->Y = segment->Y + font->Leading + (segment->BaseLine - font->Ascent); - font->AlignWidth = segment->AlignWidth; - font->setString(strbuffer); - font->draw(); - fx = font->EndX; - si = 0; - } - } - else i++; - } - - strbuffer[si] = 0; - - if ((si > 0) and (!oob)) { - font->X = fx; - font->Y = segment->Y + font->Leading + (segment->BaseLine - font->Ascent); - font->AlignWidth = segment->AlignWidth; - font->setString(strbuffer); - font->draw(); - fx = font->EndX; - } - } // for loop -} - -//******************************************************************************************************************** - -static void draw_border(extDocument *Self, objSurface *Surface, objBitmap *Bitmap) -{ - if ((!Self->BorderEdge) or (Self->BorderEdge IS (DBE_TOP|DBE_BOTTOM|DBE_LEFT|DBE_RIGHT))) { - gfxDrawRectangle(Bitmap, 0, 0, Surface->Width, Surface->Height, Bitmap->packPixel(Self->Border), BAF::NIL); - } - else { - if (Self->BorderEdge & DBE_TOP) { - gfxDrawRectangle(Bitmap, 0, 0, Surface->Width, 1, Bitmap->packPixel(Self->Border), BAF::NIL); - } - if (Self->BorderEdge & DBE_LEFT) { - gfxDrawRectangle(Bitmap, 0, 0, 1, Surface->Height, Bitmap->packPixel(Self->Border), BAF::NIL); - } - if (Self->BorderEdge & DBE_RIGHT) { - gfxDrawRectangle(Bitmap, Surface->Width-1, 0, 1, Surface->Height, Bitmap->packPixel(Self->Border), BAF::NIL); - } - if (Self->BorderEdge & DBE_BOTTOM) { - gfxDrawRectangle(Bitmap, 0, Surface->Height-1, Surface->Width, 1, Bitmap->packPixel(Self->Border), BAF::NIL); - } - } -} - -//******************************************************************************************************************** - -static LONG xml_content_len(XMLTag *Tag) -{ - LONG len; - - if (!Tag->Attrib->Name) { - for (len=0; Tag->Attrib->Value[len]; len++); - } - else if ((Tag = Tag->Child)) { - len = 0; - while (Tag) { - len += xml_content_len(Tag); - Tag = Tag->Next; - } - } - else return 0; - - return len; -} - -//******************************************************************************************************************** - -static void xml_extract_content(XMLTag *Tag, char *Buffer, LONG *Index, BYTE Whitespace) -{ - if (!Tag->Attrib->Name) { - CSTRING content; - LONG pos = *Index; - if ((content = Tag->Attrib->Value)) { - if (Whitespace) { - for (LONG i=0; content[i]; i++) Buffer[pos++] = content[i]; - } - else for (LONG i=0; content[i]; i++) { // Skip whitespace - if (content[i] <= 0x20) while ((content[i+1]) and (content[i+1] <= 0x20)) i++; - Buffer[pos++] = content[i]; - } - } - Buffer[pos] = 0; - *Index = pos; - } - else if ((Tag = Tag->Child)) { - while (Tag) { - xml_extract_content(Tag, Buffer, Index, Whitespace); - Tag = Tag->Next; - } - } -} - -//******************************************************************************************************************** - -static ERROR keypress(extDocument *Self, LONG Flags, LONG Value, LONG Unicode) -{ - pf::Log log(__FUNCTION__); - struct acScroll scroll; - - log.function("Value: %d, Flags: $%.8x, ActiveEdit: %p", Value, Flags, Self->ActiveEditDef); - - if ((Self->ActiveEditDef) and (gfxGetUserFocus() != Self->PageID)) { - deactivate_edit(Self, TRUE); - } - - if (Self->ActiveEditDef) { - UBYTE *stream; - - reset_cursor(Self); - - if (!(stream = Self->Stream)) return ERR_ObjectCorrupt; - - if (Unicode) { - // Delete any text that is selected - - if ((Self->SelectIndex != -1) and (Self->SelectIndex != Self->CursorIndex)) { - LONG start, end; - if (Self->SelectIndex < Self->CursorIndex) { start = Self->SelectIndex; end = Self->CursorIndex; } - else { start = Self->CursorIndex; end = Self->SelectIndex; } - - CopyMemory(stream + end, stream + start, Self->StreamLen + 1 - end); - Self->StreamLen -= end - start; - - Self->SelectIndex = -1; - Self->CursorIndex = start; - } - - // Output the character - - char string[12]; - UTF8WriteValue(Unicode, string, sizeof(string)); - docInsertText(Self, string, Self->CursorIndex, TRUE); // Will set UpdateLayout to TRUE - Self->CursorIndex += StrLength(string); // Reposition the cursor - - layout_doc_fast(Self); - - resolve_fontx_by_index(Self, Self->CursorIndex, &Self->CursorCharX); - - DRAW_PAGE(Self); - return ERR_Okay; - } - - switch(Value) { - case K_TAB: { - log.branch("Key: Tab"); - if (Self->TabFocusID) acFocus(Self->TabFocusID); - else { - if ((Flags & KQ::SHIFT) != KQ::NIL) advance_tabfocus(Self, -1); - else advance_tabfocus(Self, 1); - } - break; - } - - case K_ENTER: { - // Delete any text that is selected - - if ((Self->SelectIndex != -1) and (Self->SelectIndex != Self->CursorIndex)) { - LONG start, end; - if (Self->SelectIndex < Self->CursorIndex) { start = Self->SelectIndex; end = Self->CursorIndex; } - else { start = Self->CursorIndex; end = Self->SelectIndex; } - - CopyMemory(stream + end, stream + start, Self->StreamLen + 1 - end); - Self->StreamLen -= end - start; - - Self->SelectIndex = -1; - Self->CursorIndex = start; - } - - docInsertXML(Self, "
    ", Self->CursorIndex); - NEXT_CHAR(stream, Self->CursorIndex); - - layout_doc_fast(Self); - resolve_fontx_by_index(Self, Self->CursorIndex, &Self->CursorCharX); - DRAW_PAGE(Self); - break; - } - - case K_LEFT: { - Self->SelectIndex = -1; - - LONG index = Self->CursorIndex; - if ((stream[index] IS CTRL_CODE) and (ESCAPE_CODE(stream, index) IS ESC_CELL)) { - // Cursor cannot be moved any further left. The cursor index should never end up here, but - // better to be safe than sorry. - - } - else { - while (index > 0) { - PREV_CHAR(stream, index); - if (stream[index] IS CTRL_CODE) { - if (ESCAPE_CODE(stream, index) IS ESC_CELL) { - auto cell = escape_data(stream, index); - if (cell->CellID IS Self->ActiveEditCellID) break; - } - else if (ESCAPE_CODE(stream, index) IS ESC_OBJECT); - else continue; - } - - if (!resolve_fontx_by_index(Self, index, &Self->CursorCharX)) { - Self->CursorIndex = index; - DRAW_PAGE(Self); - log.warning("LeftCursor: %d, X: %d", Self->CursorIndex, Self->CursorCharX); - } - break; - } - } - break; - } - - case K_RIGHT: { - LONG code; - - Self->SelectIndex = -1; - - LONG index = Self->CursorIndex; - while (stream[index]) { - if (stream[index] IS CTRL_CODE) { - code = ESCAPE_CODE(stream, index); - if (code IS ESC_CELL_END) { - auto cell_end = escape_data(stream, index); - if (cell_end->CellID IS Self->ActiveEditCellID) { - // End of editing zone - cursor cannot be moved any further right - break; - } - } - else if (code IS ESC_OBJECT); // Objects are treated as content, so do nothing special for these and drop through to next section - else { - NEXT_CHAR(stream, index); - continue; - } - } - - // The current index references a content character or object. Advance the cursor to the next index. - - NEXT_CHAR(stream, index); - if (!resolve_fontx_by_index(Self, index, &Self->CursorCharX)) { - Self->CursorIndex = index; - DRAW_PAGE(Self); - log.warning("RightCursor: %d, X: %d", Self->CursorIndex, Self->CursorCharX); - } - break; - } - break; - } - - case K_HOME: { - break; - } - - case K_END: { - break; - } - - case K_UP: - break; - - case K_DOWN: - break; - - case K_BACKSPACE: { - LONG index = Self->CursorIndex; - if ((stream[index] IS CTRL_CODE) and (ESCAPE_CODE(stream, index) IS ESC_CELL)) { - // Cursor cannot be moved any further left - } - else { - PREV_CHAR(stream, index); - - if ((stream[index] IS CTRL_CODE) and (ESCAPE_CODE(stream, index) IS ESC_CELL)); - else { - // Delete the character/escape code - - if ((Self->SelectIndex != -1) and (Self->SelectIndex != Self->CursorIndex)) { - LONG start, end; - if (Self->SelectIndex < Self->CursorIndex) { start = Self->SelectIndex; end = Self->CursorIndex; } - else { start = index; end = Self->SelectIndex; } - - CopyMemory(stream + end, stream + start, Self->StreamLen + 1 - end); - Self->StreamLen -= end - start; - Self->CursorIndex = start; - } - else { - CopyMemory(stream + Self->CursorIndex, stream + index, Self->StreamLen + 1 - Self->CursorIndex); - Self->StreamLen -= (Self->CursorIndex - index); - Self->CursorIndex = index; - } - - Self->SelectIndex = -1; - - Self->UpdateLayout = TRUE; - layout_doc_fast(Self); - resolve_fontx_by_index(Self, Self->CursorIndex, &Self->CursorCharX); - DRAW_PAGE(Self); - - #ifdef DBG_STREAM - print_stream(Self, stream); - #endif - } - } - break; - } - - case K_DELETE: { - LONG end; - - LONG index = Self->CursorIndex; - if ((stream[index] IS CTRL_CODE) and (ESCAPE_CODE(stream, index) IS ESC_CELL_END)) { - // Not allowed to delete the end point - } - else { - if ((Self->SelectIndex != -1) and (Self->SelectIndex != Self->CursorIndex)) { - LONG start; - if (Self->SelectIndex < Self->CursorIndex) { start = Self->SelectIndex; end = Self->CursorIndex; } - else { start = Self->CursorIndex; end = Self->SelectIndex; } - - CopyMemory(stream + end, stream + start, Self->StreamLen + 1 - end); - Self->StreamLen -= end - start; - - if (Self->CursorIndex > Self->SelectIndex) { - Self->CursorIndex = Self->SelectIndex; - } - - Self->SelectIndex = -1; - - } - else { - end = index; - NEXT_CHAR(stream, end); - - CopyMemory(stream + end, stream + Self->CursorIndex, Self->StreamLen + 1 - end); - Self->StreamLen -= (end - Self->CursorIndex); - - } - - Self->UpdateLayout = TRUE; - layout_doc_fast(Self); - resolve_fontx_by_index(Self, Self->CursorIndex, &Self->CursorCharX); - DRAW_PAGE(Self); - - #ifdef DBG_STREAM - print_stream(Self, stream); - #endif - } - - break; - } - } - } - else switch (Value) { - // NB: When not in edit mode, only the navigation keys are enabled - case K_TAB: - log.branch("Key: Tab"); - if (Self->TabFocusID) acFocus(Self->TabFocusID); - else if ((Flags & KQ::SHIFT) != KQ::NIL) advance_tabfocus(Self, -1); - else advance_tabfocus(Self, 1); - break; - - case K_ENTER: { - LONG j; - LONG tab = Self->FocusIndex; - if ((tab >= 0) and (tab < Self->TabIndex)) { - log.branch("Key: Enter, Tab: %d/%d, Type: %d", tab, Self->TabIndex, Self->Tabs[tab].Type); - - if ((Self->Tabs[tab].Type IS TT_LINK) and (Self->Tabs[tab].Active)) { - for (j=0; j < Self->TotalLinks; j++) { - if ((Self->Links[j].EscapeCode IS ESC_LINK) and (Self->Links[j].Link->ID IS Self->Tabs[tab].Ref)) { - exec_link(Self, j); - break; - } - } - } - } - break; - } - - case K_PAGE_DOWN: - scroll.DeltaX = 0; - scroll.DeltaY = Self->AreaHeight; - scroll.DeltaZ = 0; - QueueAction(AC_Scroll, Self->SurfaceID, &scroll); - break; - - case K_PAGE_UP: - scroll.DeltaX = 0; - scroll.DeltaY = -Self->AreaHeight; - scroll.DeltaZ = 0; - QueueAction(AC_Scroll, Self->SurfaceID, &scroll); - break; - - case K_LEFT: - scroll.DeltaX = -10; - scroll.DeltaY = 0; - scroll.DeltaZ = 0; - QueueAction(AC_Scroll, Self->SurfaceID, &scroll); - break; - - case K_RIGHT: - scroll.DeltaX = 10; - scroll.DeltaY = 0; - scroll.DeltaZ = 0; - QueueAction(AC_Scroll, Self->SurfaceID, &scroll); - break; - - case K_DOWN: - scroll.DeltaX = 0; - scroll.DeltaY = 10; - scroll.DeltaZ = 0; - QueueAction(AC_Scroll, Self->SurfaceID, &scroll); - break; - - case K_UP: - scroll.DeltaX = 0; - scroll.DeltaY = -10; - scroll.DeltaZ = 0; - QueueAction(AC_Scroll, Self->SurfaceID, &scroll); - break; - } - - return ERR_Okay; -} - -//******************************************************************************************************************** - -static ERROR load_doc(extDocument *Self, CSTRING Path, BYTE Unload, BYTE UnloadFlags) -{ - pf::Log log(__FUNCTION__); - - log.branch("Loading file '%s', page '%s'", Path, Self->PageName); - - if (Unload) unload_doc(Self, UnloadFlags); - - process_parameters(Self, Path); - - // Generate a path without parameter values. - - LONG i; - for (i=0; Path[i]; i++) { - if ((Path[i] IS '&') or (Path[i] IS '#') or (Path[i] IS '?')) break; - } - char path[i+1]; - CopyMemory(Path, path, i); - path[i] = 0; - - if (!AnalysePath(path, NULL)) { - OBJECTPTR task; - if ((task = CurrentTask())) task->setPath(path); - - if (auto xml = objXML::create::integral( - fl::Flags(XMF_ALL_CONTENT|XMF_PARSE_HTML|XMF_STRIP_HEADERS|XMF_WELL_FORMED), - fl::Path(path), fl::ReadOnly(TRUE))) { - - if (Self->XML) FreeResource(Self->XML); - Self->XML = xml; - - AdjustLogLevel(3); - Self->Error = process_page(Self, xml); - AdjustLogLevel(-3); - - return Self->Error; - } - else { - char msg[300]; - snprintf(msg, sizeof(msg), "Failed to load document file '%s'", path); - error_dialog("Document Load Error", msg, Self->Error); - return log.warning(ERR_OpenFile); - } - } - else return log.warning(ERR_FileNotFound); -} - -//******************************************************************************************************************** -// This function lays out the document so that it is ready to be drawn. It calculates the position, pixel length and -// height of each line and rearranges any objects that are present in the document. - -static void layout_doc(extDocument *Self) -{ - pf::Log log(__FUNCTION__); - objFont *font; - LONG pagewidth, pageheight, hscroll_offset; - BYTE vertical_repass; - - if (Self->UpdateLayout IS FALSE) return; - if ((!Self->Stream) or (!Self->Stream[0])) return; - - // Initial height is 1, not the surface height because we want to accurately report the final height of the page. - - pageheight = 1; - - LAYOUT("~layout_doc()","Area: %dx%d,%dx%d Visible: %d ----------", - Self->AreaX, Self->AreaY, Self->AreaWidth, Self->AreaHeight, Self->VScrollVisible); - - Self->BreakLoop = MAXLOOP; - -restart: - Self->BreakLoop--; - - hscroll_offset = 0; - - if (Self->PageWidth <= 0) { - // If no preferred page width is set, maximise the page width to the available viewing area - pagewidth = Self->AreaWidth - hscroll_offset; - } - else { - if (!Self->RelPageWidth) { - // Page width is fixed - pagewidth = Self->PageWidth; - } - else { - // Page width is relative - pagewidth = (Self->PageWidth * (Self->AreaWidth - hscroll_offset)) / 100; - } - } - - if (pagewidth < Self->MinPageWidth) pagewidth = Self->MinPageWidth; - - Self->SegCount = 0; - Self->SortCount = 0; - Self->TotalClips = 0; - Self->TotalLinks = 0; - Self->ECIndex = 0; - Self->PageProcessed = FALSE; - Self->Error = ERR_Okay; - Self->Depth = 0; - - if (!(font = lookup_font(0, "layout_doc"))) { // There is no content loaded for display - LAYOUT_LOGRETURN(); - return; - } - - layout_section(Self, 0, &font, 0, 0, &pagewidth, &pageheight, Self->LeftMargin, Self->TopMargin, Self->RightMargin, - Self->BottomMargin, &vertical_repass); - - LAYOUT("layout_doc:","Section layout complete."); - - // If the resulting page width has increased beyond the available area, increase the MinPageWidth value to reduce - // the number of passes required for the next time we do a layout. - - - if ((pagewidth > Self->AreaWidth) and (Self->MinPageWidth < pagewidth)) Self->MinPageWidth = pagewidth; - - Self->PageHeight = pageheight; -// if (Self->PageHeight < Self->AreaHeight) Self->PageHeight = Self->AreaHeight; - Self->CalcWidth = pagewidth; - - // Recalculation may be required if visibility of the scrollbar needs to change. - - if ((Self->BreakLoop > 0) and (!Self->Error)) { - if (Self->PageHeight > Self->AreaHeight) { - // Page height is bigger than the surface, so the scrollbar needs to be visible. - - if (!Self->VScrollVisible) { - LAYOUT("layout_doc","Vertical scrollbar visibility needs to be enabled, restarting..."); - Self->VScrollVisible = TRUE; - Self->BreakLoop = MAXLOOP; - goto restart; - } - } - else { - // Page height is smaller than the surface, so the scrollbar needs to be invisible. - - if (Self->VScrollVisible) { - LAYOUT("layout_doc","Vertical scrollbar needs to be invisible, restarting..."); - Self->VScrollVisible = FALSE; - Self->BreakLoop = MAXLOOP; - goto restart; - } - } - } - - // Look for clickable links that need to be aligned and adjust them (links cannot be aligned until the entire - // width of their line is known, hence it's easier to make a final adjustment for all links post-layout). - - if (!Self->Error) { - DocLink *link; - DocSegment *segment; - escLink *esclink; - LONG i; - - for (i=0; i < Self->TotalLinks; i++) { - if (Self->Links[i].EscapeCode != ESC_LINK) continue; - - link = &Self->Links[i]; - esclink = link->Link; - if (esclink->Align & (FSO_ALIGN_RIGHT|FSO_ALIGN_CENTER)) { - segment = &Self->Segments[link->Segment]; - if (esclink->Align & FSO_ALIGN_RIGHT) { - link->X = segment->X + segment->AlignWidth - link->Width; - } - else if (esclink->Align & FSO_ALIGN_CENTER) { - link->X = link->X + ((segment->AlignWidth - link->Width) / 2); - } - } - } - } - - // Build the sorted segment array - - if (!Self->Error) { - if (Self->SortSegments) { - FreeResource(Self->SortSegments); - Self->SortSegments = NULL; - } - - if (Self->SegCount) { - if (!AllocMemory(sizeof(Self->SortSegments[0]) * Self->SegCount, MEM::NO_CLEAR, &Self->SortSegments)) { - LONG seg, i, j; - - for (i=0, seg=0; seg < Self->SegCount; seg++) { - if ((Self->Segments[seg].Height > 0) and (Self->Segments[seg].Width > 0)) { - Self->SortSegments[i].Segment = seg; - Self->SortSegments[i].Y = Self->Segments[seg].Y; - i++; - } - } - Self->SortCount = i; - - // Shell sort - - LONG h = 1; - while (h < Self->SortCount / 9) h = 3 * h + 1; - - for (; h > 0; h /= 3) { - for (i=h; i < Self->SortCount; i++) { - SortSegment temp = Self->SortSegments[i]; - for (j=i; (j >= h) and (sortseg_compare(Self, Self->SortSegments + j - h, &temp) < 0); j -= h) { - Self->SortSegments[j] = Self->SortSegments[j - h]; - } - Self->SortSegments[j] = temp; - } - } - } - else Self->Error = ERR_AllocMemory; - } - } - - Self->UpdateLayout = FALSE; - -#ifdef DBG_LINES - print_lines(Self); - //print_sorted_lines(Self); - print_tabfocus(Self); -#endif - - // If an error occurred during layout processing, unload the document and display an error dialog. (NB: While it is - // possible to display a document up to the point at which the error occurred, we want to maintain a strict approach - // so that human error is considered excusable in document formatting). - - if (Self->Error) { - unload_doc(Self, ULD_REDRAW); - - CSTRING errstr; - if (Self->Error IS ERR_Loop) errstr = "This page cannot be rendered correctly due to its design."; - else errstr = GetErrorMsg(Self->Error); - - char msg[200]; - LONG i = StrCopy("A failure occurred during the layout of this document - it cannot be displayed.\n\nDetails: ", msg, sizeof(msg)); - StrCopy(errstr, msg+i, sizeof(msg)-i); - - error_dialog("Document Layout Error", msg, 0); - } - else { - for (auto trigger=Self->Triggers[DRT_AFTER_LAYOUT]; trigger; trigger=trigger->Next) { - if (trigger->Function.Type IS CALL_SCRIPT) { - OBJECTPTR script; - if ((script = trigger->Function.Script.Script)) { - const ScriptArg args[] = { - { "ViewWidth", FD_LONG, { .Long = Self->AreaWidth } }, - { "ViewHeight", FD_LONG, { .Long = Self->AreaHeight } }, - { "PageWidth", FD_LONG, { .Long = Self->CalcWidth } }, - { "PageHeight", FD_LONG, { .Long = Self->PageHeight } } - }; - scCallback(script, trigger->Function.Script.ProcedureID, args, ARRAYSIZE(args), NULL); - } - } - else if (trigger->Function.Type IS CALL_STDC) { - auto routine = (void (*)(APTR, extDocument *, LONG, LONG, LONG, LONG))trigger->Function.StdC.Routine; - if (routine) { - pf::SwitchContext context(trigger->Function.StdC.Context); - routine(trigger->Function.StdC.Context, Self, Self->AreaWidth, Self->AreaHeight, Self->CalcWidth, Self->PageHeight); - } - } - } - } - - LAYOUT_LOGRETURN(); -} - -//******************************************************************************************************************** -// Converts XML into RIPPLE bytecode, then displays the page that is referenced by the PageName field by calling -// layout_doc(). If the PageName is unspecified, we use the first that has no name, otherwise the first page -// irrespective of the name. -// -// This function does not clear existing data, so you can use it to append new content to existing document content. - -static ERROR process_page(extDocument *Self, objXML *xml) -{ - DOUBLE x, y; - - if (!xml) return ERR_NoData; - - pf::Log log(__FUNCTION__); - - log.branch("Page: %s, XML: %d, Tags: %d", Self->PageName, xml->UID, xml->TagCount); - - // Look for the first page that matches the requested page name (if a name is specified). Pages can be located anywhere - // within the XML source - they don't have to be at the root. - - XMLTag **firstpage = NULL; - XMLTag **page; - if ((page = xml->Tags)) { - while (*page) { - if (!StrMatch("page", page[0]->Attrib->Name)) { - if (!firstpage) firstpage = page; - CSTRING name = XMLATTRIB(page[0], "name"); - if (!name) { - if (!Self->PageName) break; - } - else if (!StrMatch(Self->PageName, name)) break; - } - page++; - } - - if ((!Self->PageName) and (firstpage)) page = firstpage; - } - - Self->Error = ERR_Okay; - if ((page) and (*page) and (page[0]->Child)) { - Self->PageTag = *page; - - UBYTE noheader = FALSE; - UBYTE nofooter = FALSE; - if (XMLATTRIB(page[0], "noheader")) noheader = TRUE; - if (XMLATTRIB(page[0], "nofooter")) nofooter = TRUE; - - if (Self->Segments) ClearMemory(Self->Segments, sizeof(Self->Segments[0]) * Self->MaxSegments); - - if (!Self->Buffer) { - Self->BufferSize = 65536; - if (AllocMemory(Self->BufferSize, MEM::NO_CLEAR, &Self->Buffer)) { - return ERR_AllocMemory; - } - } - - if (!Self->Temp) { - Self->TempSize = 65536; - if (AllocMemory(Self->TempSize, MEM::NO_CLEAR, &Self->Temp)) { - return ERR_AllocMemory; - } - } - - if (!Self->VArg) { - if (AllocMemory(sizeof(Self->VArg[0]) * MAX_ARGS, MEM::NO_CLEAR, &Self->VArg)) { - return ERR_AllocMemory; - } - } - - Self->SegCount = 0; - Self->SortCount = 0; - Self->XPosition = 0; - Self->YPosition = 0; - Self->ClickHeld = FALSE; - Self->SelectStart = 0; - Self->SelectEnd = 0; - Self->UpdateLayout = TRUE; - Self->ArgIndex = 0; - Self->ArgNestIndex = 0; - Self->BufferIndex = 0; - Self->Error = ERR_Okay; - - //drwForbidDrawing(); // We do this to prevent objects from posting draw messages on their creation - - // Process tags at the root level, but only those that we allow up to the first entry. - - { - pf::Log log(__FUNCTION__); - - log.traceBranch("Processing root level tags."); - - Self->BodyTag = NULL; - Self->HeaderTag = NULL; - Self->FooterTag = NULL; - for (LONG i=0; xml->Tags[i]; i++) { - if (!xml->Tags[i].Attrib->Name) continue; // Ignore content - - ULONG tag_hash = StrHash(xml->Tags[i].Attrib->Name, 0); - - if (tag_hash IS HASH_page) { - break; - } - else if (tag_hash IS HASH_body) { - // If a tag contains any children, it is treated as a template and must contain an tag so - // that the XML insertion point is known. - - Self->BodyTag = xml->Tags[i].Child; - insert_xml(Self, xml, xml->Tags[i], Self->StreamLen, 0); - i = xml->Tags[i].Next->Index - 1; - } - else if (tag_hash IS HASH_background) { - insert_xml(Self, xml, xml->Tags[i], Self->StreamLen, 0); - i = xml->Tags[i].Next->Index - 1; - } - else if (tag_hash IS HASH_editdef) { - insert_xml(Self, xml, xml->Tags[i], Self->StreamLen, 0); - i = xml->Tags[i].Next->Index - 1; - } - else if (tag_hash IS HASH_template) { - insert_xml(Self, xml, xml->Tags[i], Self->StreamLen, 0); - i = xml->Tags[i].Next->Index - 1; - } - else if (tag_hash IS HASH_head) { - insert_xml(Self, xml, xml->Tags[i], Self->StreamLen, 0); - i = xml->Tags[i].Next->Index - 1; - } - else if (tag_hash IS HASH_info) { - insert_xml(Self, xml, xml->Tags[i], Self->StreamLen, 0); - i = xml->Tags[i].Next->Index - 1; - } - else if (tag_hash IS HASH_include) { - insert_xml(Self, xml, xml->Tags[i], Self->StreamLen, 0); - i = xml->Tags[i].Next->Index - 1; - } - else if (tag_hash IS HASH_parse) { - insert_xml(Self, xml, xml->Tags[i], Self->StreamLen, 0); - i = xml->Tags[i].Next->Index - 1; - } - else if (tag_hash IS HASH_script) { - insert_xml(Self, xml, xml->Tags[i], Self->StreamLen, 0); - i = xml->Tags[i].Next->Index - 1; - } - else if (tag_hash IS HASH_header) { - Self->HeaderTag = xml->Tags[i].Child; - i = xml->Tags[i].Next->Index - 1; - } - else if (tag_hash IS HASH_footer) { - Self->FooterTag = xml->Tags[i].Child; - i = xml->Tags[i].Next->Index - 1; - } - else log.warning("Tag '%s' Not supported at the root level.", xml->Tags[i].Attrib->Name); - } - } - - if ((Self->HeaderTag) and (noheader IS FALSE)) { - pf::Log log(__FUNCTION__); - log.traceBranch("Processing header."); - insert_xml(Self, xml, Self->HeaderTag, Self->StreamLen, IXF_SIBLINGS|IXF_RESETSTYLE); - } - - if (Self->BodyTag) { - pf::Log log(__FUNCTION__); - log.traceBranch("Processing this page through the body tag."); - - START_TEMPLATE(page[0]->Child, xml, NULL) - - insert_xml(Self, xml, Self->BodyTag, Self->StreamLen, IXF_SIBLINGS|IXF_RESETSTYLE); - - END_TEMPLATE() - } - else { - pf::Log log(__FUNCTION__); - log.traceBranch("Processing page '%s'.", XMLATTRIB(page[0], "name")); - insert_xml(Self, xml, page[0]->Child, Self->StreamLen, IXF_SIBLINGS|IXF_RESETSTYLE); - } - - if ((Self->FooterTag) and (!nofooter)) { - pf::Log log(__FUNCTION__); - log.traceBranch("Processing footer."); - insert_xml(Self, xml, Self->FooterTag, Self->StreamLen, IXF_SIBLINGS|IXF_RESETSTYLE); - } - - //drwPermitDrawing(); - - #ifdef DBG_STREAM - print_stream(Self, Self->Stream); - #endif - - // If an error occurred then we have to kill the document as the stream may contain disconnected escape - // sequences (e.g. an unterminated ESC_TABLE sequence). - - if (Self->Error) unload_doc(Self, 0); - - Self->UpdateLayout = TRUE; - if (Self->initialised()) redraw(Self, TRUE); - - if (Self->Buffer) { FreeResource(Self->Buffer); Self->Buffer = NULL; } - if (Self->Temp) { FreeResource(Self->Temp); Self->Temp = NULL; } - if (Self->VArg) { FreeResource(Self->VArg); Self->VArg = NULL; } - - #ifdef RAW_OUTPUT - objFile::create file = { fl::Path("drive1:doc-stream.bin"), fl::Flags(FL::NEW|FL::WRITE) }; - file->write(Self->Stream, Self->StreamLen); - #endif - } - else { - if (Self->PageName) { - char buffer[200]; - snprintf(buffer, sizeof(buffer), "Failed to find page '%s' in document '%s'.", Self->PageName, Self->Path); - error_dialog("Load Failed", buffer, 0); - } - else { - char buffer[200]; - snprintf(buffer, sizeof(buffer), "Failed to find a valid page in document '%s'.", Self->Path); - error_dialog("Load Failed", buffer, 0); - } - Self->Error = ERR_Search; - } - - if ((!Self->Error) and (Self->MouseOver)) { - if (!gfxGetRelativeCursorPos(Self->PageID, &x, &y)) { - check_mouse_pos(Self, x, y); - } - } - - if (!Self->PageProcessed) { - for (auto trigger=Self->Triggers[DRT_PAGE_PROCESSED]; trigger; trigger=trigger->Next) { - if (trigger->Function.Type IS CALL_SCRIPT) { - if (auto script = trigger->Function.Script.Script) { - scCallback(script, trigger->Function.Script.ProcedureID, NULL, 0, NULL); - } - } - else if (trigger->Function.Type IS CALL_STDC) { - if (auto routine = (void (*)(APTR, extDocument *))trigger->Function.StdC.Routine) { - pf::SwitchContext context(trigger->Function.StdC.Context); - routine(trigger->Function.StdC.Context, Self); - } - } - } - } - - Self->PageProcessed = TRUE; - return Self->Error; -} - -//******************************************************************************************************************** - -static docresource * add_resource_id(extDocument *Self, LONG ID, LONG Type) -{ - docresource *r; - if (!AllocMemory(sizeof(docresource), MEM::NO_CLEAR, &r)) { - r->ObjectID = ID; - r->Type = Type; - r->ClassID = 0; - r->Prev = NULL; - r->Next = Self->Resources; - if (Self->Resources) Self->Resources->Prev = r; - Self->Resources = r; - return r; - } - else return NULL; -} - -//******************************************************************************************************************** - -static docresource * add_resource_ptr(extDocument *Self, APTR Address, LONG Type) -{ - docresource *r; - if (!AllocMemory(sizeof(docresource), MEM::NO_CLEAR, &r)) { - r->Address = Address; - r->Type = Type; - r->Prev = NULL; - r->Next = Self->Resources; - if (Self->Resources) Self->Resources->Prev = r; - Self->Resources = r; - return r; - } - else return NULL; -} - -//******************************************************************************************************************** -// This function removes all allocations that were made in displaying the current page, and resets a number of -// variables that they are at the default settings for the next page. -// -// Set Terminate to TRUE only if the document object is being destroyed. -// -// The PageName is not freed because the desired page must not be dropped during refresh of manually loaded XML for -// example. - -static ERROR unload_doc(extDocument *Self, BYTE Flags) -{ - pf::Log log(__FUNCTION__); - - log.branch("Flags: $%.2x", Flags); - - #ifdef DBG_STREAM - print_stream(Self, Self->Stream); - #endif - - //drwForbidDrawing(); - - log.trace("Resetting variables."); - - Self->FontColour.Red = 0; - Self->FontColour.Green = 0; - Self->FontColour.Blue = 0; - Self->FontColour.Alpha = 1.0; - - Self->Highlight = glHighlight; - - Self->CursorColour.Red = 0.4; - Self->CursorColour.Green = 0.4; - Self->CursorColour.Blue = 0.8; - Self->CursorColour.Alpha = 1.0; - - Self->LinkColour.Red = 0; - Self->LinkColour.Green = 0; - Self->LinkColour.Blue = 1.0; - Self->LinkColour.Alpha = 1.0; - - Self->Background.Red = 1.0; - Self->Background.Green = 1.0; - Self->Background.Blue = 1.0; - Self->Background.Alpha = 1.0; - - Self->SelectColour.Red = 1.0; - Self->SelectColour.Green = 0; - Self->SelectColour.Blue = 0; - Self->SelectColour.Alpha = 1.0; - - Self->LeftMargin = 10; - Self->RightMargin = 10; - Self->TopMargin = 10; - Self->BottomMargin = 10; - Self->XPosition = 0; - Self->YPosition = 0; -// Self->ScrollVisible = FALSE; - Self->PageHeight = 0; - Self->Invisible = 0; - Self->PageWidth = 0; - Self->CalcWidth = 0; - Self->LineHeight = LINE_HEIGHT; // Default line height for measurements concerning the page (can be derived from a font) - Self->RelPageWidth = FALSE; - Self->MinPageWidth = MIN_PAGE_WIDTH; - Self->DefaultScript = NULL; - Self->SegCount = 0; - Self->SortCount = 0; - Self->BkgdGfx = 0; - Self->DrawIntercept = 0; - Self->FontSize = DEFAULT_FONTSIZE; - Self->FocusIndex = -1; - Self->PageProcessed = FALSE; - Self->MouseOverSegment = -1; - Self->SelectIndex = -1; - Self->CursorIndex = -1; - Self->ActiveEditCellID = 0; - Self->ActiveEditDef = NULL; - - if (Self->ActiveEditDef) { - deactivate_edit(Self, FALSE); - } - - free_links(Self); - - Self->ECIndex = 0; - Self->ECMax = 0; - if (Self->EditCells) { FreeResource(Self->EditCells); Self->EditCells = NULL; } - - if (Self->LinkIndex != -1) { - Self->LinkIndex = -1; - gfxRestoreCursor(PTR_DEFAULT, Self->UID); - } - - if (Self->FontFace) FreeResource(Self->FontFace); - if (Flags & ULD_TERMINATE) Self->FontFace = NULL; - else Self->FontFace = StrClone("Open Sans"); - - if (Self->Stream) FreeResource(Self->Stream); - if (Flags & ULD_TERMINATE) Self->Stream = NULL; - else Self->Stream = (UBYTE *)StrClone(""); - - Self->StreamLen = 0; - Self->StreamSize = 0; - Self->PageTag = NULL; - - if (Self->SortSegments) { FreeResource(Self->SortSegments); Self->SortSegments = NULL; } - - if (Self->Segments) { - FreeResource(Self->Segments); - Self->Segments = NULL; - Self->MaxSegments = 0; - } - - if (!(Flags & ULD_TERMINATE)) { - Self->MaxSegments = 100; - if (AllocMemory(sizeof(Self->Segments[0]) * Self->MaxSegments, MEM::NO_CLEAR, &Self->Segments) != ERR_Okay) { - return ERR_AllocMemory; - } - } - - for (LONG i=0; i < ARRAYSIZE(Self->Triggers); i++) { - if (auto trigger = Self->Triggers[i]) { - while (trigger) { - auto next = trigger->Next; - FreeResource(trigger); - trigger = next; - } - Self->Triggers[i] = NULL; - } - } - - if (Flags & ULD_TERMINATE) { - if (Self->Vars) { FreeResource(Self->Vars); Self->Vars = NULL; } - } - - if (Self->Params) { FreeResource(Self->Params); Self->Params = NULL; } - if (Self->Clips) { FreeResource(Self->Clips); Self->Clips = NULL; } - if (Self->Keywords) { FreeResource(Self->Keywords); Self->Keywords = NULL; } - if (Self->Author) { FreeResource(Self->Author); Self->Author = NULL; } - if (Self->Copyright) { FreeResource(Self->Copyright); Self->Copyright = NULL; } - if (Self->Description) { FreeResource(Self->Description); Self->Description = NULL; } - if (Self->Title) { FreeResource(Self->Title); Self->Title = NULL; } - - if (Self->EditDefs) { - auto edit = Self->EditDefs; - while (edit) { - auto next = edit->Next; - FreeResource(edit); - edit = next; - } - Self->EditDefs = NULL; - } - - auto mouseover = Self->MouseOverChain; - while (mouseover) { - auto mousenext = mouseover->Next; - FreeResource(mouseover); - mouseover = mousenext; - } - Self->MouseOverChain = NULL; - - // Free templates only if they have been modified (no longer at the default settings). - - if (Self->Templates) { - if (Self->TemplatesModified != Self->Templates->Modified) { - FreeResource(Self->Templates); - Self->Templates = NULL; - } - } - - if (Self->Tabs) { - FreeResource(Self->Tabs); - Self->Tabs = NULL; - Self->MaxTabs = 0; - Self->TabIndex = 0; - } - - // Remove all page related resources - - { - pf::Log log(__FUNCTION__); - log.traceBranch("Freeing page-allocated resources."); - - auto resource = Self->Resources; - while (resource) { - if (resource->Type IS RT_MEMORY) { - FreeResource(resource->Memory); - } - else if ((resource->Type IS RT_PERSISTENT_SCRIPT) or (resource->Type IS RT_PERSISTENT_OBJECT)) { - if (Flags & ULD_REFRESH) { - // Persistent objects and scripts will survive refreshes - resource = resource->Next; - continue; - } - else if (Flags & ULD_TERMINATE) FreeResource(resource->ObjectID); - else SendMessage(MSGID_FREE, MSF::NIL, &resource->ObjectID, sizeof(OBJECTID)); - } - else if (resource->Type IS RT_OBJECT_UNLOAD_DELAY) { - if (Flags & ULD_TERMINATE) FreeResource(resource->ObjectID); - else SendMessage(MSGID_FREE, MSF::NIL, &resource->ObjectID, sizeof(OBJECTID)); - } - else FreeResource(resource->ObjectID); - - if (resource IS Self->Resources) Self->Resources = resource->Next; - if (resource->Prev) resource->Prev->Next = resource->Next; - if (resource->Next) resource->Next->Prev = resource->Prev; - - auto next = resource->Next; - FreeResource(resource); - resource = next; - } - } - - if (!Self->Templates) { - if (!(Self->Templates = objXML::create::integral(fl::Name("xmlTemplates"), fl::Statement(glDefaultStyles), - fl::Flags(XMF_PARSE_HTML|XMF_STRIP_HEADERS)))) return ERR_CreateObject; - - Self->TemplatesModified = Self->Templates->Modified; - } - - Self->NoWhitespace = TRUE; // Reset whitespace flag - - if (Self->PageID) acMoveToPoint(Self->PageID, 0, 0, 0, MTF::X|MTF::Y); - - //drwPermitDrawing(); - - Self->UpdateLayout = TRUE; - Self->GeneratedID = AllocateID(IDTYPE_GLOBAL); - - if (Flags & ULD_REDRAW) { - DRAW_PAGE(Self); - } - - return ERR_Okay; -} - -//******************************************************************************************************************** -// If the layout needs to be recalculated, set the UpdateLayout field before calling this function. - -static void redraw(extDocument *Self, BYTE Focus) -{ - pf::Log log(__FUNCTION__); - - log.traceBranch(""); - - //drwForbidDrawing(); - - AdjustLogLevel(3); - layout_doc(Self); - AdjustLogLevel(-3); - - //drwPermitDrawing(); - - DRAW_PAGE(Self); - - if ((Focus) and (Self->FocusIndex != -1)) set_focus(Self, -1, "redraw()"); -} - -//******************************************************************************************************************** - -#if 0 -static LONG get_line_from_index(extDocument *Self, LONG Index) -{ - LONG line; - for (line=1; line < Self->SegCount; line++) { - if (Index < Self->Segments[line].Index) { - return line-1; - } - } - return 0; -} -#endif - -//******************************************************************************************************************** - -static void error_dialog(CSTRING Title, CSTRING Message, ERROR Error) -{ - pf::Log log(__FUNCTION__); - static OBJECTID dialog_id = 0; - - log.warning("%s", Message); - - if (dialog_id) { - if (CheckObjectExists(dialog_id) IS ERR_True) return; - } - - OBJECTPTR dialog; - if (!NewObject(ID_SCRIPT, &dialog)) { - dialog->setFields(fl::Name("scDialog"), fl::Owner(CurrentTaskID()), fl::Path("scripts:gui/dialog.fluid")); - - acSetVar(dialog, "modal", "1"); - acSetVar(dialog, "title", Title); - acSetVar(dialog, "options", "okay"); - acSetVar(dialog, "type", "error"); - - CSTRING errstr; - if ((Error) and (errstr = GetErrorMsg(Error))) { - LONG len = strlen(Message); - char buffer[len+120]; - if (Message) { - len = StrCopy(Message, buffer, sizeof(buffer)); - len += StrCopy("\n\nDetails: ", buffer+len, sizeof(buffer)-len); - } - else len = StrCopy("Error: ", buffer, sizeof(buffer)); - - StrCopy(errstr, buffer+len, sizeof(buffer)-len); - acSetVar(dialog, "message", buffer); - } - else acSetVar(dialog, "message", Message); - - if ((!InitObject(dialog)) and (!acActivate(dialog))) { - CSTRING *results; - LONG size; - if ((!GetFieldArray(dialog, FID_Results, (APTR *)&results, &size)) and (size > 0)) { - dialog_id = StrToInt(results[0]); - } - } - } -} - -//******************************************************************************************************************** - -static void add_template(extDocument *Self, objXML *XML, XMLTag *Tag) -{ - pf::Log log(__FUNCTION__); - LONG i; - - // Validate the template (must have a name) - - for (i=1; i < Tag->TotalAttrib; i++) { - if ((!StrMatch("name", Tag->Attrib[i].Name)) and (Tag->Attrib[i].Value[0])) break; - if ((!StrMatch("class", Tag->Attrib[i].Name)) and (Tag->Attrib[i].Value[0])) break; - } - - if (i >= Tag->TotalAttrib) { - log.warning("A